In questa sezione

Cosa copre questa pagina

Una cartuccia è un piccolo programma che dichiara capacità tipizzate e parla Bifaci, il protocollo binario a frame di CapDAG tra host e cartuccia. Genera uno starter corrente in Python, Rust, Go o Swift con capdag new. Il menu Transmute può quindi scoprirne le destinazioni, il planner può instradare attraverso di essa e le altre cartucce possono chiamarla.

Cos’è una cartuccia, come parla il protocollo wire, come registra gli handler e come funziona l’invocazione peer-to-peer tra cartucce fanno parte del runtime delle cartucce CapDAG, cross-platform. È specificato una volta sola ed è lo stesso su ogni host:

Per il formato wire stesso (layout dei frame, handshake, stream multiplexati) consulta i documenti del protocollo Bifaci.

Questa pagina copre il livello specifico per macOS sopra quel runtime: come FabricLoom trova le cartucce su disco, come il sistema operativo le isola, cosa devi firmare e notarizzare per distribuirne una e come confezionarla in un installer .pkg che gli utenti possono aprire con doppio click.

Per un tutorial end-to-end, usa Costruisci la tua prima cartuccia. Va dallo scaffold Python mantenuto a una cartuccia di sviluppo installata e a una peer call ospitata.

Dove vivono le cartucce su disco

Su macOS, FabricLoom scansiona due root di cartucce all’avvio e ne monitora i cambiamenti:

  • FabricLoom.app/Contents/Resources/cartridgesrv-signed/cartridges/: cartucce incluse, distribuite con l’applicazione.
  • /Library/Application Support/FabricLoom/Cartridges/: cartucce installate dall’utente. Gli installer .pkg scrivono qui, e tu la popoli a mano durante lo sviluppo.

All’interno di entrambe le root, ogni cartuccia segue il layout imposto dalla spec CapDAG:

{cartridges-root}/{slug}/v{registry_version}/{channel}/{name}/{version}/
    cartridge.json
    {entry-binary}

{slug} è dev per le cartucce non pubblicate. Per le cartucce pubblicate attraverso un registro è una trasformazione deterministica e leggibile del dominio del registro (il suo host, più :port se presente): in minuscolo, con qualsiasi carattere al di fuori di [a-z0-9.-] sostituito da -. v{registry_version} è la versione del regime del registro con cui la cartuccia è stata installata (v1 oggi) e si applica a ogni installazione, incluso dev (per esempio dev/v1/release/...). {channel} è nightly o release. {name} e {version} provengono dal manifest della cartuccia e devono corrispondere esattamente ai nomi delle directory. L’host lo verifica al momento della discovery e rifiuta le discrepanze come bad_installation.

Il manifest pubblicato del registro dichiara due campi accanto alle sue voci: registryVersion, un intero che indica la versione del regime che determina il livello v{registry_version} del layout, e fabricRegistryUrl, il registro fabric rispetto a cui le cartucce sono state costruite. Se aggiungi registri di cartucce extra o personalizzati, tramite l’interfaccia dell’app o la CLI capdag, ogni registro deve dichiarare lo stesso fabricRegistryUrl affinché le loro cartucce restino comparabili. Un registro costruito rispetto a un fabric diverso viene rifiutato.

Il record di installazione cartridge.json è il contratto di validazione pre-spawn dell’host. I campi obbligatori sono name, version, channel, registry_url (presente ma eventualmente null), entry e installed_at. La discovery può segnalare manifest_invalid, bad_installation, entry_point_missing o handshake_failed quando record, layout, entry o avvio del protocollo non sono validi.

Sandbox e isolamento dei processi

Le cartucce girano in un servizio XPC in sandbox, separato sia dal motore sia dall’app rivolta all’utente. FabricLoom non carica mai il codice delle cartucce nel proprio processo.

A runtime:

  1. Il servizio XPC tiene in memoria i manifest di ogni cartuccia scoperta.
  2. Quando un cap viene dispatchato a una cartuccia, il servizio avvia il binario di entry della cartuccia come processo figlio.
  3. La cartuccia parla il protocollo Bifaci su stdin/stdout: un handshake, poi richieste e risposte multiplexate per frame.
  4. La sandbox XPC limita ciò che la cartuccia può fare. Per default non ha accesso alla rete né ai file utente, salvo quelli esplicitamente passati.
  5. Gli heartbeat mantengono viva la connessione, e un heartbeat mancato abbatte la cartuccia.

Il lato del runtime host di tutto questo (spawn dei processi, routing dei frame, monitoraggio della salute) è il runtime host CapDAG. Il livello di relay che collega più cartucce attraverso una singola connessione è relay switch e relay topology.

L’envelope XPC e il profilo della sandbox sono le parti specifiche di macOS. Una cartuccia che ha bisogno di entitlement oltre il default, come l’accesso di rete per una cartuccia cloud-proxy, li dichiara nel .pkg e deve essere revisionata prima di essere accettata nel manifest canonico.

