@agenticprimitives/estate-projection
v0.0.0-alpha.21
Published
An estate's public projection of its authority (spec 410 §4): the live-grant root and the membership root over blinded commitments, anchored on public ground; the authority presentation a verifier in another estate checks against them, learning that a gra
Maintainers
Readme
@agenticprimitives/estate-projection
An estate's public projection of its authority — spec 410 §4.
Grants and relationships are enforced on an estate's own chain and kept in its principals' vaults. A verifier in another estate cannot read either. What the estate publishes is two Merkle roots over blinded commitments: the live-grant root (every grant currently live) and the membership root (every countersigned relationship credential). They are anchored on public ground with a monotonic sequence, signed by the estate's governance.
A holder presents one leaf with its opening and a proof. A verifier in another estate checks it against the roots it reads from the anchor and learns exactly one thing: this subject holds a live grant, or is a member, in that estate as of that sequence. It learns nothing else — not the terms, not the counterparty, not any other leaf.
import { buildProjection, makeAuthorityPresentation, verifyAuthorityPresentation } from '@agenticprimitives/estate-projection';
const projection = buildProjection({ chainId: 34348, governance, sequence: 7, liveGrants, memberships });
// … the estate signs projectionDigest(projection) and anchors the roots on public ground …
const pres = makeAuthorityPresentation(projection, 'membership', credentialDigest, { nonce, audience });
const verdict = verifyAuthorityPresentation(pres, rootsReadFromTheRegistry, { subject, nonce, audience, now, maxAgeSeconds: 3600 });The issuer row
A credential issuer anchors one more root on the same registry: its live-credential set, the credentials it still
stands behind. The leaf is credentialDigestOf(jwt) — keccak over the issuer-signed compact JWT — under a per-leaf
blind; the row id is estateIdOf(chainId, issuerSA) and the row is tagged ISSUER_ROW_TAG, so a verifier tells it
from an estate's. Revoking a credential is retiring its leaf: the next root is anchored without it, and every status
presentation built at an older sequence is stale against the chain. No chain is asked about a credential's liveness;
the issuer's own ledger decides it.
import { buildIssuerProjection, credentialDigestOf, makeCredentialStatusPresentation, verifyCredentialStatusPresentation } from '@agenticprimitives/estate-projection';
const row = buildIssuerProjection({ chainId, issuer, sequence, liveCredentials }); // anchored by the issuer's projector
const status = makeCredentialStatusPresentation(row, credentialDigestOf(jwt), { nonce, audience });
const verdict = verifyCredentialStatusPresentation(status, issuerRootsReadFromTheRegistry, { nonce, audience, now, maxAgeSeconds });A status presentation names no subject. It is linkable to the credential's leaf, which is why a verifier asks for it only where the alternative is phoning a status list.
Evidence, never authority: whether the receiving estate lets the agent act is its own mandate, verified per step. An inclusion proof over the live set, deliberately — a revocation is a removal and a new root.
