diff --git a/WORK-QUEUE.md b/WORK-QUEUE.md index 74e9871..a361e89 100644 --- a/WORK-QUEUE.md +++ b/WORK-QUEUE.md @@ -3389,3 +3389,56 @@ prototype, the walk and the fixture harness. `c4127c6c` into the shared build tree first, then publish.** As of this clock the shared tree still reads `97fedb5d…` (`build_blocks.py`) / `63c9cee6…` (`blocks.json`), the live index is 34,488 B / `4f764ef4dfb9…`, and nothing has been published. + +--- + +**Status: DONE 2026-10-11 — `recoveries/render-site-channels.md` (Merlin), scratch tree +`/root/crucible/q28/`. 20 channels: 13 covered by fixture (19 fixtures), 7 excluded with a +measured command; every negative exits 1 with 0 builder writes; the no-token control is +byte-identical to the live `site-ledger` at `91ecf6bf`.** + +- **The guarantee, restated as one sentence and printed from the source:** any string containing + `{{` or `}}` anywhere inside a `blocks.json` entry — at any nesting depth, checked before a + single byte is written — kills the build; the only tokens that ever ship are well-formed + `{{x:HANDLE}}` tokens in the four prose panels of a summary-branch entry naming a cited handle. + Guards printed with line numbers: `check_tokens` (:192-225), `check_gaps` (:228-234), + `check_uncited` (:151-169), all above `OUT.mkdir` (:292-304). +- **Fixture table (19 fixtures, one mutated `blocks.json` per scratch tree).** 16 negatives, + every one exit 1 / 0 files: `coverage.gaps[0]`; `slug` (canonical href, sitemap `loc`, index + `li` id, pager hrefs — one fixture, and `slug_for("{{x:")` → `"x"`, which is why the die + prints `x:slug:`); `sort_date` (year heading `sortable[:4]`); `n` (pager text); + `body_source_url` both shapes (`safe_url` → `must be https, got '{{x:'`; sentinel scan); + `receipt.usd` (arithmetic formatted strings); `title`; `date` (JSON-LD `datePublished`); + `contributor.display_name` (JSON-LD author); `status`/`ledger` (entry validation — + `unknown status '{{x:'`); `block-5` body on the quote branch (genesis :435, panel set printed + without `body`); `block-5` uncertainty (genesis :448, `check_uncited` pre-write); a + research-only `title` token (label staged branch :385); a planted `index.html` in OUT + (PROTECTED guard — 1 planted file refused, 0 builder writes). 3 positives, all exit 0 / + 125 files: research-only without a token builds and prints `(staged, not published)` once on + the index (the branch is data-reachable; 121/121 are `cleared` today); `hi` + in `title` ships as `<\/script>` (the JSON-LD channel is watched by `json.dumps` + ``-escape, + not the sentinel — a different class, stated); a cited token in `block-5`'s `body_provenance` + expands on **both** landings — exactly 2 files change, 1 anchor each. +- **Control:** unmodified `blocks.json` (`63c9cee6…`) through the patched builder + (`c4127c6c…`): exit 0, 125 files, tree digest + `91ecf6bf939a2a499983066a2331bb953eab8a4ca85c66a8a19f42cb1b28f7a8`, `diff -rq` against the + shared `site-ledger` silent. +- **Two corrections, stated in prose (Q27's file corrected by reference, never by edit):** + the pristine builder has **36 `esc()` call lines / 43 call occurrences**, not 28 (measured: + lines containing `esc(` minus the `def esc(v):` at :87 → 36; occurrence count minus the + definition's → 43); and Q27's stated fixture breakdown sums to **41 — 42 counting the omitted + `excl:contributor.handle` row — against its own 35-row log** (`Q27-RESULTS.json`: 35 rows, + 5 × exit 0 / 125 files, 30 × exit 1 / 0 files). +- **The one Q27 exclusion reason falsified by measurement:** `slug_for()`'s sanitisation is + real but irrelevant — the walk kills the token one step earlier, so "sanitised out" is not + the guard (the pipe's C4 holds; re-measured here). Conversely the label-staged branch's "no + entry takes it" is true today and false as an exclusion reason: flipping one entry builds it. +- **Nothing touched:** shared tree still `97fedb5d…` / `63c9cee6…` (nothing modified since + 2026-10-11 02:00Z), live index **200 / 34,488 B / `4f764ef4dfb9c08b…`** re-fetched this run, + `decisions/` and `inbox/` untouched, nothing executed, no other party's file edited. The + publish precondition stands unchanged: **adopt `c4127c6c` into the shared build tree first, + then publish** — Alexander's call, not this item's. +- **Limits:** the 16 negatives die at the sentinel walk by construction, so they demonstrate + the channels, not a shape census (Q26's 12-fixture set is the shape census); the `OUT`-is-`site/` + guard is source-read only (`OUT` is hardcoded, so the comparison cannot fire without editing + the builder); Q25's census is cited, not re-run; no X page fetched this tick. diff --git a/checkins/2026-10-11-merlin.md b/checkins/2026-10-11-merlin.md index fdec88c..f3d2d23 100644 --- a/checkins/2026-10-11-merlin.md +++ b/checkins/2026-10-11-merlin.md @@ -255,3 +255,136 @@ Re-verified in the same breath: shared `build_blocks.py` still `97fedb5dd5e85d2 the live ledger index `https://alexanderwhitestone.com/stackchain/blocks/` is 200 / 34,488 B / `4f764ef4dfb9c08b…`. `blocks.json` read-only throughout; `decisions/` and `inbox/` untouched, nothing executed, no secret printed anywhere. + +--- + +# Run 3 — Q28, claimed and finished (the channels the entry walk cannot see) + +> Screen. Every claim below carries a path, a hash, a URL, or a command with its output, or the word +> `unverified`. Nothing secret is printed anywhere in this check-in or in the files it lands. + +## Did + +Claimed and finished **Q28 — the channels the entry walk cannot see** (the top unclaimed item, +opened by the pipe 02:5xZ on the residue of its own Q27 verification tick; Q20 is +zephyrus-sparkborn's, Q9 blocked on the audio handover, Q13/Q19 gated on Alexander). + +Deliverable: `recoveries/render-site-channels.md` (**16,456 B / sha256 +`ea4b5e988a065dfd0bbc06f735cf7aead88e30030dfd9af4bcfdf5c05ec4c1bc`**), scratch tree +`/root/crucible/q28/`. The builder under test is the Q27 patched one, copied in and verified: +`build_blocks_hard.py` sha256 `c4127c6c9325ed9f8cab03b80b454cccde0f9f1e768289ff216d2fb79e78dbf2` +(29,174 B); `blocks.json` `63c9cee6103a6824c90c71440fa983d2f5592e380f9c3fb40f7ad366ae41723d` +(278,459 B), read-only throughout. + +**The guarantee, now one sentence with the walk printed:** any string containing `{{` or `}}` +anywhere inside a `blocks.json` entry — at any nesting depth, checked before a single byte is +written — kills the build; the only tokens that ever ship are well-formed `{{x:HANDLE}}` tokens +in the four prose panels of a summary-branch entry naming a cited handle. Guards with line +numbers in the deliverable: `check_tokens` (:192-225), `check_gaps` (:228-234), +`check_uncited` (:151-169), all above `OUT.mkdir` (:292-304). + +**Result: 20 channels — 13 covered by fixture (19 fixtures), 7 excluded with a measured +command. Every negative exits 1 and writes 0 files; the one output directory holding a file at +failure holds the file the fixture planted, which the guard refused to clean.** Control: +unmodified `blocks.json` through the patched builder → exit 0, **125 files**, tree digest +`91ecf6bf939a2a499983066a2331bb953eab8a4ca85c66a8a19f42cb1b28f7a8`, `diff -rq` against the live +`site-ledger` silent. + +The 16 negatives, each its first stderr line in the deliverable: `coverage.gaps[0]`; `slug` +(one fixture covers canonical href, sitemap `loc`, index `li` id, pager hrefs — and +`slug_for("{{x:")` returns `"x"`, so the die prints `x:slug:`); `sort_date` (year heading); +`n` (pager text); `body_source_url` both shapes (`safe_url` → `must be https, got '{{x:'`; +sentinel scan); `receipt.usd`; `title`; `date`; `contributor.display_name`; `status`/`ledger` +(validation); `block-5` body on the quote branch (genesis :435); `block-5` uncertainty +(:448, pre-write); a research-only `title` token (label staged branch :385); a planted +`index.html` in OUT. The three positives: the staged branch builds and prints +`(staged, not published)` once when an entry takes it; `hi` in `title` ships as +`<\/script>` (the JSON-LD channel's guard is the `json.dumps` + ``-escape, not the sentinel — +a different class, stated); a cited token in `block-5`'s provenance expands on **both** landings, +2 files changed, 1 anchor each. + +The 7 exclusions, each measured: `CSS`/`FOOT` literals (grep of definition + usage sites, plus +`grep -c '\.format(' build_blocks_hard.py` → **0**); receipt row keys (the only `esc(k)`, over a +hardcoded tuple); dict keys (`walk(v, …)` recurses on values only); the `OUT`-is-`site/` guard +(source-read — `OUT` is hardcoded to `BASE/"site-ledger"`, so the comparison cannot fire without +editing the builder); the write set (**125 files, intersection with `PROTECTED` = `[]`**); the +manifest (124 file entries, every value `{"sha256","bytes"}` only); `coverage` keys other than +`gaps` (four grep lines, all `coverage.gaps` — the rest is unrendered data). + +Two corrections stated in prose, Q27's file corrected by reference only: the pristine builder +has **36 `esc()` call lines / 43 call occurrences**, not 28 (measured — 37 lines contain `esc(` +including the definition, 44 occurrences including it); and Q27's stated fixture breakdown sums +to **41 — 42 with the omitted `excl:contributor.handle` row — against its own 35-row log** +(`Q27-RESULTS.json`: 35 rows, 5 × exit 0 / 125 files, 30 × exit 1 / 0 files). One Q27 exclusion +reason is falsified by measurement: `slug_for()`'s sanitisation is real but irrelevant — the walk +kills the token one step earlier. + +## Blocked + +Nothing blocked the run. Limits, stated in the deliverable: the 16 negatives die at the sentinel +walk *by construction*, so they demonstrate the channels, not a shape census (Q26's 12-fixture +set is the shape census and is not re-run); the `OUT`-is-`site/` guard is source-read, not +fixture-tested; Q25's census (46 rows / 25 X fetches) is cited, not re-run — no X page was +fetched this tick; all digests are dated readings from this host at the run clocks, and the +control's byte-identity to the live `site-ledger` is what anchors the fixture set to production. + +Three defects of my own, logged first in the deliverable: the first harness run died +`not found: block-5 None` because the receipt entries carry no `slug` (`slug_for` derives +`block-5` from `n`) — fixed with an `n=` selector; the first `protected-clash` fixture ran the +build before planting the file and reported exit 0 / 125 files — restructured so the plant +precedes the build; and `slug-sentinel`'s `x:slug:` die message is an artifact of the fixture, +recorded as finding 2 rather than normalised away. + +## Next + +- **Alexander's call, not mine:** publish, hold, or decline the patched builder. The ordering + guard is now checkable rather than a wait — **adopt `c4127c6c` into the shared build tree + first, then publish** — and Q28's result is the one-sentence guarantee that publish decision + can be taken on. +- **Q20** remains the top unclaimed item and is zephyrus-sparkborn's; I take nothing over it. +- **Q7, measured:** Q20 open (zephyrus's); Q9 blocked on the audio handover; Q13/Q19 gated on + Alexander; Q26/Q27/Q28 all gated on the same publish decision. The unclaimed executable set + is empty again; a successor is owed, and this record opens none — the successor should come + from a fresh measurement, not from this run's own finding. + +## Ask + +1. **Alexander — adopt `c4127c6c` into the shared build tree, or hold?** It is the difference + between an uncited-token failure leaving 20 files on disk and leaving 0, plus Q28's + one-sentence guarantee. Scratch until you say so. +2. **Nothing asked of zephyrus-sparkborn this tick.** His lane is Q20. + +## Run detail — Q28 + +**Clock and host.** All fixtures and the control from this host, 2026-10-11 ~04:0x–04:2x UTC. +Working tree `/root/crucible/q28/` (19 fixture trees under `fixtures/`, control build in the +scratch root, every body kept beside the scripts). Repo at `/root/troupe-standup`, branch +`main`, HEAD before this run `a3b45b3`, working tree clean. + +**Scripts, all re-runnable.** `q28-probe.py` (data facts), `q28-fixtures.py` (19 fixtures + +control, emits `Q28-RESULTS.json`), `q28-exclusions.py` (7 exclusions + the 2 corrections, +emits `Q28-EXCLUSIONS.json`), `q28-count-q27.py` (the Q27 breakdown recount), `q28-which.py`. + +**Data facts measured before any fixture** (`q28-probe.py`): 121 entries; publication_status +121 × `cleared`, 0 research-only; ledger 5 block / 3 dollar_receipt / 22 timeline / 91 magazine; +status 115 documented / 5 testimony_only / 1 corroborated; 113 entries carry `sort_date`, 112 +`date`, 113 are `body_kind: summary`, 1 is the quote branch; `coverage.gaps` holds 4 strings. + +**Counts, recomputed not accepted.** 19 fixtures (16 negative / 3 positive); 7 exclusions; 2 +corrections. Negatives: 16 × exit 1, 0 builder writes. Positives: 3 × exit 0, 125 files. +Control: exit 0, 125 files, digest `91ecf6bf939a2a499983066a2331bb953eab8a4ca85c66a8a19f42cb1b28f7a8`, +`diff -rq` vs `/root/stackchain-legends-build/site-ledger` silent. + +**Live archive, re-measured this run:** +`https://alexanderwhitestone.com/stackchain/blocks/` → **200 / 34,488 B / sha256 +`4f764ef4dfb9c08b2654ff0783550d20ad1bb7a31cb0c32070974a5fe451557e`**. Shared tree: +`build_blocks.py` still `97fedb5dd5e85d2b10071e8e4904b3a9b1573072149e722fbece93eaf0774672`, +`blocks.json` `63c9cee6103a6824c90c71440fa983d2f5592e380f9c3fb40f7ad366ae41723d`, +`find /root/stackchain-legends-build -newermt '2026-10-11 02:00' -type f` → nothing. +`decisions/` and `inbox/` untouched; nothing executed; no other party's file edited. + +Files written this run: + +- `recoveries/render-site-channels.md` (new — the deliverable) +- `WORK-QUEUE.md` (Q28 status block → DONE) +- `checkins/2026-10-11-merlin.md` (this section) diff --git a/recoveries/render-site-channels.md b/recoveries/render-site-channels.md new file mode 100644 index 0000000..c1b44b5 --- /dev/null +++ b/recoveries/render-site-channels.md @@ -0,0 +1,185 @@ +# Q28 — The channels the entry walk cannot see + +*Merlin, 2026-10-11. Scratch tree `/root/crucible/q28/`; builder `build_blocks_hard.py` +(sha256 `c4127c6c9325ed9f8cab03b80b454cccde0f9f1e768289ff216d2fb79e78dbf2`, 29,174 B — the +Q27 scope-clause patch, copied in byte-identical and verified). `blocks.json` +(`63c9cee6103a6824c90c71440fa983d2f5592e380f9c3fb40f7ad366ae41723d`, 278,459 B) read-only. +Nothing published, nothing staged, no shared-tree edit, no `decisions/` or `inbox/` action.* + +## The guarantee, in one sentence + +**Any string containing `{{` or `}}` anywhere inside a `blocks.json` entry — at any nesting +depth, in any field, checked before a single byte is written — kills the build; the only +tokens that ever ship are well-formed `{{x:HANDLE}}` tokens inside the four prose panels of +a summary-branch entry naming a handle the ledger cites somewhere.** + +The three guards that enforce it, printed from `build_blocks_hard.py`: + +``` +:192-225 check_tokens(b, slug) — walk(b, "") recurses dicts/lists; a string with a + sentinel dies unless its path is in panels_for(b), + then dies again if TOKEN_RE leaves residue. +:228-234 check_gaps(data) — the one non-entry string channel: coverage.gaps[i]. +:151-169 check_uncited(b, slug, cited) + — same TOKEN_RE scan, same message as expand_prose's + die(), run above OUT.mkdir so no partial tree. +:204 walk(v, ...) — recurses on the VALUE only; keys are never visited. +:292-304 build() — check_gaps, then check_tokens and check_uncited over + every entry, all above OUT.mkdir / the rmtree. +``` + +## Result + +**20 channels: 13 covered by fixture (19 fixtures), 7 excluded with a measured command.** +Every negative fixture exits 1 and writes **0 files**; the one fixture whose output directory +holds a file at failure (`protected-clash`) holds the file *it planted*, which the guard +refused to clean — the builder itself wrote nothing. The no-token control is byte-identical +to the live `site-ledger` (digest `91ecf6bf939a2a499983066a2331bb953eab8a4ca85c66a8a19f42cb1b28f7a8`, +125 files, `diff -rq` silent). + +## The channel table + +Each fixture is a fresh scratch tree: patched builder + one mutated `blocks.json`. Columns: +channel · guard · fixture · exit · files written · first stderr line. Malformed token `{{x:` +unless stated; cited token `{{x:arizonanhodl}}`; uncited `{{x:NotACitedHandle}}`. + +| # | channel | guard | fixture | exit | files | first stderr line | +|---|---|---|---|---|---|---| +| 1 | `coverage.gaps[i]` — index Known-gaps list | `check_gaps` | `gaps-sentinel` | 1 | 0 | `coverage.gaps[0]: token sentinel {{ in a field that is not a prose panel (panels: body, body_provenance, plain_summary.text, uncertainty)` | +| 2 | `slug_for()` → canonical href | walk (`slug`) | `slug-sentinel` | 1 | 0 | `x:slug: token sentinel {{ in a field that is not a prose panel` | +| 3 | `slug_for()` → sitemap `loc` | walk (`slug`) | `slug-sentinel` | 1 | 0 | *(same fixture — one slug feeds all four slug-derived landings)* | +| 4 | `slug_for()` → index `li` id | walk (`slug`) | `slug-sentinel` | 1 | 0 | *(same fixture)* | +| 5 | `slug_for()` → pager hrefs | walk (`slug`) | `slug-sentinel` | 1 | 0 | *(same fixture)* | +| 6 | `sortable[:4]` → index year heading | walk (`sort_date`) | `sortdate-sentinel` | 1 | 0 | `magazine-001:sort_date: token sentinel {{ in a field that is not a prose panel` | +| 7 | `esc(prev/nxt["n"])` → pager link text | walk (`n`) | `pager-n` | 1 | 0 | `magazine-002:n: token sentinel {{ in a field that is not a prose panel` | +| 8 | `safe_url()` → `body_source_url`, non-https shape | `safe_url` | `url-nonhttps` | 1 | 0 | `block[30]: source URL must be https, got '{{x:'` | +| 9 | `body_source_url`, https-with-token shape | walk | `url-https-token` | 1 | 0 | `magazine-001:body_source_url: token sentinel {{ in a field that is not a prose panel` | +| 10 | receipt arithmetic formatted strings (`f'${usd}'`, `f'{price}'`, `f'{calc:,} sats'`) | walk (`receipt.usd`) | `receipt-usd` | 1 | 0 | `block-5:receipt.usd: token sentinel {{ in a field that is not a prose panel (panels: body_provenance, plain_summary.text, uncertainty)` | +| 11 | `title` — head `