Plan · for red-pen · 2026-07-06

Burn-down to Done

The machine that copies a practice’s website exists. What’s left is proving its promises with gates that can’t lie — and there is now a written bottom to burn down to: five promises, a closed list. This page asks for three calls, shows what’s confirmed broken vs. still a claim, and lays out the sprint order that ends with fairfax proven, once.

ALL THREE CALLS MADE (07-06) · anchor MERGED · board COMPLETE, receipts verified · Sprints 1 + 2 (worker-side) RUNNING · one input left: WP Engine SSH
00

The anchor, in one rule

Done = five promises hold on a real site — all pages there · exactly the same site · nothing pointing at the old provider · editable through the genome · leads actually arrive — and each promise is guarded by a gate that (a) a deliberate break provably turns red, forever, in CI, and (b) checks a list derived from the artifact itself, never written by hand. Clause (b) is this page’s one amendment to the anchor.
01

The story, start to finish

  1. Where we actually are. The URL → editable-copy machine landed July 4 — fairfax, all 246 pages, through committed code. What stopped us from calling it done: green lights kept turning out to be capable of lying, and each fix surfaced another. Last session you named the root cause — we never wrote down what “done” means. Now it’s written (the five promises, PR #1868), and this plan burns down to it.
    ↘ go deeper — exact repo state
    Trunk origin/main @ 09af74d75 (#1866 genome onboarding L2). Anchor: docs/ai/definition-of-done.md on draft PR #1868 (MERGEABLE, held for ratification). 16 open PRs total — dispositioned in Sprint 0 (see PR sweep at bottom). Live working tree is parked on a stale forms branch with local mods; Sprint 0 returns it to main. Canonical markdown of this plan: docs/ai/plans/burndown-to-done.md.
  2. The step back: every confirmed lie has one shape. The gate checked a list a human wrote, and the world outgrew the list. The produced repo’s “files to copy” list went stale when two imports were added last week — so the editable copy crashes on a fresh machine while every light stays green. The forms gate trusts a list of form plugins — so it approves forms whose submissions go nowhere. The route checker asks 4 hand-picked pages. The menu/accordion checker knows one page-builder’s selectors and counts silence as a pass. The leak hunt was six rounds of growing a skip-list — until we derived the complete surface list from the web standard, and it came back finite.
    ↘ go deeper — the five instances, with receipts
    1. PRODUCER_CLOSURE hand-list (assembly-line.ts:3097-3107, 10 entries) omits lib/rewrite-emission-ledger.ts (imported by produce.ts ~:75, added #1856) and lib/host-context.ts (imported by lib/url-map-scope.ts:5, added #1865) → ERR_MODULE_NOT_FOUND on clean checkout. Lead-verified on trunk bytes 07-06.
    2. Form gate isDeadForm (assert-form-endpoint-viability.ts:112-163) flags only 4 hand-chosen categories; CF7/Gravity pass unchecked; zero forms = vacuous pass. Independent check completed 07-06: “confirmed, worse than claimed.”
    3. routesToProbe hardcoded 4 routes (capture-rendered-outcome.ts ~:935) — in re-verification now.
    4. Interaction probe selectors tuned to one builder; all-skip aggregates to pass (rar-index.ts ~:1966-2069) — in re-verification now.
    5. The AJAX carve-out (AJAX_REPLAY_SEPARATE_SURFACE) is a hand-declared exception to byte-identity — and it’s exactly where another practice’s data (levineneuro.com ×19) rode into fairfax’s copy. Lead re-confirmed the contaminated fixture files on disk 07-06.
    6. The stranded-fact check (genome-shape-validator.ts:44-45) covers only a hand-listed set of fact types (TEXT_FAMILY_FACT_TYPES) — independent probe 07-06: an edit to a stranded phone fact lands in zero served bytes while EDIT-SMOKE stays green; the positive control (orphan sorted first) goes red, proving detection is filename-sort luck, not coverage.
  3. The amendment — the one thing fresh eyes add to the anchor. The anchor’s honesty rule (“every gate must be provably able to go red”) catches dead gates but not blind ones — a gate with a stale hand-list still goes red on the cases it knows; it just doesn’t know enough cases. So: a gate counts only if it’s break-proven and its checklist is derived from the artifact itself — the import graph, the page ledger, the capture record, the web standard. This kills the “next surface” ambush structurally. It’s the compiler’s founding lesson — don’t reconstruct the answer, capture it — applied to our own gates. With this clause added, I looked for a deeper plan under the anchor and did not find one.
    Your question, answered — does the Plato PR / quanta work help here? Yes: it mechanizes exactly half of this rule, and it’s on trunk as of today. Plato’s ledger industrializes clause (a) — it plants a real break, watches whether the check fires, deposits the verdict with the evidence attached (150 checks probed; after the #1870 correction: 86 alive · 39 real suspects · 25 honestly-unreachable; each verdict a look-up-able fact with its history preserved). Surviving breaks are also a scent for clause (b) — code a check never exercises shows up as breaks it never catches. But (b) itself is construction work per gate: deriving the checklist so the blind spot can’t exist. Detection is now industrialized; prevention is what Sprints 1–4 build. And the two instruments already converge: Plato’s suspects include the exact file where “all-skipped counts as pass” lives.
  4. The board is COMPLETE: 9 confirmed · 1 caught-downstream · 1 already-fixed · 1 honest. All twelve claims resolved, every receipt verified against trunk bytes by my own hands. The four that finished last are the sharpest — each would make a fairfax certificate false today: byte-checks anchored to our own re-fetch, not what the browser saw (the capture literally stores no response bodies) · the route check asks 4 hand-picked pages and nothing probes the rest over HTTP · the produced repo’s undo (promote/rollback) has never been executed by any gate · the crawler/share-tag check passes on an empty capture. One nuance: the menu/slider probe’s “all-skipped counts as pass” is real, but the certificate independently catches it downstream — not ship-false, still getting fixed at the source. And one piece of good news: the “certificate stays clean after bytes change” claim was true once and is already fixed on trunk — the re-checker drove the real tool and watched it go red on a single corrupted byte. Every new confirmation is another hand-written list the world outgrew.
    ↘ go deeper — the full burn-down table
    #ClaimPromiseStatus
    1Produced repo crashes on fresh checkout (stale vendored-file hand-list)4CONFIRMED · recent regression
    2Wrong-practice bytes ride the AJAX carve-out (levineneuro ×19)2CONFIRMED
    3Forms gate passes forms that deliver nowhere5CONFIRMED · cutover-blocking today
    4Blank-hero tripwire foolable (symptom of #2’s carve-out)2CONFIRMED · fix = close carve-out
    5Byte-checks anchored to our own re-fetch, not capture bytes (capture stores no bodies)2CONFIRMED · ship-false today
    6Route check hardcoded to 4 routes; nothing probes the rest over HTTP1CONFIRMED · ship-false today
    7Edit check samples one fact per type; stranded-fact edits land nowhere, stay green4CONFIRMED · blind spot, not cutover-false today
    8Promote/rollback never executed inside the produced repo (CI runs preview only)4CONFIRMED · ship-false today
    9Crawler/share-tag check passes on empty capture (all checks “if present”)1/2CONFIRMED · ship-false today
    10Menu/slider probe: all-skip counts as pass at the probe layer2MECHANISM REAL · certificate catches it downstream · fixing at source anyway
    11Certificate stays “clean” after the copy’s bytes changeDROPPED — already fixed on trunk; proven red on a planted break
    12Page-count gate (every source page present)1HONEST — audit-verified

    Rules of the board: a row flips to CONFIRMED only with a disk receipt I re-checked myself (file:line, re-run command, or structural proof). Confident negatives get the same bar. Anything phrased in pixels instead of instructions is rejected on sight. Full receipts: docs/ai/plans/burndown-to-done.md Layer 2.

  5. Your three calls — the sprints wait on these.
    1 ✅
    Ratify the five promises, amended — RATIFIED (your “yes,” 07-06)
    The list is closed, nothing is added without you, every fix lands as a gate meeting both clauses. The anchor doc now carries the amendment and your ratification stamp, and its PR is merging.
    2 ✅
    Fleet gates: sample-then-flow — CONFIRMED (your “agree with tier two, let’s do it,” 07-06)
    Tier 2a — a diversity sample (~10–15 sites picked by shape) proves no site shape escapes the gates, once; you glance the sample list before that phase runs. Tier 2b — every site then gets the battery as it flows through the factory. Nothing ships ungated; nobody audits 425 sites in a batch.
    3 ✅
    Forms scope — SCOPED; test inbox = digitalempathyleads@gmail.com (your “yeah,” 07-06)
    Building test-flag routing + delivery self-verification into the intake worker, on top of the fail-closed isolation already on trunk. Test submissions land only at the DE inbox — no customer-visible test email, by construction. One input still open: WP Engine SSH, needed when we read each practice’s current form + notification config; the worker-side build runs without it.
  6. The sprints — each ends “green and can’t rot,” or names its own gap.
    S0 · running now
    True the board
    The 7 re-checks finish; every receipt verified by my own hands before it counts. Sweep the 16 open PRs (mine what’s useful, close the rest with a pointer). Fresh top block in the state file. Exit: every claim CONFIRMED-with-receipt or DROPPED.
    S1 · ~a day
    The editable copy runs, provably (promise 4)
    Vendored-file list derived from the real import graph. New gate: clean-machine install + full edit round-trip (apply → preview → promote → rollback) inside the produced copy, in CI. Break-tests: remove a file → red; break rollback → red.
    S2 · on your details
    Leads actually arrive (promise 5)
    Internal-inbox test path + delivery self-check built into the intake worker. Form targets rewritten to the intake by construction. Plugin-trust gate retired; the new gate drives a real submission and watches it arrive, test-flagged, internal. Runs alongside S3 once unblocked (~1–2 days).
    S3 · ~2–3 days
    Nothing points home (promise 3)
    Eliminate by construction: compiler freezes everything local; the only allowed external references are attested live services on a small registry (one reviewed file); anything else fails the build. Gate: zero external hosts across the complete derived surface map — static over all bytes, confirmed by a real browser.
    S4 · ~1–2 days
    All there, exactly right (promises 1+2)
    Close the AJAX carve-out (kills the wrong-practice-data class and the blank-hero class at the root). Anchor byte-checks to what the browser captured at the source. Probe every page in the ledger over HTTP. Bind the certificate to the exact bytes it certifies. Scope firms up from S0’s receipts.
    S5 · ~a day
    The proof — fairfax, once
    Fresh capture → full pipeline → all five gates green → the deliberate-break battery proves each can go red → certificate → you walk it. DNS flip is yours to make any time after. Exit: “the machine exists,” provable by re-run. Then fleet (Tier 2) gets its own short plan — deliberately not planned today.
    ↘ go deeper — the gate contract behind each sprint
    Promise 1 (complete): page-count gate (already honest) + HTTP-served probe whose route list = the deploy ledger. Break: delete/500 one real route → red.
    Promise 2 (faithful): byte-identity including AJAX fixtures, anchored to source-capture bytes (never our own re-fetch); surface set = the capture record itself. Break: corrupt one served byte and one AJAX byte → red on both.
    Promise 3 (self-contained): zero-external-hosts over the spec-derived surface map; registry membership attested, never inherited. Break: plant an old-provider address in each surface class → red per class.
    Promise 4 (editable): produced-repo CI — clean install, produce, apply→preview→promote→rollback; vendored closure = import-graph reach; every fact must be reachable by an edit, not one sample per type. Break: missing file → red; out-of-genome byte change → red; broken rollback → red.
    Promise 5 (forms): end-to-end driven submit → observed arrival at the intake, test-flagged to the internal inbox; form census from capture, not a plugin list. Break: dead endpoint → red.
    Cross-cutting: the certificate binds every verdict to the exact deploy bytes + code version it certified; re-verify recomputes from current bytes. Break: mutate a byte after emit → re-verify red.
  7. What could go wrong — named, with the response in hand.
    Some of the 7 claims come back wrong
    Possible — the audit partly read a side branch. That’s Sprint 0’s whole job; Sprint 4 shrinks or grows accordingly, and the closed list bounds the growth.
    Forms meet realities we haven’t seen
    WP Engine internals, current intake routing. The isolation guard is already fail-closed; the unknowns sit in the email-forward leg — which is why Sprint 2 starts with your details, early, and runs alongside Sprint 3.
    The live-services registry balloons
    It starts as one reviewed file in the repo and stays that way until the fleet tier forces more.
    Fresh fairfax capture takes real wall-clock
    Capture-farm pacing, one per account. It runs in the background during Sprint 4 so Sprint 5 never waits.
  8. Where your word stands: all three calls made. The anchor is on trunk with your stamp. Sprint 1 (the editable copy runs, provably) and Sprint 2’s worker half (leads arrive, test-safely) are running. The single remaining input from you: WP Engine SSH — hand it over whenever, and the source-config leg of forms starts that moment. Everything else runs in my lane — progress counts, not questions.
02

Reference strip

Jump by type — same atoms as the story above.

Your 3 calls · Burn-down board · Gate contracts · Sprints · Risks · PR sweep · Environment notes

↘ PR sweep — Sprint 0 dispositions (my git lane; listed for visibility)
#1868 the anchor → fold red-pen + amendment, merge on ratification · #1867 gate-vacuity inheritance → aligned with this program, review + merge on green · #1846 slider fix → mine into S4, close · #1834/#1833 forms serving mechanism + spec → mine into S2, close · #1829 forms harness (conflicting) → mine into S2, close, return live tree to main · #1826 image-swap → superseded by merged #1831, verify + close · #1823 preview-serving cutover → park, reassess after Tier 1 · #1820 CI trim → rebase, merge if green · #1805 download-scan gaps → mine into S3, close · #1789/#1771 genome breadth → likely superseded by the merged breadth work, verify + close · #1747 → superseded by the One Door, close · #1746 → superseded by S4 reshaping, mine + close · #1738 docs fix → fold into state refresh, close.
↘ environment notes (for future sessions, not for you)
Re-verification workflow: wf_122a029d-128 (7 legs, fail-closed, receipts schema-forced; edit-applies done+cached, 6 legs resume after the 11:20am rate-limit reset via resumeFromRunId). Evidence: ~/.claude/handoffs/2026-07-06-session/. Plan worktree: ~/factory-worktrees/dod-plan. Plato for neuron via CLI from a neuron checkout (session MCP binds another snapshot). /tmp reaps mid-session — use ~/factory-clones / ~/factory-moments. Tests: node --import tsx --test.