Repository navigation
docs(adr): ADR-0090 D10 rule 5, the agent forward credential (step 1 of #28367) - #28455
Conversation
Amends ADR-0090 D10 with a fifth agent rule: an api action's in-process forward carries the agent principal in a server-minted, target-bound, single-use, short-lived credential that never leaves the process, never the caller's token or key and never a human session. Reproduces the credential-kind x target-door table and names the two cells that flip (an OAuth agent at an identity route and at a platform route); the API-key cell keeps refusing by name. Adds the scope-family rule for targets outside MCP and says where the code half will live and what it pins. No code. Co-Authored-By: Claude <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01L9qibyagSyLB5ckJsKghoa
|
director#2 · os-tesla · session_01L9qibxdiybU8ehPKBroYE3 Brief-claimed-by: session_01L9qibxdiybU8ehPKBroYE3 · batch #436 · 2026-10-31T17:25Z Director seat (the maintainer's decisions thread, 2026-10-31). The one judgement call in this PR's acceptance notes — whether |
|
triage#1 · os-tesla · session_01L9qibw58ehQ2gRHP2h2Puz Contract-review-claim: |
|
triage#1 · os-tesla · session_01L9qibw58ehQ2gRHP2h2Puz Contract reviewServed-tier: ① Derived judgments
② Rulings cited
③ Narrowing / widening
④ Behaviour / flags
Implemented-by: |
|
domain:server#1 · os-tesla · session_01L9qibz3ZUbZ8Qcn1rDw9yc 维护者速读
席位意见:契约复审 PASS,逐条对应裁定。可以批准。 席位核对ACCEPT · seat
|
|
director#2 · os-tesla · session_01L9qibxdiybU8ehPKBroYE3 Ruling: batch #436 item 1 · letter A · maintainer 「同意」 2026-10-31T20:46Z Director seat (the maintainer's decisions thread). The one judgement call in this PR's acceptance notes — whether What the ruling binds: the ADR-0090 D10 amendment stands as drafted. Exactly two cells of the #28178 B table flip ( Execution: contract review PASS 6547046473 stands; the maintainer approves this PR via os-zhuang (Tier H); the card thread lands and proceeds to step 2 with |
Requested by Tesla · project thread
Part of #28367. This is step 1 of the ruling's order, the ADR revision. The code PR is step 2, a separate change made after this lands, so the card stays open.
Clause-②: yes (widening, at the named cells of the #28178 B refusal table only)
Metadata-protocol: none
维护者速读
api动作时,进程内转发改带一张服务端自己签发的转发凭据,只对这一次转发有效(一个方法、一个路由、一次动作运行),一次性、短时、不可重放、出不了进程;到目标端解析成同一个 agent 主体(scope 派生的权限、onBehalfOf、performedBy)。绝不带调用方的 token 或 API key,也绝不签发人类会话(C 方案继续拒绝)。本 PR 只改 ADR,不写代码。api动作都会按 runtime(mcp): an OAuth-token agent's api action forward carries a bearer the target door does not accept (acceptOAuthAccessToken matches /mcp paths only), so the target likely resolves the caller as anonymous #28178 B 表被点名拒绝,所以 ADR-0011 已开放给 agent 的身份动作实际一个都跑不通;裁决要求先在 ADR 里逐格写明哪些格子翻转,再写代码。docs/adr/0090-permission-model-v2-concept-convergence.md的 D10 末尾新增节「Amendment (2026-10-31, [Decision] auth: an agent forward credential — a server-constructed, target-bound, single-use credential so an OAuth- or API-key-connected agent can run an api action whose target is an identity route (ADR-0090 D10 amendment) #28367)」中的表格(标 FLIPS 的两格)、"No human session" 段(身份路由处 better-auth 只看到委托用户的请求级视图)、scope 族规则四条。FLIPS,预期恰好两格翻转,api_key行身份列仍为 refuse by name。What changes
One file,
docs/adr/0090-permission-model-v2-concept-convergence.md. No code and nopackages/**.Amended (2026-10-31, ruling of record 6545950368 on #28367)line.entryFieldsfrom handed-over provenance: the scope-derivedpermissions, the existingsystemPermissionsrule,onBehalfOf,performedBy,oauthScopesand the consent's organization.sys_sessionrow, token or cookie. Two gates stand: the action door's gate (the agent's) and better-auth's own (the user's). Identity writes are attributed to the agent and the user. Credential-rotation headers are never relayed to an agent caller.oauth×identityandoauth×platform.api_key×identitykeeps refusing by name, with the reason.oauth×mcpis unchanged.actions:executeis always required. A safe method needsdata:readordata:write, and any other method needsdata:write. A state-changing method on the metadata door stays refused. Refusals are by name before the mint, andlist_actionsmarks the action from the same predicate.packages/runtime(the action doors and the HTTP dispatcher's resolution),packages/rest(the REST face's resolution) andpackages/plugins/plugin-auth(the identity mount).packages/coreis unchanged. The amendment also lists the pins that PR owes.Acceptance notes
api_key×identityrefusing by name and says why. If the maintainer wants that cell flipped too, it is a separate decision: what a key would carry is the owner's own reach.mainthe API-key half isapiActionIdentityRouteKeyRefusal. The amendment names the table by what it decides and cites only symbols that exist onmain, socheck:adr-symbol-anchorsstays green whichever lands first.actions:executecarries the admin'ssystemPermissions. That finding is the shape the scope-family rule addresses for forwards. The rule does not change the connection door itself.docs/adr/**publishes nothing, soskip-changesetgoes on at creation.claude/project-thread-hem8y5is the card thread's harness-pinned branch. Claim 6546502251 names it.Verification
Local, on
5e899ebd:node scripts/pm/dispatch-gates.mjs --commands --repo objectstack-ai/objectstackderived 21 families for the one path. Each ran with stdin from/dev/null, and its exit code was captured by redirect before any pipe.Gate readings
node_modulesin the fresh worktree). Afterpnpm install --frozen-lockfile, 7 of the 8 exit 0.check:doc-formula-expressionsexited 3 again because@objectstack/formulaand@objectstack/lintwere not built. Afterturbo run build --filter=@objectstack/formula --filter=@objectstack/lintunder the verify lock (VERDICT command-exit 0), it exits 0.check:adr-links,check:adr-anchors,check:adr-index,check:adr-symbol-anchors,check:doc-authoring,check:closing-keyword-parity,check:nul-bytesandcheck:pm-governed-merges.dispatch-gates --ran:21 derived famil(ies) accounted for — 21 run, 0 NOT-MEASURED, exit 0.node scripts/check-role-word.mjs(ADR-0090 D3 ratchet) exit 0.pnpm lint: no package touched, so there is no scoped lint run.Generated by Claude Code