| Filename | Latest commit message | Latest commit date |
|---|---|---|
Add a coherent set of long-running-agent capabilities, each as a spec section + reference implementation + conformance class, every one metered, attested, and receipt-chained. Sandbox: - §13 Durable run records (C6): the receipt chain IS the resumable run; execute/suspend/resume segments hash-chained; idle energy metered across parks. (sandbox-attest::runrecord) - §14 Environment manifest (C7): devcontainer.json declarative-subset ingestion -> canonical, content-addressed, signed manifest; command/widening and unknown fields refused. (sandbox-attest::manifest) - §5.5 Content-addressed process control (C8): exec allow/deny by BLAKE3 of the binary; denylist absolute, survives rename/move/wrapper. - §15 Warm pools (C9): a claim attributes accrued idle energy to the run (a fast start has a visible joule price); evictions record overhead, not zero. (sandbox-attest::warmpool) - §16 Fleet records (C10): merkle aggregate receipt over per-item runs; log-size membership proofs. (sandbox-attest::fleet) - durable.json cross-impl wire vectors + file-backed verify. JCP: - §4.6 Standing grants (C20): a signed mint policy turns a held grant into bounded, rate-limited, event-triggered children via the attenuation path. (jcp-grant::standing) - §4.7 Checkpoints + amendments (C21): mid-run steering under separation of duties — the agent checkpoints its own state, only the issuer (a distinct principal) may amend, and only to tighten. (jcp-grant::checkpoint) - standing.json cross-impl vectors. Both workspaces green; conformance harnesses pass with no skips; clippy clean. Co-Authored-By: Claude Opus 4.8 <[email protected]> |
||
| .. | ||
| conformance/v1 | ||
| jcp-rs | ||
| CONTRIBUTING.md | ||
| LICENSE | ||
| LICENSE-SPEC | ||
| README.md | ||
| SPEC.md | ||
JCP — The Joule Context Protocol
A unified, energy-native, capability-secured protocol for agentic systems. Where today's stack splits across MCP (tools), A2A/ACP (agent-to-agent), an identity layer, and an authorization layer — and standardizes energy nowhere — JCP is one spec, built on one idea:
A capability and an energy budget are the same object: a signed, bounded, debited grant. A capability you can't pay for is denied; an expenditure you're not capable of is denied. One check, made outside the model, sealed in a receipt.
The design answers the documented failure modes of the current agentic ecosystem, not hypotheticals. Tool descriptions are untrusted input → JCP refuses to take control from a tool's output. Prompts can't enforce access control (and a more capable model only follows injected instructions better) → JCP decides every action in the runtime, never in the LLM. Agent loops have no cost ceiling → every grant carries a joule budget that's debited and enforced before the side effect. Audit is a mutable telemetry span → JCP seals every decision, allow and deny, as a non-repudiable signed receipt.
- Licence: Apache-2.0 for reference code (see
LICENSE); CC-BY-4.0 for specification text (seeLICENSE-SPEC). - Status: v0.3.0 draft. Specification core published (
SPEC.md+conformance/v1/); reference workspacejcp-rs/.
What's here
jcp/
├── SPEC.md — the normative standard (§1–§12)
├── conformance/v1/ — published vectors (a signed grant + allow/deny receipts)
└── jcp-rs/ — the Apache-2.0 reference implementation
The reference implementation (jcp-rs/)
jcp-schema— the wire objects: thedid:keyactor, the Grant (the metered capability — capability ⊗ joule budget, content-addressed and signed), the Frame (every message, with itscontrol/datatrust tag), the familyEnergy/Provenancemodel, canonical det-CBOR content addressing.jcp-grant— issuance, signature verification, attenuation (object-capability delegation where a child grant can only narrow — capability ⊆, budget ≤, expiry no later, delegation depth − 1), chain verification (root-first, hop-by-hop: parent links, holder-issued hops, narrowing, signatures, depth bounds), revocation (issuer-only, signed, admitted into aRevocationSetonly after authority checks), sharding (shard()splits a grant into siblings whose budgets must sum within the parent — distributed enforcement with no consensus, SPEC §4.5), and identity continuity (KeyLog: KERI-style pre-committed rotation, SPEC §2.1 — a thief with the current key can't rotate, an owner who lost it still can).jcp-runtime— the deterministic enforcer. One ordered check fuses authorization and energy, decided outside any model: untrusted-control, revocation, configured trust roots (an enforcement point honors only the root-issuer keys it was configured with —authorized_keysshape, no CA), audience binding, signature, expiry, capability, and budget — then debit. The first failure names the reason.decide_chainedenforces full delegation chains: a revoked ancestor kills the subtree, and the cost must fit — and is debited from — every link, so sibling delegations share their root's budget and delegation can never mint joules.jcp-receipt— thejcp/1JCR-1 receipt: canonical det-CBOR + COSE_Sign1/EdDSA, byte-compatible with the family verifiers. Allow and deny both seal. The receipt stream is the write-ahead log (SPEC §8.1): a chained receipt recordschain_ids— every link the decision debited — soreplay_spendrebuilds an enforcement point's budget state, ancestors included, from its own verified output with no external index;aggregatekeys a team's receipts by(grant, subject)for per-worker cost attribution computed from evidence (SPEC §8.2).jcp-bridge— a reference gateway that wraps existing MCP tool calls and A2A tasks in Grants and Frames without rewriting the endpoint. It maps each outbound call to a Frame (the tool/method is the action; the(server, tool)identity is the content-addressed resource), decides it against the caller's grant before the call reaches the endpoint, and seals a receipt — so an existing server keeps its transport while every call becomes capability-scoped, joule-budgeted, decided outside the model, and sealed. Inbound results are framed as untrusteddata.jcp-energy— the metering ladder (SPEC §5.1): RAPL package counters (Linux powercap, wraparound-corrected,HwShunt), NVML GPU energy behind thenvmlfeature (HwShunt), a time×calibrated-power model (ModelBased, always available), and a constant per-op estimator (Estimator). Measured when the platform exposes it, estimated when it doesn't — and the provenance always says which; a hardware backend that fails mid-reading degrades honestly to the model.jcp-gateway— the energy-native MCP gateway: a JCP enforcement point that sits in front of an MCP server so an existing client/server pair keeps its transport while everytools/callbecomes capability-scoped, joule-budgeted, and sealed. The novel mechanic is two-phase metered enforcement: the call is authorized before it runs (no debit, because the cost isn't yet known), the upstream call is metered on real hardware (the sibling Sandbox standard's energy probe — Apple Silicon IOReport, RAPL, NVML), and the measured joules are debited from the grant — so the budget that stops a runaway agent is denominated in energy actually spent, not a token estimate. Every decision, allow and deny, seals into a hash-chained receipt log: excise, reorder, or splice a receipt and the chain breaks at that point. A denied call never reaches the server (the live 2025–26 MCP exploits land on tool output, which the gateway frames as untrusteddatathat can never exercise a capability), and thejcp-gatewaybinary runs it over stdio in front of any MCP-server subprocess. This is the chokepoint the AI-gateway field occupies, on the two axes nobody there holds: the unit of account is the joule, and the audit is cryptographic and tamper-evident rather than a dollar figure and a span.jcp-wire— thejcp/1wire binding (SPEC §11): 4-byte length prefix + canonical det-CBOR over any byte stream, with TCP and Unix-socket endpoints and a client. The decoder rejects non-canonical bodies, so a message has exactly one wire form. Requests carry the full delegation chain and are caller-signed — the endpoint authenticates from the request itself and denies an impersonationbad-signature, sealed like any other decision. Responses carry the deterministic decision and the sealed receipt.jcp-threshold— threshold actors (SPEC §2.2): adid:keywhose private key is split k-of-n with FROST (RFC 9591); the group key is an ordinary Ed25519 key, so a 2-of-3 team issues, holds, and signs wire requests with nothing else in JCP changing. Shares come from a trusted dealer or distributed key generation — with DKG the group's private key never exists anywhere, not even momentarily. The two-agent rule for irreversible actions, refused by arithmetic rather than policy.jcp-channel— receipt-settled budget channels (SPEC §4.5, the OPTIONAL profile): N enforcement points spend optimistically against one grant and settle by exchanging signed statements of cumulative spend — forged, stale, and regressing statements refused; between settlements the exposure is bounded by the window, and after settlement any overdraft is provable from the signed statements. Where bounded overdraft is unacceptable,shard()remains the baseline.jcp-conformance— C1–C18 + a negative pack, all checks real (C8 decides over a live socket; C13 drives a FROST 2-of-3 caller; C16 replays ancestor debits from a chained receipt; C17 settles a budget channel by signed statement; C18 mints a dealer-free group via DKG), published vectors inconformance/v1/.jcp-cli— thejcpdemo: one metered grant driven through an agent loop — legitimate calls allowed and debited, a poisoned tool-result refused structurally, out-of-scope actions and resources denied, the budget stopping a runaway loop, a sub-agent getting a strictly-weaker delegated grant, a signed receipt verified, the detected energy meter reporting its honest provenance, and the issuer revoking the grant — after which the runtime goes dark.
cargo test --workspace green; cargo clippy --workspace --all-targets
warning-free.
The demo, abbreviated
frame verdict reason rem µJ
read the db (legit) allow −20000 µJ 80000
tool-result says 'delete db' (poison) DENY untrusted-control 80000
try to delete (not granted) DENY action-not-granted 80000
read prod-secrets (wrong audience) DENY wrong-resource 80000
read again — budget runs out DENY budget-exceeded 30000
amplification refused: capability exceeds parent
receipt allow · 50000 µJ · verified true
The model never gates itself; the runtime does, and the receipt proves it.
Consumers in this repository
JCP is not only specified — it is consumed. Three sibling standards gate their real dispatch through it, each with its own adapter crate and tests:
- JouleClaw (
jouleclaw-rs/crates/jouleclaw-jcp) — every MCP tool dispatch is decided against a Grant before a byte reaches the tool; an ungranted tool named by an injected instruction is refused and the refusal sealed. - Sandbox (
sandbox-rs/crates/sandbox-jcp) — a unit's execution is authorized against a Grant bound to its image by content address; one flipped image byte is a different audience and is denied before the executor is ever invoked. Two receipts per run: the JCP authorization and the sandbox's metered, attested execution. - Joule Code (
joule-code-rs/crates/joule-code-jcp) — every cascade-stage consultation is decided pre-dispatch; the L4 escape hatch to a remote frontier agent exists only when a signed grant names it and can pay for it.
Relationship to the family
JCP composes the primitives the Transaction Science family already proved:
did:key/Ed25519 identity, capability-gated execution (sandbox), the honest
Energy/Provenance model (proof), and JCR-1 signed receipts (family-wide).
It is where they stop being per-tool adapters and become the protocol.