Skip to content

Rework the explorer for AAuth -11 and R3 -02 - #5

Merged
christian-posta merged 2 commits into
mainfrom
aauth-11/wp18-explorer
Aug 17, 2026
Merged

Rework the explorer for AAuth -11 and R3 -02#5
christian-posta merged 2 commits into
mainfrom
aauth-11/wp18-explorer

Conversation

@dickhardt

Copy link
Copy Markdown

Generated from the AAuth protocol -11 / R3 -02 migration. The explorer's last commit was 2026-05-28, so it was already behind before -11 landed; twelve of the twenty-seven scenarios depicted mechanisms that no longer exist.

Please push back on any scenario framing that does not match how you teach the protocol. I optimised each scenario for "what does this one thing show", and several of those calls are judgement rather than spec.

What changed in the protocol

Seven changes drove everything here. If you have not read the -11 diff:

  1. The person token is new. aa-person+jwt, issued by the PS from a new REQUIRED person_token_endpoint, audience-restricted to one resource, carrying a directed sub and no authorization at all. The agent presents it via Signature-Key in place of its agent token. A resource MUST have verified one before it issues a resource token — which is why it now appears in every flow that reaches one.
  2. AAuth-Mission was removed, header and IANA registration both. A mission reaches a resource only inside a PS-issued token, as the mission_s256 claim. It is no longer agent-asserted.
  3. act and the delegation chain were removed. Chain routing uses the auth token's ps claim. The PS holds the chain because it authorizes every hop; no token a resource reads shows it.
  4. No token a resource reads carries an agent identifier. Resource tokens carry ps, sub, person_token_jti; auth tokens carry ps and a REQUIRED directed sub. agent_jkt and cnf are the binding.
  5. The mission surface was rewritten. POST {mission_endpoint} proposes; POST {mission_endpoint}/{mission_s256} with action: update or action: completion. Completion moved off the interaction endpoint. The approval response is {s256, mission, capabilities, person_tokens} — the blob base64url-encoded so the digest covers unambiguous bytes.
  6. Five access modes, not four: agent identity, resource-managed, person identity, PS authorization, federated authorization. aauth-access-token became session-token.
  7. R3 -02: r3_conditionalr3_per_call, the version field removed, per-call proposals are now full R3 documents carrying a parameters object, and the openapi-gateway vocabulary is gone (it was not in the site).

New scenario: Person Identity Access

/access/person-identity — the centre of the protocol now, and the one thing the site had no representation of at all. Four steps:

  1. Agent signs with its agent token → 401 AAuth-Requirement: requirement=person-token (also new in -11).
  2. POST {person_token_endpoint} with {resource}aa-person+jwt with aud = the one resource, a directed sub, cnf.jwk = the agent's key, no scope, no account.
  3. The agent presents it via Signature-Key in place of its agent token and is served on identity alone. No resource token, no auth token, the PS not in the path of the call.
  4. A write endpoint needs more than identity, so the resource challenges there with requirement=auth-token — and the resource token it issues copies ps, sub and person_token_jti straight out of the person token it just verified.

Step 4 is the point I most want you to check. I used it to show the person-token → resource-token copy (interop profile Surface 2) and the "most calls on identity, a few sensitive operations challenging for more" shape, rather than ending the scenario at step 3. It makes the scenario do two jobs.

Scenarios changed

Access modes

  • ps-asserted → retitled PS Authorization Access. Rebuilt on the authorization-endpoint path from the spec's own figure: person token, POST /authorize with it, resource token aud=PS, auth_token_endpoint, present. Both variants.
  • federated → retitled Federated Authorization Access. Same two steps prepended, aud=AS, annotations on why agent_token stays REQUIRED at the AS and why only the PS can redeem a resource token.
  • identity-based → retitled Agent Identity Access, description mentions requirement=agent-token.
  • resource-managed → "opaque token" is now the session token throughout, with the access_mode=session-token value and the rolling-refresh behaviour called out.
  • access/compare → five modes, each carrying the spec's "resource knows / established by" pair.

