The Agent Package
This page renders Chapter 12 of the Common Agent Specification in its own numbering. Where this page and that document disagree, that document governs. Section numbers other than this page's own, such as Section 6 or 8.2, refer to the specification. The overview, and how the package fits with the Descriptor, the roles, and the catalog, is here.
An agent has an inside and an outside. The inside is what it is made of: skills, the scripts they run, the servers they reach. The outside is what a caller can rely on: what it does, what it refuses, what it needs, what it leaves behind, which is the Descriptor of Section 6. The inside has a portable format of its own, the Agent Plugin, whose standard says in its own words that distribution, installation, and permissions stay under each client's control. This chapter defines the thing that carries both halves from a description to a running agent with an identity: the Agent Package, what it contains, how the halves are joined, how it is published to and installed from a depot, and how a verifier can check that the agent answering on a network is the package that was built.
It is not a package format: Agent Plugins defines the layout and the manifest, and Agent Skills defines a skill folder; this chapter adds two files beside the manifest and one namespace inside it, restating neither. It is not a runtime, not a listing, and not a change to any wire.
1 Terms
These are the words this chapter uses for the things an install joins, and they are used in this sense throughout.
- Host: the machine an agent runs on. One host may hold many agents, each with its own home and its own identity.
- Harness: the program that does the thinking when a message arrives, whether a coding tool driven from a terminal, a model runner, or an agent framework. A harness is not an agent: it is what an agent runs on, and one harness may serve many agents on one host.
- Package: an Agent Plugin directory, or its archive, carrying a draft Descriptor and an install file at the paths in §2. A package is not an agent: it carries no subject, and until it is installed nobody can address it.
- Draft Descriptor: a Descriptor without a subject (6.2.1), inside a package. Bound Descriptor: the same document with its subject filled and signed, served by the running agent.
- Install file: the host-facing declaration of §4: what an installer must have and do.
- Agent: what exists after an install: a subject with a key and a handle, a home on a host, a harness configured to read the package, and whatever parts the binding requires to receive messages and answer them.
- Bare agent: an agent that carries no package and answers as its harness alone. It has a subject and a Descriptor like any other agent; what it does not have is offerings a package declared.
- Depot: where packages are published to and fetched from, by name, version, and digest. A depot is not a registry of agents (6.7): it holds packages, which contain drafts, and it never serves a draft as any agent's Descriptor.
- Installer: whatever performs §7; on a conforming deployment, an agent holding the deployment manager role of the roles registry.
An owner instructs a deploy; the installer installs the package; the result is an agent. The three words are not interchangeable: the deploy is the instruction, the install is the procedure, and the agent is what the procedure leaves behind.
2 Layout
A package is an Agent Plugin. Its portable parts are exactly what that standard says: plugin.json, skills/, and optionally mcp.json. Beside the manifest sit the two authored files this chapter adds, and one namespace directory holds the views generated from them.
<name>/
├── plugin.json the Agent Plugins manifest
├── descriptor.json the draft Descriptor: every caller-facing fact
├── install.json the install file: every host-facing fact
├── skills/<offering-id>/ one skill per offering: SKILL.md, scripts/, references/
├── mcp.json servers by role, no vendor (optional)
└── net.agentdoc.package/ NOT.md, RECORDS.md, SYSTEMS.md, generated
The manifest's extension entry for the namespace net.agentdoc.package carries pointers and digests, never copies:
"extensions": {
"net.agentdoc.package": {
"descriptor": { "path": "descriptor.json", "sha256": "<digest>" },
"install": { "path": "install.json", "sha256": "<digest>" },
"built": true,
"draft": true
}
}
The namespace is the same for every conforming implementation, so any reader that knows this chapter finds the pointers under one key. A package MUST declare the Agent Plugins schema version that clients read, and an implementation SHOULD validate against a pinned copy of that schema rather than a fetched one, so that a moved or unavailable address cannot make a valid package unverifiable.
3 The draft Descriptor
The draft Descriptor is the only authored spelling of every caller-facing fact in the package. Every rule of Section 6 applies to it unchanged: no subject, shapes only and never an address, credential, or endpoint, an absent member means not stated, versioned by replacement with its digest over exact bytes. Its refusals member is prose, and a builder SHOULD write it as one sentence per line, because an evaluator turns each refusal into a probe and a line is the one boundary it can rely on.
Two members are added to the Descriptor by this chapter, both optional and both ignored by a consumer that does not know them, as 6.2.4 requires:
records[]: what the agent must leave behind, each with aname,when(per_taskorstanding), and an optionalfile, a pattern relative to the records directory. A record is not an output: outputs are what a caller receives, records are what an operator and an auditor can inspect, and a caller reading outputs would be misled by a spend log listed among deliverables. An audit with the pattern is exact; without it, it falls back to the name.escalates[]: what always goes to a person, one sentence each.
A system in systems[] to which the agent sends a caller's material during the work SHOULD say so with leaves: true; a caller deciding whether to engage is entitled to know that their text leaves the agent.
4 The install file
The install file is the host-facing half. Everything in it is something an installer must have or do, and nothing in it is something a caller could act on. It MUST NOT contain a credential value, an address, an account identifier, or a host path outside the package: it names things, and the host resolves the names. Its format is "agent-install-v1", and it has five sections:
runtimes[]andbinaries[]: what must be present on the host before install proceeds, each with a purpose a person can read. The installer MUST check each and MUST stop and escalate when one is missing, never substitute.dependencies[]: what the skills' scripts need, per skill, as a lockfile with integrity hashes carried under the skill's own folder, and the lockfile's digest. The installer MUST install from the lockfile into the agent's own home, never system-wide, and MUST NOT execute install-time scripts or lifecycle hooks of any kind.systems[]: one entry per role the Descriptor names, and no others; the two sets MUST be equal. Each entry says what kind of thing the role is bound to (directory,mcp, orservice) and, for a service, the name of the credential the scripts expect, the environment variable they read it from, and whether the service spends and in what unit. Kindmcpbinds the role to an entry inmcp.json, which names the server by the same role and carries no vendor address. A service whose scripts also read a non-secret value the host must supply, such as a billing project, lists it undersettingsby variable name and purpose; the instruction supplies the value at install, and the record names the variable.ceilings[]: which spending systems need a ceiling and per what. The install file says a ceiling is required; the owner's instruction sets the number; the platform enforces it. A spending system with no ceiling entry does not conform.directories[]: the working directories the installer creates and binds, including where records land.
{
"format": "agent-install-v1",
"runtimes": [ { "name": "node", "version": ">=22" } ],
"binaries": [ { "name": "chromium", "purpose": "renders every step for the fit check" } ],
"dependencies": [ { "skill": "check-the-fit", "lockfile": "skills/check-the-fit/scripts/package-lock.json", "sha256": "<digest>" } ],
"systems": [
{ "role": "text-to-speech", "kind": "service", "credential": "tts-key", "env": "TTS_TOKEN", "spends": { "unit": "characters" } },
{ "role": "draft-host", "kind": "service", "credential": "draft-host-writer", "env": "DRAFT_HOST_TOKEN" },
{ "role": "brand-assets", "kind": "directory" }
],
"ceilings": [ { "system": "text-to-speech", "per": "task" } ],
"directories": [ { "name": "records", "purpose": "every record the descriptor names" }, { "name": "work" } ]
}
5 Skills and the generated views
One skill per offering, named by the offering's id, and no skill without an offering. A skill folder is an Agent Skill and MAY carry scripts/ and references/; its instructions are the place for the long-form judgment an agent needs to do the job well, and this chapter places no limit on their length. A skill MAY ship an acceptance check, a script that reads the skill's declared outputs and answers pass or fail on their form; it judges form, never quality.
NOT.md, RECORDS.md, and SYSTEMS.md exist so that a harness which reads markdown has them, and for no other reason. They are projections of the two authored files, generated by the builder, MUST NOT be edited by hand, and a checker regenerates them and compares bytes.
6 The rules
- One authored spelling. A caller-facing fact appears in the draft Descriptor and nowhere else in the package; a host-facing fact appears in the install file and nowhere else. The manifest points, the markdown projects, and neither restates.
- The inside matches the outside. Every offering has exactly one skill and every skill an offering; every system role in the Descriptor has exactly one install entry and every entry a role; every
mcp.jsonserver is a role. - Shapes in the Descriptor, names in the install file, values nowhere. A package MUST NOT contain a credential value, an address, an endpoint, or an account identifier in any file, and a depot MUST refuse to publish one that does.
- Nothing commercial. A package carries no price, no handling terms, and no claim about who may call the agent or whether a person attends it. Those attach at listing and at install, by whoever makes those decisions.
- One digest. A package is published and installed as an archive, and its SHA-256 over the archive bytes is the package's digest. Every record that mentions the package names that digest.
- The bound Descriptor is the draft plus a subject. The Descriptor a running agent serves MUST differ from the draft in its package only by the presence of
subjectandsignaturesand by the members the install decides:interaction,shape, andagent_versionwhen the draft leaves it empty (rule 4 keeps those out of the package). The deployment record names which members the binding added or changed. Any other difference means the agent is not the package that was built, and a verifier reports it. - Nobody runs a package's code but the agent. The depot executes nothing. The installer executes nothing from the package. The agent's harness runs the skills' scripts, in the agent's own home, with the credentials placed for it and no others.
- No hidden characters. A depot MUST scan every text file for zero-width characters, bidirectional controls, and the tag block before publishing, and refuse a package carrying one. Agent configuration has no gap between install and execution the way code does, so the check belongs at the door.
7 Publish, install, update, remove
Publish. A package is published to a depot by name and version, signed by its builder. A publish MUST carry the build record (8.2) whose package.sha256 equals the digest of the bytes being published, and a depot MUST refuse a publish without one or with a digest that does not match. A published version is immutable; a version can be withdrawn, which marks it and stops new installs, and is never deleted, because deploy records point at it. A depot serves bytes by digest and indexes the draft Descriptor and the install file, so a search can answer what a package does, refuses, needs, and spends; a package whose install file declares nothing is indexed as "not stated", never as needing nothing. A depot SHOULD expose list-versions, download, and publish over the registry HTTP API that Agent Package Manager clients speak, so the skills in its packages reach any client that installs plugins.
Install, on instruction from an owner and under the deployment manager's contract, in order: fetch by name and version and verify the digest against the build record and the manifest against the pinned schema; check every runtime and binary; create the agent's home and the declared directories; install the dependencies from each lockfile, executing nothing from the package; bind each system, a directory to a path under the home, an mcp entry to the address the instruction supplies, a service to the credential the instruction names, fetched from the owner's store and placed in the agent's environment, and refuse a request that contains a credential value before the value is used; set each required ceiling to the number the instruction gives, and stop when a spending system has none; translate the skills, views, and instructions into the form the target harness reads; mint the subject and bind the draft into the bound Descriptor by adding subject and the operator's signature, placed where the agent serves it; start the agent and check it with the grade stated, smoke or conformance; produce the deployment record (8.3) with the package digest, the bound Descriptor's digest, the credentials placed by name, the ceilings set, and the checks.
Update installs a new version under the same subject: agent_version MUST increase and the subject MUST NOT change; the old version's files are retained until the check passes, and a failed check restores them; the record names both package digests and both Descriptor digests. Rollback is an update to the previous version.
Remove lists what was removed and what remains, under remaining, which is empty only when the removal was complete; placed credentials are removed and named. The subject's Descriptor history at the registry is not removed (6.7).
The ledger. An installer MUST record every file it placed and each file's digest, in the deployment record or in a ledger it names, and answer "what is deployed" by rehashing those files and reporting every difference, so a hand edit to a running agent's instructions is detectable rather than invisible.
8 Provenance
Three records join by digest. The build record names the package digest, the draft Descriptor's digest, each lockfile's digest, and the checks the builder ran with their grade, unrun or acceptance, with draft always true. The deployment record names the package digest, the bound Descriptor's digest, the subject, the credentials placed by name, the ceilings, and the graded checks. The evaluation record (8.4) names the bound Descriptor's digest and the verdict.
A verifier fetches the package by the deployment record's digest and confirms the bytes hash to it; confirms the build record names the same digest and its signature verifies against the builder's key; fetches the draft from the package and the bound Descriptor from the agent and confirms they differ only by subject and signatures; confirms the bound Descriptor's signature verifies against the subject's key; and confirms the evaluation record names that digest. A verifier that completes all five knows what is running and who vouched for each step. It does not know that the work is good, which no document about an agent can say. The evaluation record is optional. A verifier without one knows what is running and who vouched for the build and the deploy, and nothing about whether the work is done; an AgentDoc prints that nothing has been evaluated rather than hiding it. An agent a person attends is not evaluated by probing, because the person would be answering; the deploy's own graded check is the check it carries.
9 What stays out of a package
The agent's identity, handle, admission list, and attendance, which are the owner's decisions at install. Price and handling terms, which attach at listing, and which the Descriptor points at rather than holds. Evidence: the three records are about a package and never inside one. The runtime: a package declares what a host must have and never carries the harness that runs it.
10 Conformance
A checker verifies a package mechanically: the layout of §2; the manifest validates against the pinned schema; the draft Descriptor conforms to Section 6 and carries no subject; the install file has its five sections with no values, addresses, or paths outside the package; one skill per offering and one offering per skill; the system roles in the Descriptor and the install file are the same set; every mcp.json server is a role with no address; the generated views match a fresh generation byte for byte; the manifest's digests match the files; and no text file carries a hidden character. A depot conforms when it refuses a publish without a matching build record, serves immutable versions by digest, marks rather than deletes on withdraw, indexes the two authored files, and scans for hidden characters. An installer conforms when it follows §7 in order, stops on a missing runtime, binary, credential, or ceiling, executes nothing from the package, produces a bound Descriptor that differs from the draft only by subject and signatures, keeps the ledger, and states the grade of its check.
v0.1.0 of this chapter (2026-09-05, Common Agent 0.5.0-draft): first published text, condensed from a working draft that was walked against an interactive-explainer agent as its first package and against the Agent Package Manager tool as the reference for skill layout, ledgers, and content scanning.