Mandates
The optional, polymorphic authorization an agent presents at checkout — veto · ap2 · acp · none. A Veto-governed agent is simply the highest-trust input, never a requirement.
A mandate is what an agent presents at checkout to prove its spend was authorized. It
is optional and polymorphic — type ∈ { veto, ap2, acp, none }. A Veto-governed
agent is the highest-trust input, never a requirement: your policy decides whether a
mandate is needed for a given amount.
interface PresentedMandate {
type: 'veto' | 'ap2' | 'acp' | 'none';
token?: string; // compact JWS for `veto`
raw?: unknown;
}veto — verified and bound
A compact Ed25519 JWS signed by an issuer whose JWKS you trust (matched by kid). The
payload authorizes a specific merchant, amount, and intent:
{
"iss": "veto",
"typ": "veto-mandate+jws",
"sub": "<jti uuid>",
"exp": 1750003600,
"decision": "approve",
"agent_id": "<uuid>",
"authorization": {
"merchant": "<merchantId-or-domain>",
"max_amount": "50.00",
"currency": "USD",
"intent": "<text>"
}
}Valid + bound ⇒ tier premium when all hold:
- signature verifies against a trusted JWKS (
kidmatch) decision === "approve"exp > nowauthorization.max_amount >= cart.totalmerchantmatches yourmerchant.idor.domain→merchantMatch = true
If any binding fails, a specific reason code fires — MANDATE_INVALID_SIGNATURE,
MANDATE_EXPIRED, MANDATE_AMOUNT_INSUFFICIENT,
MANDATE_MERCHANT_MISMATCH, or MANDATE_NOT_APPROVED.
ap2, acp — typed stubs
Accepted on the wire so the protocol is forward-compatible, but today they return
valid:false with MANDATE_TYPE_UNSUPPORTED. A TODO marks exactly
where a real AP2 cart-mandate / ACP token verifier plugs in.
none — no mandate
Legal and first-class, not an error. Trust falls back to reputation alone: standard
if the agent is known, cautious if unknown. Use policy to decide
whether a none request can clear at a given amount.
Replay protection
A mandate's subject (sub/jti) is single-use. The gate reserves it atomically the
moment a mandate verifies valid and has a subject — before capture — so two concurrent
settles of one mandate cannot both succeed. A reused subject is
MANDATE_REPLAY.
Mandates pair with receipts.
The buyer holds a mandate; on accept, the merchant issues a receipt
whose mandateRef points back at the mandate subject. Two signed artifacts pointing at each
other are your non-repudiation evidence.
The acceptance gate
The ordered sequence that runs on every settle — load, idempotency, verify, replay, reputation, policy — all before any money is captured. The order is the chargeback defense.
Trust tiers
How a verified mandate and hosted reputation resolve to a trust tier — premium, trusted, standard, cautious — that your policy gates on.