Missions (all eight)

  • missions-lifecycle → proposal carries resources; approval returns {s256, mission, capabilities, person_tokens}; annotations explain that capabilities is not in the blob and not covered by the digest. PS metadata shows person_token_endpoint, auth_token_endpoint, mission_control_endpoint.
  • missions-resource-access → retitled Mission Context at a Resource. Rebuilt around mission_s256 flowing person token → resource token → auth token, with an s256 chain visual.
  • missions-out-of-bounds → person token naming M1 added; new-mission approval uses the new response shape; annotation notes that action: update is the right tool when the description still describes the work.
  • missions-completion → retitled Mission Update & Completion. New first step showing action: update and the returned update digest; completion moved from POST /interaction {type: completion} to POST /mission/{s256} {action: completion}; termination reasons added.
  • missions-auditmission object → mission_s256; the terminated case returns application/problem+json with termination_reason.
  • missions-permission → mission variant names mission_s256; annotations tie decisions to approved_tools and the mission log.
  • missions-end-to-end → person token comes back attached to the approval, so no extra request; s256 chain added.
  • missions/compare → the whole token diff rebuilt: no header, no act, no agent, person token column added, lifecycle list rewritten to include update and completion.

Mission digests are now real. s256 is the actual SHA-256 of the blob bytes, and mission is those bytes base64url-encoded. You can decode and verify them from the page, which is what the interop profile asks a Surface 1 implementer to do.

Advanced

  • call-chaining → R1 now acts as an agent with its own agent token (it was signing sig=jwks_uri as a resource). It obtains a person token for R2 with upstream_token, then routes the token request to the PS named by the upstream token's ps claim, with an annotation on why its own ps claim is not used. act annotations replaced with why the chain is absent from the token and present at the PS. Directed-sub-across-a-chain explained.
  • interaction-chaining → same person-token step; the downstream token request now goes to the PS rather than straight to AS2 (the -11 change removed that branch).
  • clarification → was showing the agent POSTing directly to the AS token endpoint, which was never right. Retargeted to the PS. Added the action: clarification_response discriminator, which the scenario was missing.

R3

  • r3-conditional-opsr3-per-call-ops, route /r3/conditional-ops/r3/per-call-ops. The bespoke call_params claim in the resource token and call_binding in the auth token are gone; the resource now builds a per-call proposal (a full R3 document with parameters, including a digest-object parameter for a large value) and the token carries only r3_uri/r3_s256. The challenge is a proper 401 + AAuth-Requirement rather than an invented conditional_operation error.
  • r3-vocabulary-basics, r3-content-addressing → person token presented at the authorization endpoint; version removed from the documents; r3_s256 values are now the real SHA-256 of the document bytes shown; token_type: DPoP and Authorization: DPoP … replaced with expires_in and Signature-Key.

Components

  • HeaderInspectorAAuth-Mission removed from tooltips and the AAuth-header set; AAuth-Access and Authorization descriptions rewritten around the session token.
  • JWTVieweract and mission tooltips gone; mission_s256, person_token_jti, tenant, account, parent_agent added; sub and ps rewritten; r3_conditionalr3_per_call.
  • MissionBlobViewer — separates blob members (where approver still lives) from the identifier, and shows the base64url mission member next to its digest.
  • R3DocumentViewerversion badge replaced with a per-call-proposal badge; renders parameters and display.detail.
  • lib/types.tsMissionBlobData gains expires_at, approved_resources, encoded; R3Document loses version, gains parameters; R3Display gains detail.

Housekeeping: every token's raw is regenerated from its header and payload, so the raw tab decodes to what the decoded tab shows. It did not before — several raws still decoded to 127.0.0.1:800x values and to claims that had been edited away.

Removed

lib/scenarios/user-delegation.json and /access/user-delegation. Its steps are the federated scenario's "With User Approval" variant; what it added on top was wrong under -11 (the agent signing sig=jwks_uri, and AAuth-Access sent as a request header carrying the auth token). Rather than rebuild a duplicate I dropped it and removed the sidebar entry. Say the word and I will restore it — it is one file.

