Skip to content

Commit fe91144

Browse files
committed
chore(changeset): record the present-tense correction of the confirmation-gate prescriptions
Claude-Session: https://claude.ai/code/session_01AmH9bKvGoLjiY86Q4Z3og2 Co-authored-by: Claude <noreply@anthropic.com>
1 parent ce11ba5 commit fe91144

1 file changed

Lines changed: 72 additions & 0 deletions

File tree

Lines changed: 72 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,72 @@
1+
---
2+
"@objectstack/spec": patch
3+
---
4+
5+
fix(spec): the three shipped confirmation-gate prescriptions state the gate in the present tense — they were denying a door that exists (#17487)
6+
7+
Clause-②: no
8+
9+
No accept-set change and no export moves. `ToolSchema` still refuses
10+
`requiresConfirmation` with a located parse error, `ActionSchema` still accepts
11+
`ai.requiresConfirmation` in both directions, and `check:authorable-surface` /
12+
`check:api-surface` are byte-identical across this diff. What moves is text.
13+
14+
Three customer-facing prescriptions were written while the runtime confirmation
15+
door was a separate, unlanded change, and each said so in the present tense. The
16+
door has since landed on `main` — `actionConfirmationRefusal`, called pre-dispatch
17+
by `invokeBusinessAction` in `@objectstack/runtime`, with the `confirm` member
18+
grown on the MCP `run_action` tool in the same change. From that moment the
19+
published prose DENIED a door that exists, and it denied it in the dangerous direction: an author who
20+
reads it concludes the safety flag stops nothing and either arranges a human in
21+
the loop some other way or stops setting the flag — losing the gate exactly when
22+
it starts working. That is the ADR-0049 false-compliance defect with the sign
23+
flipped.
24+
25+
**The three carriers**, all of them shipped text rather than comments:
26+
27+
1. the `requiresConfirmation` entry of `TOOL_RETIRED_KEY_GUIDANCE`
28+
(`ai/tool.zod.ts`), which reaches consumers as the parse error on the
29+
`.strict()` `ToolSchema` — the one channel every consumer bumping
30+
`@objectstack/spec` is guaranteed to hit;
31+
2. the ADR-0087 D3 entry's `replacement`, and
32+
3. its `acceptanceCriteria` — what `spec-changes.json`,
33+
`docs/protocol-upgrade-guide.md` and `os migrate meta` project to consumers.
34+
35+
FROM → TO, on the sharpest of the three (the acceptance criterion):
36+
37+
```
38+
was: Do NOT try to "prove the gate" by invoking the operation without the
39+
confirmation member: ... before that ships the call is not refused, it
40+
RUNS the destructive operation.
41+
now: ... that gate is PERFORMED: invoking the operation over an AI-exposed
42+
door without the confirmation member is REFUSED with
43+
ACTION_CONFIRMATION_REQUIRED (428) and nothing runs, so that call is a
44+
real check you can make rather than a destructive experiment.
45+
```
46+
47+
**The corrections carry the door's BOUNDS, because over-promising here is the
48+
same defect in the other direction.** Each prescription now states, as the door
49+
itself declares them: the refusal is `ACTION_CONFIRMATION_REQUIRED` / 428 naming
50+
the action and the member `confirm: true`; it is a GATE, not a queue — nothing
51+
is parked and a refused call did not run, no record read and none written; the
52+
enforced set is the doors that enforce the author's `ai.exposed` opt-in, today
53+
the action door reached from the MCP `run_action` tool, while REST `/actions` is
54+
not `ai.exposed`-gated and sits outside the gate; only the author's declared
55+
`ai.requiresConfirmation: true` refuses, while the wider listing heuristic
56+
advises and never refuses; and `confirm: true` is an unverifiable caller claim,
57+
so the gate makes FORGETTING loud without proving a human.
58+
59+
`ai/tool-confirmation-prescription-tense.pin.test.ts` is the tie that was
60+
missing the first time: it reads the three shipped strings AND the runtime door,
61+
so a prescription that re-acquires a not-yet-shipped denial fails, and a door
62+
that is removed, narrowed off the DECLARED flag, unhooked from
63+
`invokeBusinessAction`, or widened onto REST `/actions` fails naming both files.
64+
The denial predicate is fed the three retired sentences verbatim, so it cannot
65+
pass by the prose merely falling silent.
66+
67+
**On release ordering.** The door ships in the same release this correction
68+
does: the runtime changeset that carries it (`action-confirmation-gate-enforced`)
69+
is still pending alongside this one, and one `changeset version` run consumes
70+
both. A release cut before this lands is the failure this card exists to end —
71+
the runtime refusing calls while the published spec text tells authors the flag
72+
stops nothing.

0 commit comments

Comments
 (0)