INSTR-01: grade the suppression rule at the level it is written at, one case per clause
checks / unit (pull_request) Successful in 7m4s
checks / unit (pull_request) Successful in 7m4s
SAFETY-44 produced THREE inert controls for this one rule, each inert differently, and split the two remaining fixes out rather than ship them unmeasured. This is that card, and the first thing it did was explain why the end-to-end route could never have worked. ⚠️ `moved_to` IS ONE COMPREHENSION CARRYING FIVE CONDITIONS WITH FIVE DIFFERENT REASONS TO EXIST, AND `run()` BUILDS BOTH SNAPSHOTS FROM ONE STATE FILE. So "the destination was already latched" and "the destination was made by this transition" are the same file answering two incompatible questions: the arrangement that reaches one forecloses the other. That is why rebuilding a fixture to reach clause N kept moving the others, and it is not a fixture problem. ⭐ SO THE RULE IS GRADED WHERE IT IS WRITTEN - `diff()` on constructed Snapshots, ONE CASE PER CLAUSE. Six rows, and on the SHIPPED tree before any fix they already separated the two known defects: R1 rename (legitimate) migrated correct R2 narrowing vanished correct R3 provenance MIGRATED ⚠️ the defect R4 same value vanished correct R5 injectivity BOTH migrated ⚠️ the defect R6 machine_read vanished correct The two one-line fixes SAFETY-44 reverted are back, and R3/R5 flip while R1/R2/R4/R6 do not - so the legitimate rename is still suppressed and this is not an over-correction. ⭐ AND EACH CLAUSE REMOVAL FLIPS **EXACTLY ITS OWN ROW**, which is the acceptance criterion this card was filed with: C1 machine_read removed -> ['R6-machine-read'] C3 same value removed -> ['R4-value'] C5 off-roster removed -> ['R2-narrowing'] C6 injectivity removed -> ['R5-injectivity'] C7 provenance removed -> ['R3-provenance'] A removal that flips nothing is an unmeasured clause; a removal that flips someone else's row means the cases are not separable after all. Neither happened. ⚠️ AND M12 IS DELETED, WHICH IS THE MOST USEFUL THING THIS CARD FOUND. M12 was SAFETY-44's end-to-end control for the narrowing and it was a REAL control - red when the narrowing was removed. Adding the provenance clause disarmed it, and NO FIXTURE CAN RESTORE IT, measured both ways: with the sibling latched in its own right, C7 rejects the destination before C5 is consulted, so the mutation is reported whether or not C5 exists; making the destination transition-made means a flat latch, which makes the shipped run dirty and breaks M12's own precondition. The second half of the card's acceptance criterion - "M12 still turns red with the new clauses in" - is therefore UNSATISFIABLE, and the honest answer is to remove the control rather than keep one that has become inert. R2 measures C5 strictly better. Part 5 keeps the end-to-end coverage; discrimination lives in 5e. `state-both-latched.json` goes with it. Nothing referenced it once M12 was gone, and the first draft of that paragraph said it was "kept, because 5e's R2/R3 are derived from the arrangements it represents" - a nice sentence and not a reference. An unused fixture a comment calls load-bearing is an inert check one directory over. TWO THINGS THE DRIVER GETS RIGHT ON PURPOSE: - it is written to a TEMPDIR, not beside the tool. `checks / unit` mounts the checkout READ-ONLY, so writing into the tree works on a dev box and is `OSError: Read-only file system` in CI - green for whoever wrote it and red on every PR. Caught by running it in the check image before committing. - the TABLE stays in the test file and the driver goes into the tree under test, so a mutation to the tool cannot also move the answer it is graded against. 28/28 files pass. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01BwRLw7eKYj2byVdwB6kbjU
This commit is contained in:
co-authored by
Claude Opus 5
parent
806390d8b1
commit
91b0d5e4dc
@@ -545,6 +545,12 @@ def diff(before: Snapshot, after: Snapshot) -> list:
|
||||
# name and whose roster start writes them under another reported two
|
||||
# VANISHED findings about a pair of defaults, and CONTROL-C went red on a
|
||||
# build that was CORRECT.
|
||||
# ⚠️ `claimed` MAKES THE MOVE INJECTIVE. Without it N vanished keys can all
|
||||
# claim the SAME destination - and `DEFAULTS["sign_tripped"] is False`, so
|
||||
# `True` is the ONLY non-default value a latch can hold, which means they
|
||||
# collide by CONSTRUCTION rather than by coincidence. Two keys cannot both
|
||||
# have become one key; the second claimant has not moved anywhere.
|
||||
claimed = set()
|
||||
for key in sorted(set(before.data) - set(after.data)):
|
||||
value = before.data[key]
|
||||
bare = key.rsplit("/", 1)[-1]
|
||||
@@ -575,9 +581,15 @@ def diff(before: Snapshot, after: Snapshot) -> list:
|
||||
# thing it named - and a citation is the worst possible carrier for that,
|
||||
# because it reads as having been checked. The branch is now bounded by
|
||||
# M12, written for it, in test_rehearse.py.
|
||||
# ⚠️ AND THE DESTINATION MUST BE ONE **THIS TRANSITION MADE**
|
||||
# (`before.data.get(k) != value`) AND NOT ALREADY SPOKEN FOR
|
||||
# (`k not in claimed`). Without the first, a roster unit that was
|
||||
# already latched in its own right is a free suppression slot that
|
||||
# nobody moved into.
|
||||
moved_to = sorted(
|
||||
k for k in after.machine_read
|
||||
if k.rsplit("/", 1)[-1] == bare and after.data.get(k) == value)
|
||||
if k.rsplit("/", 1)[-1] == bare and after.data.get(k) == value
|
||||
and before.data.get(k) != value and k not in claimed)
|
||||
# ⚠️ AND THE VANISHED KEY'S OWN UNIT MUST BE **OFF THE ROSTER**, WHICH
|
||||
# THE FIRST VERSION OF THIS RULE DID NOT REQUIRE AND WHICH IS WHAT MADE
|
||||
# IT A SOFTENING. The match was bare-key-plus-value over the whole of
|
||||
@@ -600,6 +612,7 @@ def diff(before: Snapshot, after: Snapshot) -> list:
|
||||
vanished_unit = key.split("/")[1] if key.startswith("unit/") else None
|
||||
if vanished_unit is not None and vanished_unit not in after.units \
|
||||
and moved_to:
|
||||
claimed.add(moved_to[0])
|
||||
after.vanished_but_migrated.append(
|
||||
f"{key} = {value!r} -> {moved_to[0]}")
|
||||
continue
|
||||
|
||||
Reference in New Issue
Block a user