Version. 0.1 · Date. 2026-08-11 · Author. Claude.ai (drafting) / Marvin Percival (approving).
Target. /Users/dunin7/loomworks-engine, branch main.
Baseline. Engine f9372d6. CC confirms at Step 0.
Companion to. B-77's build-list entry (build list v0.55 onward) and the B-8 slice-two scoping read that found it — the source for every fact below. Where this CR and that read disagree, the read governs.
Charter. Autonomous regime. Status. Ready for CC execution, with a read-first Step 1.
The Companion's assembled prompt is cached process-lifetime with no TTL, invalidated solely by current_engagement_version. Seed writes land on the administrative engagement's log. So the cache watches one log and the thing it caches changes on another.
It is saved today by two accidents:
revise_engagement on the working engagement (seed_amendment.py:146-153 → creation.py:920-927), bumping the version the cache checks.seed_ref at creation (creation.py:1058).
For an engagement whose seed_ref is unpinned — which the bootstrap paths construct — a new seed version changes what the loader returns without bumping the version the cache checks. The Companion would speak from a superseded seed indefinitely, with no expiry to eventually correct it.
Latent, not live. The exposure is one bootstrap change away, and neither accident that prevents it is recorded as a guarantee anyone is maintaining.
The Companion speaking from a superseded seed is the product asserting the engagement is committed to something it is no longer committed to. The seed is the foundation document; the prompt is where its content becomes what the Companion says.
And it fails silently in both directions. Nothing errors, nothing looks stale, and the Operator sees a correct current seed on the surface while the Companion speaks from the old one. That is the shape this project has now caught repeatedly: the wrong state and the right state render identically.
Three candidate shapes, and the CR does not pre-decide between them because the deciding facts are in the code:
seed_ref on every path including bootstrap, and make the convergence call explicit rather than incidental.CC reports which the code supports, with reasoning. Option 3 is not sufficient alone — it removes today's exposure without fixing the mechanism, and leaves the next unpinned path re-creating it. It may be worth doing alongside one of the others.
Also establish: what else the cache holds besides seed content. If it caches things invalidated correctly today, a remedy that widens the key may cost more recomputation than the defect costs. Report the trade rather than assuming either way.
Halt if the remedy requires changing where seed writes land. That is a substrate decision, not a cache fix.
Whichever remedy Step 1 supports, plus:
A test that fails if the cache serves a superseded seed. Not "the cache invalidates when the version bumps" — that tests the mechanism that already works. The test must stage the actual defect: an unpinned seed_ref, a seed amended, and the assembled prompt still carrying the old content. Observed failing against current code, or the test is not testing the defect.
Record the two accidents as what they are. Whatever the remedy, the completion note names that convergence-calls-revise and pin-at-creation were preventing this incidentally, so a future change to either is not read as harmless.
B-69 applies directly — this CR is entirely inside a Kind B contact point. Record what changed about it and what did not. Specifically: fixing the cache means the Companion stops speaking from a superseded seed, but nothing about what happens to already-derived artefacts when a seed moves is settled here. Say so plainly.
| Step | What | Mode |
|---|---|---|
| 0 | Pre-flight. | Auto |
| 1 | Read per §3. Report the remedy, the trade, and what else the cache holds. Halt if seed-write location must change. | Auto, conditional halt |
| 2 | The remedy. | Auto |
| 3 | The defect test per §4, observed failing first. | Auto |
| 4 | Full engine suite; ruff 0; mypy at/below baseline. Report any recomputation cost if the key widened. | Auto |
| A | Checkpoint. | Checkpoint |
| 5 | Tag cr-2026-202-b77-prompt-cache. Push. Watch the CI run and report its result. | Auto |
seed_ref engagement whose seed is amended gets a Companion prompt carrying the new seed — proven by a test that fails against current code.
Execute CR-2026-202 v0.1 at ~/Downloads/cr-2026-202-loomworks-b77-
prompt-cache-v0_1.md. Confirm the CR number first.
B-77: the Companion's prompt cache is invalidated by
current_engagement_version, but seed writes land on the administrative
engagement's log. It watches one log while the thing it caches changes
on another. Saved today by two accidents — convergence incidentally
calling revise_engagement, and operator-created engagements pinning
seed_ref. Bootstrap paths construct unpinned refs.
This is not a caching bug in its consequence: the Companion would speak
from a superseded seed indefinitely, with no TTL to correct it, while
the Operator sees the current seed on the surface. Wrong state and right
state render identically.
Step 1 picks the remedy from three candidates — invalidate on the log
that changes, include the resolved seed version in the key, or make the
two accidents into guarantees. The third is NOT sufficient alone: it
removes today's exposure without fixing the mechanism and leaves the
next unpinned path re-creating it. It may be worth doing alongside.
Also report what else the cache holds. If a widened key costs more
recomputation than the defect costs, that's a trade I want stated, not
assumed either way.
HALT if the remedy needs seed writes to land somewhere else — that's a
substrate decision.
§4's test is the acceptance criterion that matters: stage the actual
defect (unpinned seed_ref, seed amended, prompt still carrying old
content), not the invalidation mechanism that already works. Observed
failing against current code or it isn't testing the defect.
§6: this CR is entirely inside a B-69 Kind B contact point. Record what
it changes and what it leaves open — fixing the cache does not settle
what happens to already-derived artefacts when a seed moves.
DUNIN7 — Done In Seven LLC — Miami, Florida CR-2026-202 — B-77 prompt cache — v0.1 — 2026-08-11