Round 7 (516dffa..45aa9e1, WARN: 12 MAJOR, 0 BLOCKER) and the fence defect
found while writing its review.md. Each fix began with a test that failed on
0f400d3 (v6.3.0); suite 2208 (2206/0/2), 14 tests more.
- Tests-only (operator 2026-10-11): the plan's Files: alone decides, and the
text says so (red-proof, trekexecute Sub-step B, step-implementer,
HANDOVER-CONTRACTS). red-proof no longer reads the step's diff, so a change
already in the tree when the step began no longer counts against it, and a
plan placed outside .claude/ reads the same. The round-6 test that had the
diff overrule the plan is rewritten to the new rule.
- The Files: reader keeps a plain file beside a backticked path
(", Dockerfile", "the CLI entry src/cli.mjs", "and Makefile"). Measured on
the 520 Files: fields in 182 plans: no field reads differently.
- Red proof reports a command its timeout killed as killed after the timeout,
not "could not start"; the release check tells a timeout from output past
its buffer and from another signal. One reading of a stop
(criteria-runner stoppedBy) for red proof, the criteria runner and the
release check.
- A trailing `# comment` is dropped in a backticked check too, and in a
command passed as written, so the words screened are the words run.
- The release check reads a relative --review in --repo.
- The 15-minute timeout is defined once (criteria-runner.mjs).
- The findings check reads each cited file once per validation.
- One isMain helper (lib/util/is-main.mjs) for every CLI: the 31 copies of
the realpath guard and the 20 modules still on the file:// guard, which
exited 0 having done nothing under a symlink or a path with a space.
- The Bash guard writes its no-one-to-ask refusal once, on a direct condition.
- The findings check ends a ```json block only at a fence on its own line, so
three backticks inside a JSON string no longer end it (also in 6.2.0).
- Brief-conformance notes: a test for test-lock green on exit 127 (it
passed at once; it fails when 127 is read as could-not-run); the prose now
names the git revision `@~1` as the one leading-@ exception.
Not changed: the example plan's steps 1-2 keep their tests-only warning
(operator decision 2026-10-09; the r5 test records it). Brief note 4 (a
Regression: whose runner is not installed goes to the fix rounds) is a
routing question for the operator.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Round 6 (v6.2.0..c3641ff, WARN: 11 MAJOR, 3 MINOR; 0 BLOCKER). The round-5
fixes hold (code-correctness-reviewer); three of the new MAJOR were side
effects of running checks with no shell. Each fixed behind a test that
failed first on c3641ff.
- git checks stay in the repo too: no path that climbs out with .., starts
at / or reads <rev>:../x, and no --no-index (both reviewers).
- A trailing `# comment` on a shell-fence line is dropped: with no shell,
its words made an honest check NOT RUN, among them the first check of the
shipped example plan.
- A glob reaches `node --test` only on Node 21 and later, which expands it
itself; on an older Node it is refused with that reason (engines >=18).
- With no shell, exit 126/127 is the test program's own: red proof reads it
as a red (the control run still tells an environment fault apart), the
done line and the test lock as a failure.
- A runner that could not start (not installed) is NOT RUN in the criteria
runner and not-run (exit 2) in regression-check, as red-proof and
done-line already said; never a red suite.
- Tests-only: a backticked `Makefile` alone in its entry is a path, and red
proof confirms the plan's tests-only reading against the step's own diff
(the altitude finding: the diff is a fact, the Files: prose is not).
- release-check stops a suite that never ends (15 minutes) and reads it as
not measured (exit 2).
- The two lines this release added to pre-bash-executor.mjs are ASCII.
- MINOR: git and the other runners share one plain-word pattern.
Not in this round: MINOR f00a2eb8 (shared norm/ticked-path and isMain
helpers) and MINOR on plan-review-dedup's repeated tokenizing.
Suite 2194 (2192/0/2).
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Round 5 (v6.2.0..d37e538, WARN: 11 MAJOR, 2 MINOR). The patching did not
converge (the same two places every round), so the operator chose a
structural fix on 2026-10-11. Each change behind a test that failed first.
- A check runs with no shell. criteria-runner's runCommand starts the runner
with the very words the screen checked (spawnSync(words[0], words.slice(1)),
without NODE_TEST_CONTEXT); Phase 7 criteria, Regression: (its exec copy is
gone, MINOR 0e98d5c7), proof of red, the done line and the test lock all
run through it. No quote, glob, tilde or variable can rewrite a checked
word any more. The screen stays and says why: a word that means something
else in a shell (quote, backslash, $, brace, leading ~) is refused; a glob
reaches only node --test, which expands its own patterns (sh read
`tests/.?/` as `tests/../`); no path climbs out with .. or starts at /;
a word starting with @ is refused (pytest reads @file as more arguments).
- The K6 plan-file sweep has v6.2.0's own Files: reader again (516dffa):
backticked paths, and plain words only in a field without them. The
shared reader from round 3 planned directories a description named and
dropped paths v6.2.0 planned. fieldPaths stays for the tests-only check,
with a path test on spans (`parse()`, `p.parse()` are no paths), plain
descriptions ignored when the field has backticked paths, dotfiles,
backslash paths and glued spans read.
- Skill frontmatter reads a value as YAML does: trailing space is nothing,
and a comment ends a plain value, a flow list or a block indicator
(`model: opus # pinned`). A comment that cuts a plain description, or is
the whole value, is still a hazard.
- release-check reads the diff with --no-renames: a test moved into an
allowed place after the review shows as removed.
- The example plan's step 2 heading no longer says "must FAIL initially";
steps 1-2 keep the tests-only warning (operator 2026-10-09, 73262b6).
Open: MINOR c1fef1ad (one shared isMain helper) is not in this round.
Measured: 0 of 463 Files: fields with backticked paths (520 fields in 182
plans across the marketplace repos) carry another path-like word.
Suite 2185 (2183/0/2).
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
voyage-lekerepo end-to-end trial (2026-10-06), report points 2, 3, 4, 9:
11 of 13 brief criteria were NOT RUN at review with no warning in /trekbrief;
a plan `git grep` criterion passed validator, gate and three critic rounds,
then felled the run in Phase 7; the End-to-end field and Phase 7's text
search never met; a prose Verify left the test command undefined.
- criteria-runner: runnableCheck() screens a declared check without running
it (same allowlist; an npm run script is not looked up at write time);
/bin/bash tests/<script> allowed; the plan report carries end_to_end,
verified when a passed criterion runs a step's End-to-end command (the
older text form still counts).
- plan-validator 1.8: PLAN_VERIFICATION_NOT_RUNNABLE,
PLAN_STEP_VERIFY_NOT_RUNNABLE, PLAN_END_TO_END_NOT_RUNNABLE,
PLAN_END_TO_END_NOT_VERIFIED (the gate inherits them).
- brief-validator: BRIEF_SC_NOT_RUNNABLE warning; /trekbrief offers a
tests/ script; brief-reviewer no longer proposes unrunnable commands.
- trekexecute: Phase 7 copies end_to_end from the runner; Verify's test
command is its first backticked span.
Measured on the trial's own brief and plan: 11 warnings (the 11 NOT RUN),
and the plan stops on V5 git grep and the unlisted End-to-end command.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Closes devils-advocate audit #4–#6 (MAJOR×MED). Four additive, non-breaking
changes to the v5.5 framing-alignment machinery:
1. --min-brief-version <ver> gate (audit #4). Opt-in version floor on
/trekplan + /trekresearch, forwarded to brief-validator as --min-version.
New opts.minBriefVersion warns BRIEF_VERSION_BELOW_MINIMUM (never blocks)
when a brief declares a version below the floor; trekreview exempt; absent
opt = no check. CLI shim parses --min-version and skips its value token in
filePath detection.
2. memory_alignment.status field (audit #5). brief-reviewer now emits
status: verified | n_a | contradictions so a score-5 N/A (no memory) is
distinguishable from a score-5 verified-aligned brief — the score≥4 gate
passes in both, status reveals whether the wrong-premise defense ran.
3. Document pre-2.2 = zero framing enforcement (audit #4). HANDOVER-CONTRACTS
§Handover 1 now states the producer-elective hole + two remedies. Also
fixes a stale "current is 2.1" line (current is 2.2).
4. Soften flagship overselling (audit #6). CLAUDE.md Context-Engineering
principle now hedges that main-context relief is asserted-by-design, not
measured (T1 PoC found Δ≈0); README carried no false claim to fix.
TDD: 8 new tests written failing-first (5 validator, 1 trekbrief status pin,
2 doc-consistency cross-file pins). Suite 691→699 (697 pass / 2 skip / 0 fail).
No flagship prose-pin added (deliberate, per S19 anti-bloat).
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01LqBYc8Ltrk7LipyJmGxXiB
Implements the CLAUDE.md cross-cutting invariant "brief framing must match
operator intent" as a controlled brief_version 2.1->2.2 bump (operator option A1).
Three defense layers, version-gated at >=2.2 so existing 2.0/2.1 briefs stay
valid (forward + backward compatible), mirroring the phase_signals >=2.1 gate:
- L1 framing: enum field (preserve|refine|replace|new-direction). Enum-checked
on any version when present (BRIEF_INVALID_FRAMING); missing at >=2.2 ->
BRIEF_MISSING_FRAMING. /trekbrief Phase 2.5 collects it BEFORE any brief prose
(non-skippable, even in --quick).
- L2 memory alignment: new brief-reviewer dimension 6 comparing brief Intent/Goal
+ framing against operator memory for explicit contradictions; degrades to
score 5 (N/A) when no memory context is supplied. Wired into Phase 4e gate
(memory_alignment.score >= 4).
- L3 obligatory ## TL;DR (<=5 content lines) at >=2.2; soft cap ->
BRIEF_TLDR_TOO_LONG warning.
trekreview briefs are exempt from the framing/TL;DR gate. Handover 1 PUBLIC
CONTRACT doc, README "What's new", and the CLAUDE.md invariant + agents table
(brief-reviewer 5->6 dimensions) updated to 2.2 (schema axis only; plugin
version badge + CHANGELOG remain S10).
Iron Law followed: validator tests red->green first. Tests 586 -> 606
(+20, 604 pass / 2 skip). claude plugin validate passes (pre-existing
CLAUDE.md root-context warning unchanged).
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01LqBYc8Ltrk7LipyJmGxXiB
Flip model: sonnet → model: opus across 20 agent files, 4 prose references
in commands (trekplan, trekresearch), trekendsession command frontmatter,
and CLAUDE.md tables. Aligns CLAUDE.md premium-profile row to actual
premium.yaml content (all-opus, which has been the case since v4.1.0 but
the doc was drift). Companion to VOYAGE_PROFILE=premium env-var (set in
~/.zshenv same day) — env-var governs orchestrator phase model; this
commit governs sub-agent models which are frontmatter-pinned and not
reachable by the profile resolver.
npm test: 516 pass, 0 fail, 2 skipped (unchanged from baseline).
Operator rationale: complete Opus coverage across all Voyage activity,
including the 20 sub-agents that the profile system does not control
(architecture-mapper, task-finder, plan-critic, scope-guardian,
brief-reviewer, code-correctness-reviewer, brief-conformance-reviewer,
review-coordinator, session-decomposer, plus the 6 researcher agents,
plus the 5 codebase-analysis agents).
Cost implication: sub-agent runs ~5x more expensive vs sonnet. Accepted.
Replace hardcoded Q1-Q8 in /ultrabrief-local with a section-driven
completeness loop (Phase 3) and a draft/review/revise loop with
brief-reviewer as stop-gate (Phase 4). Quality drives the interview,
not a question counter.
brief-reviewer now emits a machine-readable JSON block with per-dimension
scores (1-5) and detail arrays alongside the existing prose report;
planning-orchestrator continues to consume the prose verdict unchanged.
Phase 4 gate: all dimensions >= 4 AND research_plan = 5. On fail, a
targeted follow-up is generated from the weakest dimension's detail
field and the draft is re-reviewed. Max 3 review iterations bound cost;
exhaustion writes brief.md with brief_quality: partial and an explicit
Brief Quality section. Force-stop surfaces per-dimension findings before
the user chooses continue or partial.
Not breaking. /ultrabrief-local [--quick] <task> interface unchanged.
--quick now means compact start with escalation, not a max-N cap.
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>