Block Kit

In questa pagina

Il Block Kit di EmDash consente ai plugin sandboxed di descrivere la loro interfaccia di amministrazione come JSON. L’host renderizza i blocchi — nessun JavaScript fornito dal plugin viene mai eseguito nel browser.

Come funziona

  1. L’utente naviga verso la pagina di amministrazione di un plugin.
  2. L’admin invia un’interazione page_load al percorso di amministrazione del plugin.
  3. Il plugin restituisce una BlockResponse contenente un array di blocchi.
  4. L’admin renderizza i blocchi utilizzando il componente BlockRenderer.
  5. Quando l’utente interagisce (fa clic su un pulsante, invia un form), l’admin invia l’interazione al plugin.
  6. Il plugin restituisce nuovi blocchi e il ciclo si ripete.
import { definePlugin } from "emdash";
import type { PluginContext } from "emdash";

interface BlockInteraction {
	type: "page_load" | "block_action" | "form_submit";
	page?: string;
	action_id?: string;
	values?: Record<string, unknown>;
}

export default definePlugin({
	routes: {
		admin: {
			handler: async (routeCtx, ctx: PluginContext) => {
				const interaction = routeCtx.input as BlockInteraction;

				if (interaction.type === "page_load") {
					return {
						blocks: [
							{ type: "header", text: "My Plugin Settings" },
							{
								type: "form",
								block_id: "settings",
								fields: [
									{ type: "text_input", action_id: "api_url", label: "API URL" },
									{ type: "toggle", action_id: "enabled", label: "Enabled", initial_value: true },
								],
								submit: { label: "Save", action_id: "save" },
							},
						],
					};
				}

				if (interaction.type === "form_submit" && interaction.action_id === "save") {
					await ctx.kv.set("settings", interaction.values);
					return {
						blocks: [/* ... updated blocks ... */],
						toast: { message: "Settings saved", type: "success" },
					};
				}

				return { blocks: [] };
			},
		},
	},
});

Il gestore di percorso in formato standard accetta due argomenti: routeCtx (con input, request, requestMeta) e ctx (il PluginContext).

Tipi di blocchi

TypeDescription
headerIntestazione grande e in grassetto
sectionTesto con elemento accessorio opzionale
dividerLinea orizzontale
fieldsGriglia etichetta/valore a due colonne
tableTabella dati con formattazione, ordinamento, paginazione
actionsRiga orizzontale di pulsanti e controlli
statsSchede metriche dashboard con indicatori di tendenza
formCampi di input con visibilità condizionale e invio
imageImmagine a livello di blocco con didascalia
contextPiccolo testo di aiuto attenuato
columnsLayout a 2–3 colonne con blocchi nidificati
emptySegnaposto stato vuoto con icona, titolo, descrizione, riga di comando opzionale e pulsanti d’azione
accordionSezione comprimibile che avvolge blocchi nidificati

Tipi di elementi

TypeDescription
buttonPulsante d’azione con dialogo di conferma opzionale
text_inputInput di testo su una o più righe
number_inputInput numerico con min/max
selectSelezione a discesa
toggleInterruttore on/off
secret_inputInput mascherato per chiavi API e token

Helper di costruzione

Il pacchetto @emdash-cms/blocks esporta helper di costruzione per un codice più pulito:

import { blocks, elements } from "@emdash-cms/blocks";

const { header, form, section, stats } = blocks;
const { textInput, toggle, select, button } = elements;

return {
	blocks: [
		header("SEO Settings"),
		form({
			blockId: "settings",
			fields: [
				textInput("site_title", "Site Title", { initialValue: "My Site" }),
				toggle("generate_sitemap", "Generate Sitemap", { initialValue: true }),
				select("robots", "Default Robots", [
					{ label: "Index, Follow", value: "index,follow" },
					{ label: "No Index", value: "noindex,follow" },
				]),
			],
			submit: { label: "Save", actionId: "save" },
		}),
	],
};

Campi condizionali

I campi del form possono essere mostrati condizionalmente in base ai valori di altri campi:

{
	"type": "toggle",
	"action_id": "auth_enabled",
	"label": "Enable Authentication"
}
{
	"type": "secret_input",
	"action_id": "api_key",
	"label": "API Key",
	"condition": { "field": "auth_enabled", "eq": true }
}

Il campo api_key appare solo quando auth_enabled è attivato. Le condizioni vengono valutate lato client senza round-trip.

Provalo

Usa il Block Playground per costruire e testare layout di blocchi in modo interattivo.