THE REPOSITORY
finestructure-ai/claude-pluginSponsored
Open finestructure-ai/claude-pluginL'intero repository sono sette file
Clonalo e l'albero dei file entra in una schermata sola:
.claude-plugin/
plugin.json 686 B
marketplace.json 507 B
commands/
deploy.md 3.3 KB
fs-domain.md 905 B
fs-status.md 741 B
skills/
fine-structure/
SKILL.md 4.0 KB
LICENSE MIT
README.md 2.3 KBNiente package.json, niente lockfile, niente CI, niente dist. Nulla viene compilato o impacchettato, e non esiste una versione di questo repository la cui build possa fallire. Se hai rimandato la scrittura di un plugin perché davi per scontata una toolchain, ecco la correzione: il formato è una convenzione di cartelle più due file JSON, e il resto è prosa.
plugin.json è un puntatore, non un programma
Il manifesto porta i soliti campi di identità (name, versione 0.1.0, description, author, homepage, repository, license, keywords) e poi un unico blocco che svolge tutto il lavoro interessante:
"mcpServers": {
"finestructure": {
"type": "http",
"url": "https://finestructure.ai/api/mcp"
}
}Due chiavi. Nessun command, nessun args, nessun env. Confrontalo con la forma che assume la maggior parte delle configurazioni MCP: un processo locale (npx, uvx, un percorso a un binario), una lista di argomenti e una mappa env che tiene una chiave API. Dichiarare invece un endpoint streamable HTTP sposta il server fuori dalla macchina dell'utente, ed è per questo che 105 strumenti (il numero indicato dal file skill) stanno dietro un manifesto da 686 byte. Nulla nella versione di Node o di Python dell'utente può rompere l'installazione, e le modifiche lato server arrivano senza una release del plugin. In cambio si perde riproducibilità: la superficie degli strumenti non si può fissare dal lato client.
marketplace.json rende il repository il canale di distribuzione di se stesso
Claude Code installa i plugin dai marketplace e non da un registro di pacchetti, e un marketplace è un file JSON che elenca plugin con un percorso sorgente. Il secondo file dentro .claude-plugin fa esattamente questo, e la sua unica voce di plugin porta "source": "./". Il repository è insieme il plugin e il marketplace che lo serve, quindi pubblicare è un git push pubblico:
/plugin marketplace add finestructure-ai/claude-plugin
/plugin install finestructure@finestructureI due token identici nella seconda riga sono il nome del plugin presso il nome del marketplace, e coincidono perché entrambi si chiamano finestructure. Se copi questo schema, dai loro nomi diversi. Le istruzioni di installazione diventano più chiare e ti resta spazio per aggiungere un secondo plugin in futuro.
I comandi sono modelli di prompt con frontmatter
Ogni file in commands/ è frontmatter YAML più prosa. deploy.md dichiara un description e un argument-hint, le due stringhe che l'utente vede nel selettore, poi stende un albero decisionale numerato: controllare la radice del progetto per un .finestructure.json con un app_id, altrimenti chiamare list_apps e cercare una corrispondenza di nome, altrimenti trattarlo come primo rilascio e usare $ARGUMENTS come nome dell'applicazione. fs-status.md pesa 741 byte e fa il lavoro di un sottocomando CLI: risolvere l'applicazione, chiamare get_app_status, get_app_links e get_errors, riassumere. fs-domain.md percorre nell'ordine add_custom_domain, get_domain_verification, check_domain_verification, get_domain_ssl_status e set_primary_domain.
Il punto di progetto: nessuno di questi file chiama niente. Nominano strumenti, fissano un ordine e descrivono cosa fare quando un passo fallisce. L'esecuzione avviene quando il modello invoca gli strumenti MCP. Un comando slash è un prompt messo sotto controllo di versione, quindi rivederlo non significa chiedersi se la logica è corretta, ma se l'istruzione è ambigua.
Le righe migliori sono quelle negative. deploy.md vieta gli strumenti di cancellazione a meno che l'utente non li abbia chiesti esplicitamente. fs-domain.md annota che la propagazione DNS richiede da minuti a ore e prescrive di suggerire un nuovo tentativo più tardi invece di girare in un ciclo di verifica. Questa è politica dei tentativi e sono barriere di sicurezza scritte come frasi, ed è proprio ciò che i plugin ingenui tralasciano.
Skill contro command: attrazione contro spinta
skills/fine-structure/SKILL.md ha due campi di frontmatter, name e description, e la description si legge come una condizione di attivazione e non come un riassunto: da usare ogni volta che l'utente vuole distribuire, creare o aggiornare un'applicazione, collegare un dominio, gestire dati o segreti. Quella formulazione è voluta. Un comando scatta perché una persona lo ha digitato. Uno skill scatta perché il modello ha fatto combaciare la descrizione con quello che sta succedendo.
La divisione dei contenuti ne discende. SKILL.md è un modello mentale, non un elenco di compiti: che cos'è qui un'applicazione (pagine JSX, componenti condivisi, schemi di entità, nessun codice server arbitrario), che cosa sono le entità, quali operazioni consumano crediti. Poi i flussi di lavoro come catene di strumenti, da get_app_files a read_app_file, a write_app_file, a validate_app e a publish_app, con set di modifiche per le modifiche che toccano più file. Poi la semantica degli errori, che è la parte più densa per byte: gli errori di autenticazione significano riconnettersi, quelli di credito significano ricaricare, e nessuno dei due è ripetibile. Un agente privo di questa conoscenza ritenta in ciclo un fallimento non ripetibile, e su una piattaforma a consumo quel ciclo ha un prezzo.
La regola per il tuo plugin viene fuori pulita. Se un file di comando sta spiegando che cos'è il tuo prodotto, quel paragrafo appartiene allo skill. I comandi restano procedure.
OAuth è il motivo per cui il manifesto non contiene segreti
L'endpoint si autentica con OAuth 2.1 e registrazione dinamica del client, quindi la prima chiamata a uno strumento apre una pagina di consenso nel browser e il token finisce nell'archivio delle credenziali di Claude Code, non nel repository. Un fork è sicuro per costruzione, la revoca avviene lato server e non come modifica di configurazione che deve raggiungere ogni macchina, e a nessuno viene chiesto di incollare una chiave a lunga durata in un file che dista un commit distratto da un diff pubblico.
Che cosa copiare per il tuo plugin
Indicazioni concrete, più o meno in ordine di costruzione:
- Parti da .claude-plugin/plugin.json con name, version e description. Tutto il resto è opzionale.
- Se gestisci un endpoint MCP ospitato, dichiara "type": "http" con una url invece di un comando locale. Questo cancella l'ambiente di esecuzione dell'utente dalla tua superficie di supporto.
- Spedisci marketplace.json nello stesso repository con "source": "./" finché hai un solo plugin, e dagli un nome diverso da quello del plugin.
- Dai a ogni comando un description e un argument-hint nel frontmatter, scritti come risposte alle domande che cosa fa e che cosa scrivo dopo.
- Usa $ARGUMENTS invece di inventare una sintassi posizionale. Non c'è nessun parser, solo sostituzione.
- Scrivi il corpo dei comandi come alberi decisionali con gli strumenti nominati in modo esplicito. "Se il file di configurazione esiste leggi app_id, altrimenti chiama list_apps" regge meglio di un paragrafo di intenzioni.
- Metti per iscritto la semantica dei fallimenti: quali errori sono definitivi, quali ripetibili, e che cosa dire invece di ritentare.
- Nomina gli strumenti distruttivi nella prosa e vietali se non richiesti.
- Tieni il modello di dominio in SKILL.md e la procedura nel comando. La duplicazione tra i due è un cattivo segno.
- Prova con /plugin marketplace add su un percorso locale o sul tuo fork prima di indirizzare qualcuno a main.
Spigoli
Tre, onestamente, e nessuno letale. È tutto in inglese, e il formato non offre alcun aggancio per rimediare: non c'è alcuna chiave di locale nel frontmatter, quindi localizzare significa duplicare i file di comando o accettare il disallineamento.
La storia dell'assenza di chiavi API ha un asterisco. SKILL.md ammette che gli strumenti di generazione dei media stanno fuori dalla connessione OAuth e richiedono un token MCP statico con permessi sui media, creato nello Studio della piattaforma e inviato in un header bearer. Il plugin lo gestisce bene, perché dice al modello di spiegare l'assenza invece di ritentare contro un muro, ma è una seconda via di autenticazione avvitata su un progetto il cui argomento di vendita è averne una sola.
E siamo alla versione 0.1.0, senza changelog, senza test e senza CI. Per del markdown è difendibile, anche se un controllo di schema JSON in un hook di pre-commit intercetterebbe l'unica classe di errore che rompe davvero le installazioni, un manifesto malformato. L'invio alla directory è in revisione mentre scriviamo, quindi per ora si installa tramite il riferimento al repository.
Leggi prima i tre file di comando, poi SKILL.md, poi i due file JSON. In quest'ordine il formato si spiega da solo: il markdown decide che cosa deve succedere e in che ordine, il server MCP decide che cosa viene davvero eseguito, e il manifesto è la cucitura sottile tra i due.
QUESTIONS
Asked about this repository
- qual è la struttura minima di file per un plugin di claude code?
- Un file solo: .claude-plugin/plugin.json con un name, una version e una description. Comandi, skill, agenti e hook sono strati opzionali sopra. finestructure-ai/claude-plugin è un utile riferimento di dimensioni perché usa diversi di quegli strati e resta comunque a sette file e sotto i quattordici kilobyte, senza passo di build.
- come funzionano i comandi slash in un plugin di claude code?
- Un comando slash è un file markdown dentro commands/ il cui nome di file diventa il nome del comando. Il frontmatter fornisce un description e un argument-hint per il selettore, e il corpo è un prompt che il modello riceve quando il comando viene eseguito, con $ARGUMENTS sostituito da ciò che lo segue. Il file di per sé non esegue nulla, quindi il lavoro vero deve arrivare da strumenti che il modello può chiamare, ed è per questo che questo plugin abbina i comandi a un server MCP.
- serve una chiave API per usare un server MCP in un plugin di claude code?
- No, se il server parla OAuth. Questo manifesto dichiara soltanto "type": "http" e una url, e l'endpoint usa OAuth 2.1 con registrazione dinamica del client, quindi l'autorizzazione avviene nel browser e il token resta nell'archivio delle credenziali di Claude Code. L'alternativa, un blocco env che contiene una chiave, funziona ma mette un segreto a lunga durata in un file che gli utenti si passano. Un'avvertenza visibile qui: gli strumenti per i media stanno fuori da questo flusso e richiedono ancora un token statico.
- come trasformo un repository github in un marketplace di plugin per claude code?
- Aggiungi .claude-plugin/marketplace.json con un name, un owner e un array plugins. Se serve un plugin dello stesso repository, imposta il source di quel plugin a "./", che è quello che fa questo repository. Gli utenti poi eseguono /plugin marketplace add owner/repo seguito da /plugin install plugin-name@marketplace-name. Tra un git push e un plugin installabile non c'è né un registro né un passo di pubblicazione.
THE SPONSOR
The platform behind the endpoint
Fine Structure runs the hosted MCP server this plugin points at, and sponsors this publication.
finestructure.ai