Portable trust receipts for agent workflows. Signed, chained, verifiable.
翻譯準備中
取自儲存庫 README
正在載入完整 README。 以下為已儲存的摘錄。
Verifiable work history for AI agents.
Treeship is an open-source trust layer that records agent actions as signed artifacts,
binds them to per-agent keys and capability cards, and lets each verifier apply its
own trust policy, offline. Local capture works without any server; publishing is a
separate, explicit step. The receipts are yours, not ours.檢視完整 README ↗Verifiable work history for AI agents.
Treeship is an open-source trust layer that records agent actions as signed artifacts, binds them to per-agent keys and capability cards, and lets each verifier apply its own trust policy, offline. Local capture works without any server; publishing is a separate, explicit step. The receipts are yours, not ours.
AI agents are doing real work — deploying code, processing transactions, making decisions. When someone asks "what did the agent actually do, and was it allowed to?", the answer is usually a chat log. Chat logs are editable, screenshottable, deniable. They're a story, not evidence.
Treeship produces evidence: every captured action becomes a signed, timestamped, portable artifact that anyone can verify against their own trust roots — without trusting Treeship's servers and without a network connection. What Treeship can and cannot prove is spelled out below; we'd rather you know the boundary than assume one.
No account, no server — and after the install, no network. Every output block below is real CLI output, captured against a real release; exact artifact ids and digests will differ on yours.
npm install -g treeship
treeship init
Wrap any command to get a signed artifact:
treeship wrap --action test.run -- npm test
+ receipt sealed
----------------------------------------
id: art_6df021803b626b1c2e0face3b53b7208
command: npm test
exit: 0 passed
elapsed: 398ms
output: sha256:183d9040996 (ok)
files: none detected
chain: root
signed: key_0ea751c13673b32c (ed25519)
Verify it offline:
treeship verify last
✓ verified (1 artifact . chain intact)
target: art_6df021803b626b1c
actor: ship://ship_7256c8d04a2e6ec3
actor proof: asserted
action: test.run
time: 2026-07-16T17:20:01Z
Note the honest verdict: actor proof: asserted. A wrapped command proves a specific key signed this record at this point in a hash chain — it does not yet prove which agent was behind the key. That's what identity onboarding adds.
Give an agent its own key and a signed capability card in one command:
treeship onboard deployer --tools 'deploy.*,git.push'
✓ agent certificate created
agent: deployer
valid: 365 days (until 2027-07-16T17:15:58Z)
agent key: key_97fe3be93ca7e2b7 (pinned under AgentCert)
✓ capability card attested
agent: agent://deployer
key-bound: yes (AgentCert)
tools: deploy.*, git.push
[4/4] trust bundle — hand these to a counterparty:
# trust this ship to certify its agents (the CA pin):
treeship trust add key_3f0c1d94ab77e215 ed25519:7iSghpSYV9Rfu1RCNXqk0m1x8dJ2rWvLbQ4T6yZaEo0 --kind cert_issuer --yes
# narrower alternative — trust ONLY agent://deployer, not everything this
# ship certifies. Needs a fresh pin per agent and breaks on rotation:
treeship trust add key_97fe3be93ca7e2b7 ed25519:K8V6D33O1k2LsQY5y9i2WTigc2CoYvIwdT_-yGgDbPQ --kind agent_cert --agent agent://deployer --yes
From then on, that agent's actions verify as proven, not asserted:
✓ verified (1 artifact . chain intact)
actor: agent://deployer
actor proof: proven (key-bound)
action: deploy.production
And the agent can hand any counterparty a presentation — card, certificate chain, revocations — that verifies fully offline, revealing only the capabilities that verifier needs (selective disclosure):
treeship present agent://deployer --disclose 'deploy.*' --out deployer.presentation.json
# counterparty runs, against THEIR pinned trust roots:
treeship verify-presentation deployer.presentation.json
✓ presentation
agent: agent://deployer
signature: verified (trusted key)
key-bound: yes (AgentCert)
reveals: selective — revealed 1 of 2 capabilities: [deploy.*]
status: verified (key-bound; staple unverified)
A static presentation proves the record, not the bearer; add --challenge <nonce> on both sides to prove live key control. Beyond this: treeship history (an agent's re-verified work log), treeship profile (a checkpoint-pinned track record where every number recomputes or is a provable lie), treeship resolve / publish / audit (network discovery with client-side verdicts), and treeship match (find agents by exercised, verified evidence).
Approvals are scoped and single-use by default; the nonce binds the human's approval to the specific action it authorized:
# --expires takes any ISO 8601 timestamp; it must be in the future at attest time
approval=$(treeship attest approval \
--approver human://alice \
--description "deploy v2.1" \
--allowed-actor agent://deployer \
--allowed-action deploy.production \
--max-uses 1 \
--expires 2027-01-01T00:00:00Z \
--format json | jq -r .nonce)
treeship attest action \
--actor agent://deployer \
--action deploy.production \
--approval-nonce "$approval"
treeship verify last
# → ✓ verified approved: human://alice
An unscoped bearer approval requires saying so explicitly (--unscoped). Replay of a consumed approval is rejected.
Nothing above touched a network. Publishing is its own decision:
treeship hub attach # one-time device-flow login (required before push)
treeship hub push last # → public artifact page
treeship session report # → shareable session report URL
Two honesty notes:
treeship verify <artifact-id>.TREESHIP_AUTO_PUBLISH=1. Without it the session is sealed locally and nothing leaves the machine, whether or not a hub is attached. Publish when you choose to with treeship session report.To put the receipt in the pull request instead of on a hub, close with treeship session close --receipt-dir receipts, paste the printed Treeship-Receipt: trailer on the commit, and run the verify-receipts action on pull requests: it verifies every committed package under keys the repository pins and fails on anything but verified. This repository runs it on itself. Guide: Receipts in pull requests.
Treeship sends no telemetry. Nothing phones home: not on install, not on first run, not weekly. Adoption is measured from signals the project already owns (hub activity, repository traffic, release and registry downloads) by scripts/adoption-report.py, each number printed with what it counts and what inflates it.
The Hub stores write-once bytes -- not immutable, since the publisher can withdraw a receipt -- serves lookup indices and proofs, and enforces write auth (DPoP) — it never supplies trust verdicts. Server-side verification was deliberately retired (the endpoint returns 410 Gone): a verifier you don't run yourself is not a verifier.
Each verification surface proves:
What it cannot prove alone:
actor proof: asserted vs proven (key-bound) — the CLI always tells you which)..treeship package, only the artifacts and the Merkle root are cryptographically bound; the timeline/side-effects/narrative come from the unsigned event log, and treeship package verify says so explicitly. The authenticated record of a session is the actor-signed session.v1 record.Privacy is likewise scoped, not absolute: wrapped commands store SHA-256 digests of outputs, but the signed artifact also records the (sanitized) command line, exit code, the last output line as a summary, and modified file paths. Don't wrap commands whose names are secret. The full field-by-field capture inventory is in TREESHIP.md.
Treeship doesn't decide trust globally. Each verifier decides, using pinned trust roots and local policy:
agent_cert, cert_issuer, hub_checkpoint, hub_org, revoker, session_host. You pin exactly which keys may vouch for what.present --challenge / verify-presentation --challenge is a direct, offline handshake between two parties.Agent / human action
│
▼
Treeship core (Rust)
│
├─ Serialize statement (compact JSON, deterministic field order)
├─ Sign DSSE PAE bytes with Ed25519 (per-agent or ship key)
├─ Link to parent artifact (hash chain)
└─ Append to Merkle log (inclusion + consistency proofs, signed checkpoints)
│
▼
Local store (.treeship/)
│
├─ Session packages (.treeship bundles) + signed session.v1 records
├─ Cards / certificates / revocations / presentations
├─ Verifiers: CLI (full), WASM (structural receipt + certificate/capability)
└─ Optional: hub publish, transparency anchoring, resolver
There is no single universal "verify" — different surfaces check different things, and each reports its own scope honestly:
| Surface | What it checks | Trust input |
|---|---|---|
treeship verify <artifact-id> | Signatures + parent chain + approval binding | Local keys + pinned roots |
treeship verify <URL or package> | Structure only → verdict is structural-pass, never pass | None (no issuer trust) |
treeship package verify | Artifact + Merkle integrity; warns that narrative is unsigned | Local keys + pinned roots |
treeship verify-presentation | Card + cert chain + revocations + staple, fully offline | Your pinned roots |
treeship verify-capability | Card/action signatures + scope cross-check | Your pinned roots |
treeship verify-profile | Envelope signature + field-by-field recomputation | Local keys + pinned roots |
@treeship/verify (WASM) | Receipt structure, certificates, capabilities, cross-verify | trustRoots you pass (fails closed) |
# One-liner: installs the CLI, runs treeship init, then asks before
# instrumenting detected agents (Claude Code, Codex, Kimi Code, Cursor,
# Hermes, OpenClaw). No tty: skipped unless TREESHIP_SETUP_YES=1.
curl -fsSL https://www.treeship.dev/setup | sh
# Or via npm (inspectable, signed package, no shell pipe)
npm install -g treeship
macOS arm64/x64, Linux x86_64 and Linux ARM64 (any distro, glibc or musl, single statically linked binary) are supported. Windows: use WSL. Full matrix: install guide.
claude plugin marketplace add zerkerlabs/treeship
claude plugin install treeship@treeship
Every Claude Code session in a .treeship/-initialized project auto-records to a signed session package via SessionStart / PostToolUse / SessionEnd hooks. Disclosure: the SessionEnd hook publishes the session report only when TREESHIP_AUTO_PUBLISH=1 is set; by default the receipt stays on your machine (see Share it). Design: integrations/claude-code-plugin/.
| Path | Description |
|---|---|
integrations/claude-code/ | Manual Claude Code wiring (no plugin) |
integrations/cursor/ | Cursor MCP wiring |
integrations/hermes/ | Hermes skill |
integrations/openclaw/ | OpenClaw skill |
Codex and Kimi Code are detected and instrumented by treeship add / the setup script (see integrations/agents.json).
| Package | Registry | Path | Description |
|---|---|---|---|
treeship | npm | npm/treeship/ | CLI wrapper — auto-installs the right platform binary |
@treeship/sdk | npm | packages/sdk-ts/ | TypeScript SDK: CLI-backed signing + in-process WASM receipt/certificate verification |
@treeship/verify | npm | packages/verify-js/ | Zero-dependency verification (WASM + fetch), runs on Node / Deno / browser / edge |
@treeship/core-wasm | npm | packages/core-wasm/ | Rust core compiled to WebAssembly (~190 KB gzipped) |
@treeship/mcp | npm | bridges/mcp/ | MCP bridge — signed receipts for any MCP-speaking agent |
@treeship/a2a | npm | bridges/a2a/ | A2A bridge — attest and verify agent-to-agent task receipts |
treeship-sdk | PyPI | packages/sdk-python/ | Python SDK (wraps the CLI) |
treeship-core | crates.io | packages/core/ | Receipt engine, signing, Merkle tree, verification |
The CLI is distributed via npm + GitHub Releases, not crates.io. The reference Hub server (Go) lives at packages/hub/; the hosted instance serves the Hub API at api.treeship.dev (API only — no browsable root page). Self-hosting is supported.
Both SDKs shell out to the treeship binary for signing — install the CLI and run treeship init first.
@treeship/sdk)import { ship } from "@treeship/sdk";
const s = ship();
// Sign an action — returns { artifactId }
const { artifactId } = await s.attest.action({
actor: "agent://researcher",
action: "tool.call",
meta: { tool: "search.web", query_digest: "sha256:..." },
});
// Verify the local artifact chain — { outcome: 'pass' | 'fail' | 'error', chain, target }
const result = await s.verify.verify(artifactId);
// Optional: publish (requires a prior `treeship hub attach`)
const { hubUrl } = await s.hub.push(artifactId);
For verification without a CLI (browsers, edge), use @treeship/verify — remembering that URL-fetched receipts earn structural-pass, and certificate checks require the trustRoots you pin.
treeship-sdk)from treeship_sdk import Treeship
ts = Treeship()
result = ts.attest_action(
actor="agent://deployer",
action="deploy.production",
meta={"commit": "abc123", "env": "prod"},
)
verified = ts.verify(result.artifact_id)
print(f"Outcome: {verified.outcome}, chain: {verified.chain} artifacts")
Treeship builds on existing primitives rather than inventing cryptography:
The current release is the latest tag on GitHub Releases. The CHANGELOG.md is the source of truth for what each release shipped; the living roadmap is docs/specs/vision.md.
Shipped
session.v1 work records; portable receipt export + independent reference verifier (v0.16, v0.19.1)package verify, v0.31.2+), with the close record bound into the package (v0.31.4)Experimental, explicitly non-authoritative
Open
Treeship has had six advisories in five months. Most share a root cause: a surface reported a green verdict, or signed an action, without the check the product's own rules required.
package verify never checked an artifact's Ed25519 signature, so a rewritten sealed set verified green. TS-2026-002, with a repro script. Fixed the same day; follow-ups in 0.31.3 and 0.31.4 bound the close record into the package.treeship init and other commands wrote through symlinks. TS-2026-004, GHSA-p367-33qm-pwv7.What is true now: every verdict-printing path verifies signatures against the verifier's own pinned roots, and the vocabulary a verdict may use is gated in CI. The release workflow smoke-tests the built binary, on every supported distro, before the GitHub release is created or any package is published; a separate post-publish job then re-installs the published npm and PyPI packages and re-verifies them. What is not yet true: an independent third-party audit of the verify paths. It is on the open list above. Every audit so far was internal and AI-assisted; read the advisories with that in mind. The threat model states what the verifier can and cannot conclude.
TREESHIP.mdCHANGELOG.mdSee CONTRIBUTING.md. All contributions welcome — code, docs, bug reports, security reviews. Security policy: SECURITY.md.
Apache License 2.0. See LICENSE.
Copyright 2025–2026 Zerker Labs, Inc.