Cold adversarial review of b7e5c35fb returned BLOCKED with four substantive findings. All four
are real and all four are fixed here; each fix is demonstrated rather than asserted.
1. THE guard/none LINE EXCLUDED BOTH REQUIRED CONTEXTS. The rule was "a guard enforces an
invariant about the REPOSITORY; a job exercising the PRODUCT is `none`". It reads as
principled and put `test` and `migrations` outside the table — the two required Actions
contexts on `main` per .gitea/required-status-contexts.json, i.e. exactly the jobs where a
failure to fire is fail-OPEN against branch protection, and exactly the gap #786 exists to
close. It also could not survive its own examples: `test` runs ToolCatalogTests.cs and
web/src/api/*.guard.test.ts, the structural guards this document's own scope-limit item 2
names.
Replaced with a line that can be restated: a `guard` job's output is a VERDICT; a `none`
job's output is an ARTIFACT. A `none` job can still go red — that is an error in producing
the thing, not a finding about the repo. `test`, `migrations` and `functional-e2e` flip to
`guard` and gain rows; `none` is now exactly the two image publishers plus renovate. The
rejected rule is recorded so it is not re-adopted.
2. TWO POSITIVE CONTROLS WERE VACUOUS — both of them ones this commit series added, while the
pre-existing sibling it copied was not. `len(_MUTANTS) == 2 * len(population)` is `2N == 2N`,
a tautology at N=0, so an emptied population satisfied it while the parametrised proofs
collected zero cases. Both now assert non-emptiness FIRST. Demonstrated after the fix, by
degrading each population to empty:
role mutation set -> REDDENED: "declared_roles() is EMPTY ..."
declaration mutation set -> REDDENED: "the workflow parsed to ZERO jobs ..."
phantom-row proof -> REDDENED: "the table parsed to nothing ..."
3. A MECHANISM CLAIM IN A DECISION RECORD WAS REFUTED BY EXECUTION. Four sites (the test
docstring, docs/ci-cd.md, the record's `rule:`, and the generated catalog) said
`functional-e2e` reaches dotnet only through scripts/e2e-local.sh and so is invisible to the
step scan. It is not: that job runs `dotnet restore`, `npm ci`, `npm run build` and
`dotnet build` in its own YAML, and the derivation detects it. Measured: the blind-spot set
(declared toolchain minus detected-from-own-steps) is EMPTY today, all five jobs detected.
Reworded to say that, and the converse is still not asserted because a future job could be
written behind a script.
4. THE ADJACENCY RESIDUAL WAS UNDERSTATED. All three checks fail together under one edit that
drops the container block, flips the marker AND moves the invocation into a script — the
review verified it. Now disclosed in the code and in docs/ci-cd.md, with what actually bounds
it: the failure MODE, not its likelihood. The job then dies on a missing binary, loudly,
where #774's original defect sent a REQUIRED check green on the bare runner. A silent pass
traded for a noisy crash, not a hole closed.
Also from the review: the docs-reminder row said the job "never fails" (its Checkout step can);
the phantom-row proof could not fail (it supplied its own phantom, so it now pins the unmutated
set to zero phantoms first); and the scope-limit paragraph was reworded from draft history into
a rejected-alternative note.
Review findings 6 and 7 (regex false positives on comments, false negative on `dotnet-ef`) were
already fixed in 75747fbca, which the reviewer did not see.
Suite: 1161 passed, 2 skipped. ruff 0.12.11 clean; decisions-validate OK.
NOTE for whoever sees a red `test_hook_fire_log.py::test_the_suite_does_not_write_to_the_
PRODUCTION_log` locally: it snapshots mtimes under ~/.cache/ersatztv/hook-fire/, which is shared
across worktrees and sessions, so a second Claude session running concurrently reddens it. Seen
once here with three session logs written during the window; green in isolation, both before and
after this change. That is ersatztv#809 / #822, not this diff.
Refs #786
Refs #789