Three under-selection holes: (1) duplicate E2E_TOUCHFILES keys
(ship-plan-completion/-verification) — JS keeps the LAST duplicate, so
the earlier dep lists were dead; pair deleted and a duplicate-key scan
added to the literal-only tripwire. (2) The five rehomed e2e files
didn't list themselves in their own dep lists, so editing the test
never selected it. (3) git C-escapes non-ASCII paths without
core.quotePath=false, so an accented filename matched no glob and
deselected its tests. Also updates the stale --retry cost comment.
Both sides shipped overlapping test-infra work in parallel; resolutions
compose intent rather than picking sides:
- free-tests.yml (both added): keep this branch's lane (canonical
strict-parallel runner, secretless, plain runner, ~2min) over main's
per-file-serial container loop (45min budget, hand-curated skip list,
needs GITHUB_TOKEN); ported main's git safe.directory insight.
- Dockerfile.ci Bun install: main discovered the installer IGNORES the
BUN_VERSION env var (the old form silently installed latest) — main's
arg-form mechanism + this branch's 1.3.13 target.
- parity baseline: both sides rebased after hitting the same silent
drift; adopted main's v1.64.1.0 union-normalized fixture and dropped
this branch's interim v1.64.0.0 capture. carve-guards caps: main's
tighter re-ratchets win (all four).
- touchfiles: kept this branch's three-file facade split; ported main's
pure-data removals (dead sidebar-agent entries, spec judge entry,
ship-idempotency) into touchfiles-data.ts.
- ship-idempotency SDK variant: main deliberately removed it as
redundant with the real-PTY test; adopted — dropped this branch's
rehomed copy and its periodic matrix row (the zombie-monolith deletion
stands; coverage-audit + triage rehomes verified untouched by main).
- e2e-tier-alignment: taught the new parent-mapper hard check main's
consolidated describeE2ETier()/e2eTierEnabled() self-gate shapes (the
helper's header names this file as a required recognizer).
- browse/test/compare-board.test.ts: quarantined behind
GSTACK_COMPARE_BOARD_TESTS=1 — all 16 tests fail identically on
origin/main solo on dev machines (blame protocol receipts in-file);
main's own CI lane skip-lists it. An always-red file would block every
PR now that free-tests is a required check.
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
design-consultation-research ($0.91/304s) and -preview ($0.89/481s) —
the two most expensive gate tests — plus office-hours-forcing-energy
(LLM-judge posture score; its sibling was already demoted) and
cso-full-audit (250s/$0.57; the targeted cso tests stay gate). Saves
~$8-12 and 10-15 min per gate run. The plan-*-finding-floor tests stay
gate deliberately: cheap insurance on the most-edited skill surface.
Housing files have no whole-file self-gates, so the runtime E2E_TIERS
filter handles both tiers; tier-alignment tripwire green.
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
extractSkillSections (fence-aware H2 scanner, loud-throw on missing
sections with available-heading list), extractSkillBody (drops the
shared generated preamble), extractSkillHead (frontmatter + first 30
lines, for routing fixtures). Pinned section lists per consumer, and
free-tier real-skill pins so a gen-skill-docs heading rename fails the
FREE suite instead of a paid run. skill-fixture.ts joins
GLOBAL_TOUCHFILES (fail-safe polarity: over-select).
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Editing the eval dep-list data no longer forces the full ~$38 /
30-45min suite (measured on 21.9% of recent commits). When
touchfiles-data.ts is in the diff, selection now evaluates the BASE
version (git show -> mkdtemp -> spawnSync bun child printing the four
maps as JSON — sync because e2e-helpers selects at module scope) and
JSON-diffs per key: added entries, edited dep lists, and tier flips are
selected; keys removed from all maps are reported, never silently
dropped; a GLOBAL_TOUCHFILES edit still runs everything.
FAIL-CLOSED with named causes: missing-base-ref, git-show-failed,
import-failed, shape-mismatch each degrade to run-all and print
'selection: global — touchfiles-data changed (<cause>)' (D9 — silently
expensive beats silently wrong, but never silently). eval:select prints
'selected N of M, reason: ...' + removed tests; --base scopes the
map-diff too.
The temporary conservative GLOBAL entry for touchfiles-data.ts is gone —
its changes route through the map-diff. 23 new free tests: pure-core
fixtures, selectTests wiring incl. a poison-injection guard, and a temp
git repo exercising every fail-closed cause end-to-end.
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
touchfiles.ts listed ITSELF in GLOBAL_TOUCHFILES, so adding one test's
dep entry forced the full ~$38 / 30-45min suite — measured on 21.9% of
recent commits (42/192). The self-reference existed because data and
logic shared a file: any edit COULD be a selection-logic change.
Now: touchfiles-data.ts (the four maps, literals only, zero imports —
the future map-diff target), test-selection.ts (matchGlob/detectBase
Branch/getChangedFiles/selectTests), and touchfiles.ts as a re-export
facade so all ~12 import sites are untouched. GLOBAL_TOUCHFILES drops
the self-ref, adds test-selection.ts (logic stays maximally
conservative), and TEMPORARILY adds touchfiles-data.ts until the
map-diff change lands. New free test pins the literal-only property
(comment-aware state-machine scan with a self-test) and facade export
parity (===), so neither can silently rot.
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>