Things I was unsure about

  • Whether to add a step or an annotation. Every access-mode scenario grew by two steps for the person token. It is protocol-accurate but it also means the first two steps of four scenarios are near-identical. The alternative was to annotate "the agent already holds a person token, see Person Identity Access" and keep the flows short. I chose accuracy; you may prefer the shorter flows for teaching.
  • ps-asserted and federated now use the authorization endpoint rather than the 401 challenge those scenarios used before. It matches the figures in the spec and makes the person-token requirement natural, but it does change what those two pages teach. The 401 path is mentioned in an annotation on each.
  • Endpoint URL https://ps.example/auth-token. The rename in -11 is of the metadata field (token_endpointauth_token_endpoint), not the path; the spec's own examples still use POST /token. I renamed the path too so it reads next to /person. Easy to revert if you would rather the URLs match the spec examples.
  • delegation.json was on my list as act-chain-based but is not — it is the sig=jwt agent-token scenario and has no act. Left alone apart from the mechanical claim-ordering pass.
  • missions-permission's autonomous variant is the no-mission case and stays that way; only the interactive variant names mission_s256.
  • r3_s256 and mission s256 are real digests now but the JWT signature_b64 values are still decorative. Making signatures real would mean shipping keys, which seems like a different decision.

Left alone deliberately (pre-existing, not -11)

  • alg: "EdDSA" in every JWT header. -10 adopted the fully-specified Ed25519 of RFC 9864 and says implementations MUST NOT accept the polymorphic EdDSA. Every token in the site would need Ed25519, and every cnf JWK needs an alg member. Mechanical, but it is a -10 change and I did not want it inside a -11 review.
  • ;alg="ed25519" as an HTTP signature parameter. -10 says the alg signature parameter MUST NOT be used. It appears in every Signature-Input and signature base on the site. Same reasoning.
  • The interaction_endpoint scenarios' AAuth-Capabilities annotations still cite section numbers from an older draft (§1731 and friends). The claims are right; the numbers are stale everywhere in the repo and I did not renumber them.
  • The bootstrap scenarios — -11 did not touch bootstrapping. They took only the claim-ordering and raw regeneration pass.

The site was last touched 2026-05-28 and showed several mechanisms the
protocol no longer has: the AAuth-Mission header, the act delegation
chain, agent identifiers in resource and auth tokens, the old mission
endpoint shape, four access modes, and r3_conditional.

Protocol changes reflected:

- Person token (aa-person+jwt). New scenario at /access/person-identity
  covering issuance at the person_token_endpoint and presentation via
  Signature-Key. Every flow that reaches a resource token now obtains
  and presents one first, because a resource MUST have verified one
  before it issues a resource token.
- AAuth-Mission removed. A mission reaches a resource only as the
  mission_s256 claim of a PS-issued token. Header dropped from the
  inspector, the tooltips, the scenarios and the comparison page.
- act and the delegation chain removed. Chain routing uses the auth
  token's ps claim; the PS holds the chain because it authorizes each
  hop. Call chaining and interaction chaining rebuilt around that, with
  the intermediary obtaining a person token for the downstream resource.
- No agent identifier in any token a resource reads. Resource tokens
  carry ps, sub, person_token_jti; auth tokens carry ps and a required
  directed sub. agent_jkt and cnf are the binding.
- Mission surface rewritten: proposals at the mission endpoint,
  action: update and action: completion at the mission's own URL, and
  the {s256, mission, capabilities, person_tokens} approval response.
  Mission digests are now computed from the blob bytes, so they verify.
- Five access modes on the comparison page; session-token naming for
  the credential a resource issues in resource-managed access.
- R3 -02: r3_conditional renamed r3_per_call, the version field removed,
  and per-call proposals rebuilt as full R3 documents with a parameters
  object. /r3/conditional-ops moved to /r3/per-call-ops.

Removed lib/scenarios/user-delegation.json and /access/user-delegation:
its content is the federated scenario's "With User Approval" variant,
and what it added on top contradicted -11.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01FmiCqDjRUSx6zb1N4gZPXE
…r-local

Signed-off-by: Christian Posta <christian.posta@gmail.com>
@cloudflare-workers-and-pages

cloudflare-workers-and-pages Bot commented Aug 17, 2026

Copy link
Copy Markdown

Deploying explorer with  Cloudflare Pages  Cloudflare Pages

Latest commit: f2652da
Status: ✅  Deploy successful!
Preview URL: https://3a18c59f.explorer-292.pages.dev
Branch Preview URL: https://aauth-11-wp18-explorer.explorer-292.pages.dev

View logs

@christian-posta
christian-posta merged commit 6e200eb into main Aug 17, 2026
1 check passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants