You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
checklist: re-point ai.mcp-run-action-exposure-gate acceptance[4] and step 6 — they still pin the wholesale sys_* refusal that rulings on #27681 and #27900 replaced #29892
Filing gate: ① a stale clause, a QA run clause fail (ai.mcp-run-action-exposure-gate acceptance[4]) whose red line needs an owner (checklist-test §5, "过期规格"). It failed the same way in wave 4 (#28942) and was parked on the 18.3.0 anchor #27377, which has since closed with the re-point not made, so it is red again at wave 5.
Business reason: the item is the MCP door's release evidence that an agent cannot run actions it should not reach. While acceptance[4] asserts a refusal the product no longer makes, every sweep reports this P1 item FAIL although the gate holds as ruled, and the one real defect it found (#28943) is buried under a permanent red row.
Reader who acts: the domain:devx lane that owns docs/qa/platform-checklist/areas/ai.json (one item revision, node scripts/check-platform-checklist.mjs green).
Duplicate search (incl. closed): mcp-run-action-exposure-gate re-point → 8 hits; none is a re-point card (wave 4 parked it on #27377 instead of carding).
Disposition: stale spec. Since maintainer ruling 6513869839 on #27681 (letter B) and the ADR-0011 addendum (ruling 6523087116 on #27900, amended by 6540309323), a sys_* action is listed and run over MCP when the action itself declares ai.exposed. Code: systemObjectActionExposureError (packages/runtime/src/action-execution.ts) and isListableAction (packages/mcp/src/mcp-http-tools.ts). Item revision 6 kept acceptance[4] as "system objects are refused wholesale".
Measured at 589049b0 (2 fresh stock boots, MCP Streamable HTTP on /api/v1/mcp)
A non-exposed system action is refused and never executes, in two spellings the clause does not quote: with objectName 'Action "create_api_key" on system object "sys_api_key" is not exposed via MCP: …ai.exposed… list_actions lists it for you'; without it "Action 'create_api_key' is on a system object ('sys_api_key') and is not exposed via MCP — …".
With the admin's session bearer, run_action revoke_api_key (confirm: true) answers ok: true and the key reads revoked: true — exposed and allowed, as ruled.
acceptance[4]: a sys_* action with no ai block is refused in either current spelling with zero side effects, and an ai.exposed system action passes this guard (and meets the next gate);
step 6: name a non-exposed action (create_api_key), since "any sys_* action name" can pick an exposed one;
acceptance[1].verify: "the snapshot is the one exposed action" no longer holds (37 listed on stock, 38 with qa_ai_gated); entries marked unavailable are part of the contract.
A wave-5 finding of the 18.3.0 sweep (「发版本优先的都p1」). The release judgement cannot read the MCP gate until this is re-pointed, so p1. It is one item revision, and check-platform-checklist stays green.
Claim: PM loop round 3
Session: session_017ihL2gLghEqeDKTbDTC7Zd
Account: marchtian
Branch: claude/issue-29892-mcp-exposure-gate-repoint
Worktree: objectstack-issue-29892
Domain: domain:devx
Seat: domain:devx#2
File surface: docs/qa/platform-checklist/areas/ai.json (item ai.mcp-run-action-exposure-gate), plus FOLLOW-UPS.md / coverage.json where the checklist procedure requires
Container & model: M, mode:subagent, model: default tier, effort: high
Clause-②: no
Metadata-protocol: none
Responsibility: acceptance[4] and step 6 still pin the wholesale sys_* refusal that rulings 6513869839 (#27681) and 6523087116 / 6540309323 (#27900) replaced, so this P1 release-evidence item reads FAIL on every sweep
Thread-read: 6601854076
Premise: holds
Serial constraints cleared: no open PR from this seat touches platform-checklist/areas/ai.json at claim time
{
"issue": 29892,
"status": "done",
"branch": "claude/issue-29892-mcp-exposure-gate-repoint",
"pr": "https://github.com/objectstack-ai/objectstack/pull/29931",
"head": "dd6816240090d905cc5b2efa6252eeed352db65f",
"session": "session_017ihL2gLghEqeDKTbDTC7Zd",
"premise_still_valid": true,
"gates": {
"platform_checklist": "node scripts/check-platform-checklist.mjs :: exit 0 at dd68162400 ('check-platform-checklist: OK — 16 areas, 359 items'; symbol anchors 1137/1147 resolved, base a04e9d76 read 1134/1144: the three new source anchors all resolve)",
"derived": "node scripts/pm/dispatch-gates.mjs --commands --repo objectstack-ai/objectstack at dd68162400: 16 commands, each exit 0 — check-adr-links (+ --self-test), check-closing-keyword-parity (+ --self-test), check-comment-mask-corpus, ci/plan-test-core-shards --self-test, lint check:doc-formula-expressions, check:ci-filter-parity, check:cross-package-test-inputs, check:doc-authoring, check:driver-memory-census, check:gitlink-declared, check:nul-bytes, check:platform-checklist, check:refd-timer-probe, check:watch-hint-literal. check:doc-formula-expressions first exited 3 (PREREQUISITE NOT MET: @objectstack/formula and @objectstack/lint unbuilt); after turbo build of those two (lock VERDICT command-exit 0) it exited 0",
"ran_reconciliation": "dispatch-gates --ran with exit codes recorded: 16 derived, 16 run, 0 NOT-MEASURED, 0 UNRUN (a DERIVED zero)",
"not_local": "type-check lanes, Plan Test Core shards step, the 53 roster families, 11 wide-population families: CI's, NOT MEASURED locally; PR check-runs not yet concluded at report time",
"changeset": "none — docs only; skip-changeset rode pr_create and reads back on the PR",
"merge_origin_main": "merged once before pr_create: origin/main had not moved past a04e9d76c1 (ls-remote confirms)"
},
"deviations": [
"title re-pointed too: it said 'refuses system objects', the retired wholesale refusal; now 'admits a system-object action only on its own ai.exposed'",
"acceptance[1].verify re-pointed too: it called showcase_portfolio_snapshot 'the one exposed action', true only under the retired refusal. It now says the listing also carries the ai-exposed sys_* identity actions and that an unavailable entry is listed by contract. The clause text is unchanged, and the permitted-half reasoning still holds (no sys_* action declares requiredPermissions)",
"fixtures.requires[4] added (appended, so no index shifts) to stage acceptance[4]'s exposed half: a probe API key plus the admin's session token as the MCP bearer",
"source gained three symbol anchors (systemObjectActionExposureError, isListableAction, sys-api-key.object.ts#revoke_api_key)",
"the new clause was not run live: behaviour is derived from source and unit pins at a04e9d76, plus the card's own stock-boot reading at 589049b0"
],
"files_changed": ["docs/qa/platform-checklist/areas/ai.json (item ai.mcp-run-action-exposure-gate, revision 6 to 7; +15/-10)"],
"claims": [
{
"re_point": "acceptance[4]: a sys_* action passes the MCP system-object guard only on its own ai.exposed. REFUSED half: create_api_key on sys_api_key, absent from list_actions, refused in both live spellings, no key created. EXPOSED half: revoke_api_key, listed with aiExposed true and run under the admin session token with confirm true, ok true and the key revoked",
"evidence": "packages/runtime/src/action-execution.ts L141-158 systemObjectActionExposureError (returns null only on action?.ai?.exposed === true at L154; refusal text L156; the stored-metadata family stays refused L148-153), called in invokeBusinessAction L4260-4261; packages/mcp/src/mcp-http-tools.ts L395-397 isListableAction, refusal text L399-404, list filter L1483, run_action pre-screen L1585-1590; runtime listing asks the same predicate at packages/runtime/src/domains/mcp.ts L863. Pins run on this tree: packages/mcp/src/mcp-action-system-object-exposure.test.ts 8/8 passed (L82 lists attested and hides unattested; L98 refuses unattested with no bridge run; L120 admits attested), packages/runtime/src/mcp-system-object-action-exposure.test.ts 11/11 passed (L133 refuses unflagged sys_*; L144 yields to ai.exposed true only; L152 listing; L171 run_action refusal with no dispatch; L187 flagged runs through every gate). Dogfood corroboration (read, not run): packages/qa/dogfood/test/mcp-system-object-action-exposure.dogfood.test.ts L233-249 and L344-350 pin both spellings on impersonate_user. Fixture: packages/platform-objects/src/identity/sys-api-key.object.ts create_api_key L100 has no ai block; revoke_api_key L142 has ai.exposed with requiresConfirmation true"
},
{
"re_point": "steps[6]: names create_api_key (refused, with and without objectName, sys_api_key count read before and after) and revoke_api_key (listed and run with confirm true under the session bearer, key re-read)",
"evidence": "'any sys_* action name' can now pick one of the 36 exposed ones: git grep counts 36 'exposed: true' blocks under packages/platform-objects/src at a04e9d76, and the card read 37 list_actions entries on a stock boot at 589049b0"
},
{
"re_point": "strength kept: the clause still requires a sys_* action that does not declare ai.exposed to be refused with zero side effects, and names both halves. The verify names both FAIL shapes (an undeclared sys_* action listed or run; an exposed one refused with a system-object text)",
"evidence": "acceptance[4].clause and .verify in the diff"
},
{
"re_point": "negative[1] (the list/run agreement that found #28943) left intact; the clause's verify points to it for the osk_ unavailable case instead of scoring that case itself",
"evidence": "negative[] unchanged in the diff"
}
],
"mcp_calls": "0",
"api_writes": "2 relay strokes, each a POST /repos/objectstack-ai/objectstack/dispatches executed by fleet-write as objectstack-fleet[bot]: (1) pr_create, run 41645689870 success = POST /repos/objectstack-ai/objectstack/pulls (draft) + POST /repos/objectstack-ai/objectstack/issues/29931/labels [skip-changeset]; body read back 7138 bytes sent and stored, identical; no assignees, no reviewers; (2) this comment through post-stamped.mjs = POST /repos/objectstack-ai/objectstack/issues/29892/comments. Plus one git push of the branch (not a REST write)",
"security_findings": "withheld",
"out_of_scope_findings": [
"carrier: none · noted, not filed: fixtures.requires[0] still says 'the showcase's ONE ai-exposed action'. That is true of app-authored actions and was left as is; acceptance[1].verify now says the listing carries the sys_* exposed actions too",
"carrier: none · noted, not filed: the guard's third spelling, for the stored-metadata family ('…stores metadata bodies and is never exposed via MCP'), is outside this clause, which names sys_api_key only"
]
}
Activity
objectstack-fleet commentedon Nov 3, 2026
triage#1 · os-zhuang · session_01AavokzJ5DndAwitDXvKy4U
Path: none
Triage: first-touch audit · p1 ·
domain:devx·pm:queue· 2026-11-03T10:55Z⛔ Not a claim.
ai.mcp-run-action-exposure-gateacceptance[4] and step 6 still pin the wholesalesys_*refusal that the rulings on mcp: run_action refuses every action on a sys_* object, so an agent cannot reach the identity actions (ban_user, impersonate_user, set_user_password) that REST POST /actions serves #27681 (B) and [Decision] sys_* kernel objects, assessed as one set: which of the 58 platform identity actions may an agent ever reach (plain declaration / declaration + confirmation / human-only), executing #27681 B parameter 2 in one ruling #27900 replaced. So this P1 release-evidence item reads FAIL in every sweep, although the gate holds as ruled. It failed the same way in wave 4.check-platform-checkliststays green.Generated by Claude Code
objectstack-fleet commentedon Nov 3, 2026
domain:devx#2 · marchtian · session_017ihL2gLghEqeDKTbDTC7Zd
Claim: PM loop round 3
Session:
session_017ihL2gLghEqeDKTbDTC7ZdAccount:
marchtianBranch:
claude/issue-29892-mcp-exposure-gate-repointWorktree:
objectstack-issue-29892Domain:
domain:devxSeat:
domain:devx#2File surface:
docs/qa/platform-checklist/areas/ai.json(itemai.mcp-run-action-exposure-gate), plusFOLLOW-UPS.md/coverage.jsonwhere the checklist procedure requiresContainer & model:
M,mode:subagent,model: default tier,effort: highClause-②: no
Metadata-protocol: none
Responsibility: acceptance[4] and step 6 still pin the wholesale
sys_*refusal that rulings 6513869839 (#27681) and 6523087116 / 6540309323 (#27900) replaced, so this P1 release-evidence item reads FAIL on every sweepThread-read: 6601854076
Premise: holds
Serial constraints cleared: no open PR from this seat touches
platform-checklist/areas/ai.jsonat claim timeobjectstack-fleet commentedon Nov 3, 2026
domain:devx#2 · marchtian · session_017ihL2gLghEqeDKTbDTC7Zd
os-dev-report
{ "issue": 29892, "status": "done", "branch": "claude/issue-29892-mcp-exposure-gate-repoint", "pr": "https://github.com/objectstack-ai/objectstack/pull/29931", "head": "dd6816240090d905cc5b2efa6252eeed352db65f", "session": "session_017ihL2gLghEqeDKTbDTC7Zd", "premise_still_valid": true, "gates": { "platform_checklist": "node scripts/check-platform-checklist.mjs :: exit 0 at dd68162400 ('check-platform-checklist: OK — 16 areas, 359 items'; symbol anchors 1137/1147 resolved, base a04e9d76 read 1134/1144: the three new source anchors all resolve)", "derived": "node scripts/pm/dispatch-gates.mjs --commands --repo objectstack-ai/objectstack at dd68162400: 16 commands, each exit 0 — check-adr-links (+ --self-test), check-closing-keyword-parity (+ --self-test), check-comment-mask-corpus, ci/plan-test-core-shards --self-test, lint check:doc-formula-expressions, check:ci-filter-parity, check:cross-package-test-inputs, check:doc-authoring, check:driver-memory-census, check:gitlink-declared, check:nul-bytes, check:platform-checklist, check:refd-timer-probe, check:watch-hint-literal. check:doc-formula-expressions first exited 3 (PREREQUISITE NOT MET: @objectstack/formula and @objectstack/lint unbuilt); after turbo build of those two (lock VERDICT command-exit 0) it exited 0", "ran_reconciliation": "dispatch-gates --ran with exit codes recorded: 16 derived, 16 run, 0 NOT-MEASURED, 0 UNRUN (a DERIVED zero)", "not_local": "type-check lanes, Plan Test Core shards step, the 53 roster families, 11 wide-population families: CI's, NOT MEASURED locally; PR check-runs not yet concluded at report time", "changeset": "none — docs only; skip-changeset rode pr_create and reads back on the PR", "merge_origin_main": "merged once before pr_create: origin/main had not moved past a04e9d76c1 (ls-remote confirms)" }, "deviations": [ "title re-pointed too: it said 'refuses system objects', the retired wholesale refusal; now 'admits a system-object action only on its own ai.exposed'", "acceptance[1].verify re-pointed too: it called showcase_portfolio_snapshot 'the one exposed action', true only under the retired refusal. It now says the listing also carries the ai-exposed sys_* identity actions and that an unavailable entry is listed by contract. The clause text is unchanged, and the permitted-half reasoning still holds (no sys_* action declares requiredPermissions)", "fixtures.requires[4] added (appended, so no index shifts) to stage acceptance[4]'s exposed half: a probe API key plus the admin's session token as the MCP bearer", "source gained three symbol anchors (systemObjectActionExposureError, isListableAction, sys-api-key.object.ts#revoke_api_key)", "the new clause was not run live: behaviour is derived from source and unit pins at a04e9d76, plus the card's own stock-boot reading at 589049b0" ], "files_changed": ["docs/qa/platform-checklist/areas/ai.json (item ai.mcp-run-action-exposure-gate, revision 6 to 7; +15/-10)"], "claims": [ { "re_point": "acceptance[4]: a sys_* action passes the MCP system-object guard only on its own ai.exposed. REFUSED half: create_api_key on sys_api_key, absent from list_actions, refused in both live spellings, no key created. EXPOSED half: revoke_api_key, listed with aiExposed true and run under the admin session token with confirm true, ok true and the key revoked", "evidence": "packages/runtime/src/action-execution.ts L141-158 systemObjectActionExposureError (returns null only on action?.ai?.exposed === true at L154; refusal text L156; the stored-metadata family stays refused L148-153), called in invokeBusinessAction L4260-4261; packages/mcp/src/mcp-http-tools.ts L395-397 isListableAction, refusal text L399-404, list filter L1483, run_action pre-screen L1585-1590; runtime listing asks the same predicate at packages/runtime/src/domains/mcp.ts L863. Pins run on this tree: packages/mcp/src/mcp-action-system-object-exposure.test.ts 8/8 passed (L82 lists attested and hides unattested; L98 refuses unattested with no bridge run; L120 admits attested), packages/runtime/src/mcp-system-object-action-exposure.test.ts 11/11 passed (L133 refuses unflagged sys_*; L144 yields to ai.exposed true only; L152 listing; L171 run_action refusal with no dispatch; L187 flagged runs through every gate). Dogfood corroboration (read, not run): packages/qa/dogfood/test/mcp-system-object-action-exposure.dogfood.test.ts L233-249 and L344-350 pin both spellings on impersonate_user. Fixture: packages/platform-objects/src/identity/sys-api-key.object.ts create_api_key L100 has no ai block; revoke_api_key L142 has ai.exposed with requiresConfirmation true" }, { "re_point": "steps[6]: names create_api_key (refused, with and without objectName, sys_api_key count read before and after) and revoke_api_key (listed and run with confirm true under the session bearer, key re-read)", "evidence": "'any sys_* action name' can now pick one of the 36 exposed ones: git grep counts 36 'exposed: true' blocks under packages/platform-objects/src at a04e9d76, and the card read 37 list_actions entries on a stock boot at 589049b0" }, { "re_point": "strength kept: the clause still requires a sys_* action that does not declare ai.exposed to be refused with zero side effects, and names both halves. The verify names both FAIL shapes (an undeclared sys_* action listed or run; an exposed one refused with a system-object text)", "evidence": "acceptance[4].clause and .verify in the diff" }, { "re_point": "negative[1] (the list/run agreement that found #28943) left intact; the clause's verify points to it for the osk_ unavailable case instead of scoring that case itself", "evidence": "negative[] unchanged in the diff" } ], "mcp_calls": "0", "api_writes": "2 relay strokes, each a POST /repos/objectstack-ai/objectstack/dispatches executed by fleet-write as objectstack-fleet[bot]: (1) pr_create, run 41645689870 success = POST /repos/objectstack-ai/objectstack/pulls (draft) + POST /repos/objectstack-ai/objectstack/issues/29931/labels [skip-changeset]; body read back 7138 bytes sent and stored, identical; no assignees, no reviewers; (2) this comment through post-stamped.mjs = POST /repos/objectstack-ai/objectstack/issues/29892/comments. Plus one git push of the branch (not a REST write)", "security_findings": "withheld", "out_of_scope_findings": [ "carrier: none · noted, not filed: fixtures.requires[0] still says 'the showcase's ONE ai-exposed action'. That is true of app-authored actions and was left as is; acceptance[1].verify now says the listing carries the sys_* exposed actions too", "carrier: none · noted, not filed: the guard's third spelling, for the stored-metadata family ('…stores metadata bodies and is never exposed via MCP'), is outside this clause, which names sys_api_key only" ] }objectstack-fleet commentedon Nov 3, 2026
domain:devx#2 · marchtian · session_017ihL2gLghEqeDKTbDTC7Zd
Landed ·
domain:devx#2· 2026-11-03T13:57ZPR #29931 merged as
242665f105, and the card closed on itsFixes.ai.mcp-run-action-exposure-gaterevision 7 asserts the gate as ruled (6513869839 on mcp: run_action refuses every action on a sys_* object, so an agent cannot reach the identity actions (ban_user, impersonate_user, set_user_password) that REST POST /actions serves #27681, and 6523087116 / 6540309323 on [Decision] sys_* kernel objects, assessed as one set: which of the 58 platform identity actions may an agent ever reach (plain declaration / declaration + confirmation / human-only), executing #27681 B parameter 2 in one ruling #27900). A system-object action is admitted over MCP only on its ownai.exposed. acceptance[4] names both halves onsys_api_key:create_api_keyis refused, andrevoke_api_keyis listed and runs. negative[1], the clause that found MCP list_actions offers sys_api_key.revoke_api_key as runnable to an API-key caller, and run_action then refuses it 403 #28943, is unchanged.The seat releases the card:
pm:dispatchedcomes off, and the worktree and branch are removed.