2 commits
| Author | SHA1 | Message | Date | |
|---|---|---|---|---|
| 8d58568013 |
CB-WP-0024: the table you can watch
Some checks failed
ci / check (push) Has been cancelled
Four of the maintainer's five playtest remarks. Three of the five turned
out to be data the projection already carried, rendered as text -- the
table's problem was legibility, not content, and the coverage gate passes
either way because it proves nothing is OMITTED, not that anything is
readable. That gap is named in the evidence rather than closed: the honest
control is a person playing it.
T01. The ending control was two defects wearing one button. The label said
"close -- I have read this" while hotseat.rs reads `done` as STOP THE
SERVER, and acknowledging it changed nothing -- the tab kept a full table
and a `play again` pointing at a closed port. Now labelled by its effect,
and the page seals itself on the `closed` reply: removeAttribute on every
control's data-drop, so they stop being droppable by the same rule that
made them droppable. removeAttribute rather than setAttribute(_, null),
which writes the truthy string "null" in a browser.
The reason it survived is structural. jsrun's fetch stub returned
{then: function(){return this}} and never invoked its callbacks, so every
line of the script reacting to the server was unreachable from every test
in this project -- a page that ignores the server was indistinguishable
from one that acts on it. Same finding as CB-WP-0016's "a stub too thin to
express a failure is how the failure survives", one layer deeper, at the
reply. The stub now delivers a real then-chain; gesture_with_reply reports
surviving controls; the seal is mutation-proven and a negative control
asserts `ok: dealing` does NOT seal.
T02. Draw and discard as offset stacks with counts. The shuffle question
the task required settling: it already works, at
games/ground/src/lib.rs:1419-1435, implementing the U4 default that
ground-game confirmed 2026-08-03. Nothing raised. The piles show the state
before it fires, which is derivable from the view; a claim that a
reshuffle HAS happened is not, and is not made. CB-WP-0026 applied that
ruling the same day this consumed it -- first time answering "is this
underdetermined?" was one lookup instead of a message.
T03. Each seat's play drawn as a card, sentence kept beside it. The
face-down back is a const with no parameters: SelectionView::Hidden
carries nothing, so there is no data path into the back to add later. The
leak test copies view.rs's own shape -- identical backs across two
different hidden situations, THEN assert a revealed play does show,
because without the second half the first passes for a renderer that draws
nothing.
T04. MatchTally lives in `play`, beside the listener and the seed. What
"cumulative" means was decided before anything was summed, and the answer
is that GROUND defines one game and no series: summed personal score and
games-won answer different questions, and a test asserts they can point at
different seats. Both shown, both labelled. Registered F15 as a NOTE --
the test shows the tallies can differ, which is arithmetic, not evidence
the ambiguity harms play, so GameDesign §3.1 bars reporting it. First use
of the note tier since D6 wrote it, and it came from building rather than
from play.
make all: exit 0. 41 render tests, 26 cb-play tests, loop-lint clean.
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
|
|||
| 6be9fbc9af |
CB-WP-0026: collect the rulings -- ten answers that arrived and were never applied
Some checks failed
ci / check (push) Failing after 3s
ground-game ruled all ten U-items on 2026-08-03, every one CONFIRMED as the default clay-borg simulates, and confirmed five of six provisional scenarios. clay-borg never collected the answers: CB-RES-0007 reported "0 of 10 ruled" the same day, and CB-WP-0022 built the finding register two days later still recording them as `reported`. make design's first run is what noticed -- not a human, not the adversarial review that found four other things. That is the unread-inbox failure running in the opposite direction, and it appears nowhere in the declaration, survey, ADR or spec of the pass that was built entirely around the forward version. It is arguably worse: an unread message is visible as silence, while a collected-but-unapplied ruling looks exactly like work in progress. Ten rulings quoted into §Underdetermined (the three conditional ones verbatim -- U1's designer note, U2's End-only trigger, U8's consume-only-if-it-cancels). Five provisional flags lifted, replaced by ruled/ruled_by/ruled_note so the flag went and the provenance stayed. Register queue 9 -> 0. T02's control came back clean: make sim is 26 passed, 59 rules covered, nothing red. Had a scenario gone red it would have meant we described our own behaviour incorrectly to ground-game. I wrote two U-item mappings and both were wrong. gr-a04 -> U1 (it asserts consent is REQUIRED; U1 asks WHEN the target accepts) and gr-d05 -> U5 (it exercises the UNREJECTED Reverse; U5 is the rejected one). Both plausible from covers:, neither survived reading the description. Third and fourth instance of this defect; the first two reached ground-game. So encodes_u_item is now a declaration and design.py asserts the file names what it claims -- and that check's own first version grepped for mentions and went red when two files recorded why they do NOT encode U1 and U5. A mention is not a claim, which is exactly the looseness that let "six of the ten have provisional scenarios" stand. Two positive controls went red for the best possible reason, both broken the same way -- asserting against live repo data instead of constructing their condition. rule-coverage.py required at least one provisional item to EXIST; it now builds a fixture and reports the live count as a diagnostic, because there is no number of provisional items this project should have. design-baseline.py pinned "2 of 6" while recomputing one row from a live glob, so the dated snapshot was never a snapshot; frozen to its 2026-08-03 list and unwired from self-tests, since per ADR-0012 D8 it is no longer a reporting tool. ScenarioFile is deny_unknown_fields and refused the four new fields until declared -- correct: a corpus accepting unknown metadata would let a typo'd encodes_u_iem sit there claiming nothing. DEVIATION: ADR-0012 D2 said "no new file". GroundRules.md crossed the loadability limit, so the register moved to specs/FindingRegister.md. D2's substance holds -- one register, same machinery, nothing competing -- but the literal instruction did not, and it resolves an awkwardness D2 named itself. make all: exit 0. loop-lint clean. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> |