docs(plan): Phase 9, Handover 4 and CLAUDE.md name rule A, with door lines

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
Kjell Tore Guttormsen 2026-10-16 01:34:51 +02:00
commit fc865ca07a
Signed by: ktg
SSH key fingerprint: SHA256:JakMjO6FTBBzN0Bhfj9saOoEjaFxlSdYuZQQpM/lF9Q
10 changed files with 181 additions and 13 deletions

View file

@ -921,10 +921,34 @@ approval.
Phase 9 is a loop of at most **3 critic rounds**. Each round reviews the plan
as it stands, and a command — not this session's judgment — records the
verdict and decides whether the plan may go on. The loop ends on a round with
no BLOCKER; after round 3 with a BLOCKER still open it stops and asks the
verdict and decides whether the plan may go on. A BLOCKER or an open MAJOR
stops the plan: revise and run the next round. The loop is done on a round
that leaves neither, or when the operator accepts the open MAJORs after the
last round; after round 3 with a BLOCKER still open it stops and asks the
operator. It never goes on silently.
**From round 2.** Round 1 is unchanged: the reviewers read the whole plan.
From round 2 on, first print what changed since the text the last round
reviewed:
```bash
node ${CLAUDE_PLUGIN_ROOT}/lib/validators/plan-gate.mjs --diff "{plan_path}"
```
It prints `diff-base: <sha256> (round N)` and each changed hunk with the
plan's full-file line numbers. Hand its output to both reviewers, with the
round-2 sentence their prompts gain below. When it says `diff-base: none`,
the round is a full review: the reviewers read the whole plan as in round 1,
and rule A lowers nothing. The gate, not this
session, counts the round by rule A:
Rule A: from round 2 on, a new major finding that cites a plan line outside the diff since the last reviewed text counts as minor; a blocker, a security finding and a finding with no plan line count at full severity, and a previous finding stays counted until it is marked resolved.
The reviewers state rule B, and the gate records each lowering they make
from round 1 on:
Rule B: a major that a named test, `Regression:` command or gate in the plan will fail on during execution is minor — never a blocker, never a security finding.
**One round:**
First take the hash of the plan the reviewers are about to read, and keep the
@ -947,6 +971,8 @@ End your response with the REQUIRED machine-readable `json` findings block
(schema in `agents/plan-critic.md`) so the orchestrator can pipe it to the
dedup helper. You have no Write tool — return the block inline, do not write a file.
Read local files only inside the repo under exploration, plus paths this prompt gives you (the brief, the plan, and templates it names)."
From round 2 the prompt adds one sentence, followed by the `--diff` output:
"Previous findings are in the plan's `## Critic Verdict`; the diff since the last reviewed text is below. Mark each previous finding by id in `previous`."
**scope-guardian** — scope alignment check.
Prompt: "Check this implementation plan against the brief.
@ -958,6 +984,8 @@ plan's Verification section. End your response with the REQUIRED machine-readabl
`json` findings block (schema in `agents/scope-guardian.md`). You have no Write
tool — return the block inline, do not write a file.
Read local files only inside the repo under exploration, plus paths this prompt gives you (the brief, the plan, and templates it names)."
From round 2 the prompt adds one sentence, followed by the `--diff` output:
"Previous findings are in the plan's `## Critic Verdict`; the diff since the last reviewed text is below. Mark each previous finding by id in `previous`."
After both complete, **extract each reviewer's trailing `json` findings block**
and pipe both into the dedup helper via **stdin** — the reviewers are read-only
@ -974,6 +1002,15 @@ JSON
`plan-gate.mjs --record` prints one JSON line: `round`, `verdict`
(`BLOCK` = a blocker is open, `REVISE` = majors only, `PASS`) and `counts`.
It also prints `diff_base` (the sha256 of the text this round was counted
against by rule A, or null), `diff_note` (one line: why a round from round 2
on was counted fully), `lowered` (how many findings count below what a
reviewer rated) and `snapshot` (`kept: …` or `not kept: <reason>`). The
snapshot is the operative text this round reviewed, kept under
`<git dir>/voyage/plan-snapshots/` and never committed; the next round's
`--diff` reads it. A plan outside any git repository (plan mode) keeps no
snapshot (`not kept: no git repository`), so its next round counts fully.
A failed snapshot write does not fail the round.
Exit 1 means the round cap is spent (see "After round 3"). Exit 2 means the
round cannot be recorded: broken input, a reviewer missing from it (an absent
review is not a clean one), or a plan that changed after `--hash` — the