# Governed Agent Skills (/docs/ai/governed-skills)



<StoryFrame label="Skill contract" title="Discover lightly. Load deliberately. Replay the exact artifact." accent="pressure">
  <StoryFact label="Artifact">
    Immutable, content-addressed tenant bundle
  </StoryFact>

  <StoryFact label="Baseline">
    Compact identity and capability summary only
  </StoryFact>

  <StoryFact label="Access">
    Broker-authorized reads with durable receipts
  </StoryFact>
</StoryFrame>

Ductor skills are tenant-scoped instruction bundles, not shell plugins. They let an
agent discover a compact capability summary and load detailed instructions only
when the task needs them. Skills are part of how a <Term name="Worker" /> that is
an agent is provisioned — governed, signed, and replayable, so what an agent was
told is as auditable as what it did. Pricing a skill ships as an opt-in surface
(`artifact_pricing.skill.enabled`): because a governed bundle is
content-addressed, its price pins id, version, **and** content hash, so
republishing different content under the same version cannot inherit the agreed
price. Each skill read reports its price basis, and when priced, the chargeable
micros and pricing version. An unpriced skill is not a free one.

Still on the roadmap: an agent's capped spend settling to the ledger.
`max_cost_cents` is enforced against the resolved price before provider I/O;
what is missing is the journal entry that would make that spend money.

<ProcessRail label="Artifact path" title="From promotion evidence to a governed read">
  <ProcessStep label="01" title="Sign" tone="pressure">
    Bind tenant provenance to the candidate bundle.
  </ProcessStep>

  <ProcessStep label="02" title="Certify" tone="gold">
    Verify policy, license, inventory, and content hashes.
  </ProcessStep>

  <ProcessStep label="03" title="Pin">
    Record the immutable version in the agent definition.
  </ProcessStep>

  <ProcessStep label="04" title="Read" tone="commit">
    Cross the governed broker and retain authorization receipts.
  </ProcessStep>
</ProcessRail>

## What a definition pins [#what-a-definition-pins]

An immutable agent definition records each bundle's id, version, content hash, and
manifest hash in a stable order. The baseline prompt receives only the id,
description, version, and content hash. Loading `SKILL.md` or another declared file
spends context budget and produces the normal policy, target, redaction, and result
receipts.

Replay always resolves the exact pinned bundle. Publishing a newer version never
changes an active or historical turn, and there is no fallback to `latest`.

## Promotion gate [#promotion-gate]

A bundle activates only after Ductor verifies all of the following:

* a trusted Ed25519 signer and tenant-scoped provenance;
* a passing certification receipt bound to the content and policy hashes;
* an allowed license and a present `SKILL.md`;
* the complete ordered file inventory, file hashes, content hash, and manifest hash;
* canonical relative paths with no traversal, absolute path, backslash, or symlink;
* at most 128 files, 256 KiB per file, 1 MiB total, and a 64 KiB manifest;
* execution disabled.

Bundle rows and files are append-only. Reusing one tenant/id/version with different
content is a conflict, not an update.

<Callout type="warn" title="Skills are read-only in the production contract">
  Ductor exposes `skill_load` and `skill_read`. It does not register `skill_execute`, a generic
  shell, a host-filesystem reader, an archive extractor, or an unrestricted network client.
  Executable helpers remain unavailable until a separate kernel/runtime sandbox passes escape,
  credential, egress, quota, timeout, output, and cancellation tests.
</Callout>

## Authorization and isolation [#authorization-and-isolation]

The tool receipt binds the tenant, session, definition manifest, skill and file,
schema, effective arguments, target fingerprint, duration/result limits, and
redaction policy. Cross-tenant lookup and a missing bundle return the same external
result, so ids cannot be used as an existence oracle.

There is no shared content cache in the correctness path. Retention uses the
authorized tenant purge path and removes the bundle and files together; direct
mutation remains denied.

## Production checklist [#production-checklist]

* Retain signature, provenance, certification, policy, license, and manifest evidence.
* Grant only `skill_load` and `skill_read` in the applicable tool-exposure policy.
* Set narrow result-size and deadline ceilings.
* Create a new bundle version for every content change.
* Revoke exposure policy during an incident; do not edit artifact rows.

## Related [#related]

<Cards>
  <Card title="Agent Tool Security" href="/docs/ai/agent-tool-security">
    Policies, target binding, approvals, and execution receipts.
  </Card>

  <Card title="Durable Agent Runtime" href="/docs/ai/durable-agent-runtime">
    Immutable definitions, projection, replay, and recovery.
  </Card>
</Cards>