Firma del codice e notarizzazione

Le cartucce distribuite tramite MachineFabric, cioè qualsiasi cosa finisca nel manifest canonico delle cartucce, devono essere:

  • Firmate con un certificato Developer ID.
  • Notarizzate da Apple.
  • Confezionate come installer .pkg firmato.

Per lo sviluppo locale usa capdag dev-install .. La CLI valida il manifest e lo prepara nel registry di sviluppo dell’utente. Il tutorial Costruisci la tua prima cartuccia dimostra questo flusso.

Per la distribuzione, la pipeline di build è la seguente:

# 1. Compila un binario universale (esempio Rust)
cargo build --release --target aarch64-apple-darwin
cargo build --release --target x86_64-apple-darwin
lipo -create -output mycartridge \
  target/aarch64-apple-darwin/release/mycartridge \
  target/x86_64-apple-darwin/release/mycartridge

# 2. Firma il binario con hardened runtime
codesign --sign "Developer ID Application: Your Name (TEAMID)" \
  --options runtime \
  --timestamp \
  mycartridge

# 3. Prepara il layout di installazione
mkdir -p pkg-root/{slug}/v{registry_version}/{channel}/mycartridge/1.0.0
cp mycartridge cartridge.json pkg-root/{slug}/v{registry_version}/{channel}/mycartridge/1.0.0/

# 4. Costruisci il pacchetto installer
pkgbuild --root ./pkg-root \
  --identifier com.yourcompany.mycartridge \
  --version 1.0.0 \
  --install-location "/Library/Application Support/FabricLoom/Cartridges" \
  mycartridge.pkg

# 5. Firma il pacchetto
productsign --sign "Developer ID Installer: Your Name (TEAMID)" \
  mycartridge.pkg \
  mycartridge-signed.pkg

# 6. Notarizza e applica lo staple
xcrun notarytool submit mycartridge-signed.pkg \
  --apple-id [email protected] \
  --team-id TEAMID \
  --password "@keychain:AC_PASSWORD" \
  --wait
xcrun stapler staple mycartridge-signed.pkg

La porzione {slug}/v{registry_version}/{channel}/ del percorso di installazione segue le regole di layout CapDAG. Per una cartuccia pubblicata su un registro, {slug} è la trasformazione del dominio dell’URL del registro (il suo host, più :port se presente, in minuscolo con qualsiasi carattere al di fuori di [a-z0-9.-] sostituito da -).

Linguaggi e SDK

Il protocollo delle cartucce è agnostico rispetto al linguaggio. Qualsiasi eseguibile che implementa i contratti del manifest e di Bifaci può essere una cartuccia. I percorsi runtime mantenuti sono:

Linguaggio Pacchetto Note
Rust capdag e capdag-cartridge-sdk Runtime di riferimento e contratti di prodotto
Go capdag-go e capdag-cartridge-sdk-go Runtime mirror e contratti LLM rispecchiati
Swift / Objective-C capdag-objc e capdag-cartridge-sdk-objc Runtime Apple e helper di prodotto
Python capdag su PyPI Runtime usato in Costruisci la tua prima cartuccia

I pacchetti CapDAG implementano i contratti URN, planning, Bifaci e runtime. Gli SDK di prodotto MachineFabric aggiungono payload LLM condivisi e alcune policy di prodotto, e la loro superficie esatta cambia per linguaggio. Vedi il Riferimento degli SDK per cartucce e i pattern degli handler di CapDAG.

L’SDK non è il contratto del protocollo. Un’altra implementazione si conforma producendo un manifest valido e implementando Bifaci, ma gli scaffold mantenuti sono il punto di partenza supportato e codificano dettagli facili da sbagliare.

Differenze di implementazione tra host

Rust è il riferimento comportamentale di CapDAG. FabricLoom usa un host XPC su macOS e un daemon Rust su Linux e Windows. CapDAG mantiene anche implementazioni host/relay Go e Swift per i rispettivi ruoli documentati. Le implementazioni condividono il contratto wire ma non gli stessi confini di modulo. Vedi CapDAG Rust vs Swift per le differenze API e host di quella coppia.

Per il contratto pubblico degli errori usato dai runtime delle cartucce e dagli host, vedi gestione degli errori. La persistenza dei task e la gestione della pressione del sistema operativo sono responsabilità dell’implementazione host, non del protocollo pubblico delle cartucce.

Pubblicazione

Per rendere disponibile la tua cartuccia attraverso il browser di cartucce di FabricLoom, proponila su cartridge-shelf, la casella di proposte pubblica. Ogni proposta viene revisionata a mano e integrata nel manifest canonico cartridges.machinefabric.com che viene distribuito con ogni installazione.

Il processo di proposta completo e i criteri di inclusione (cosa deve contenere il repository, cosa comporta la validità del cap URN e cosa succede tra la proposta e l’accettazione) sono in Contribuire.

Proponi una cartuccia