Commit graph

14 commits

Author SHA1 Message Date
29b4ac91b3
fix: round 7 of the release review of 6.3.0, for 6.3.1
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>
2026-10-11 09:11:57 +02:00
cb68c4f125
fix(execute): the Phase 8 payload goes on stdin; /trekreview findings closed
/trekreview of 5680591..84a0621 (verdict WARN: 0 BLOCKER, 3 MAJOR, 1 MINOR,
1 MAJOR suppressed as unverified for length only). All closed red -> green:

- Suppressed MAJOR 1d0171a7 (verified live): Phase 8 spliced {plan-path}
  into a single-quoted --payload. A lone quote broke the shell parse (event
  lost, no written:false to report); a quoted pair ran a command
  substitution and still reported written:true. event-emit now reads
  `--payload -` from stdin and the three Phase 8 blocks pass the payload
  through a quoted heredoc. Checked under bash and zsh.
- 570ba19b: the SC5 set-step extractor read line by line and never saw the
  wrapped Step 0 sentinel (`blocked`); it now matches across the break and
  the test asserts `blocked` is read.
- c69a865a: the Phase 9 line_ref in jsonl-schemas.md was 9 lines off. Both
  trekexecute rows are now pinned to the exact span by a test.
- 0004fa23 (MINOR): the gates_mode_flag_override block says what to do on
  written:false (print the reason, continue).
- emit() docstring no longer says failures are swallowed silently.
- 7ffaede5: chosen to KEEP the prose-only legacy `passed` tolerance, because
  a public-plugin run started under the 6.1.0 prose would otherwise re-run
  every finished step on resume; recorded as an accepted deviation in the
  (local-only) brief. No code change.

Suite 1400 (1398/0/2), was 1393.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-05 18:16:46 +02:00
27d586841a
fix(stats): event-emit lands without the env var and reports every failure
event-emit returned {written:false, reason:'CLAUDE_PLUGIN_DATA unset'} whenever the harness did not export the variable - the normal case for the Bash tool - so /trekexecute's Phase 8 events never landed. It now resolves the directory through stats-append's resolveStatsDir (one resolver; opts.path still wins, so intent-approval is unchanged). The CLI uses the realpath isMain() guard (the file:// guard was a silent no-op under a symlink or a path with a space) and exits 1 on every written:false - usage error, payload-not-json, failed write - instead of always 0. KNOWN_EVENTS gains main-merge-approved, main-merge-declined and gates_mode_flag_override, which /trekexecute emits by design. Header, intent-approval docstring (comment only), docs/operations.md and the README autonomy sentence (wrong state names, 'records each transition') updated.

Red: 10 of 20 tests fail on the pre-fix code - 7 new (CLI lands with CLAUDE_PLUGIN_DATA empty / absent, unwritable target exit 1, usage error exit 1, symlink, space path, known events) and 3 inverted contracts. Regression guards (green on arrival): never throws when unwritable; no second copy of the fallback directory name.

Inverted (the contract this changes, not deleted): emit with no CLAUDE_PLUGIN_DATA (silent skip) -> lands under a pinned HOME; never throws when unwritable -> a genuinely unwritable target (env {} now resolves to the real home); resolveStatsPath({}) === null -> the fallback path; malformed --payload exit 0 -> exit 1.

Readers checked: otel-export keys on 'event', yardstick counts only user_input, cache-analyzer and research-loop-cap name event-emit only in comments. Verify 268/268 (stats-event-emit, intent-approval, doc-consistency, otel-export-validators, yardstick). Suite 1376 (1374/0/2); non-hook lines in the real trekexecute-stats.jsonl 60 before and after.

Voyage order 20261005T104513Z-1250514346, plan step 2/5.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-05 17:35:11 +02:00
43e6a2b23a
fix(stats): a trekbrief record carries the order Voyage runs, written by the writer (green)
appendStatsRecord(kind, record, env, { cwd }): for kind trekbrief it drops
every order_* key the record came with and adds attributeOrder()'s three
keys (lib/stats/claimed-order.mjs), resolving the mailbox from the record's
project_dir when that lies inside cwd. Other kinds are written untouched.

The CLI guard compares real paths (realpathSync on argv[1] and on
import.meta.url). The old `import.meta.url === file://${argv[1]}` was a
silent no-op - exit 0, nothing written - under a symlink and under a path
with a space (measured 04.10). Valgt realpath fordi `resolve()` alone fixes
only the space.

stats-landing 15/15; intent-approval, claimed-order, proevesett green.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-04 19:50:32 +02:00
2337d7f2ac
feat(stats): the recorder finds the one claimed order Voyage runs (green) [skip-docs]
lib/stats/claimed-order.mjs reads <coord>/<mailbox>/orders/claimed/ the way
repo-mailbox's claim verb writes it (read, never called): the stem is the id,
the .claim sidecar gives claimed-at, every .md counts toward "several".
Mailboxes come from two independent git calls (toplevel basename, the claim
script's rule; and the main repo behind a linked worktree), with GIT_DIR /
GIT_WORK_TREE dropped and a 5 s timeout. A project_dir outside cwd cannot
steer the lookup. Never throws, never guesses, starts nothing.

Valgt: identity = file stem, not frontmatter, fordi the claim script moves
<id>.md and never reads the frontmatter; a quoted order-id would otherwise
never join.

claimed-order.test.mjs 20/20.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-04 19:49:11 +02:00
d906999036
fix(stats): M6 — trekbrief and trekplan records land where the yardstick reads
New lib/stats/stats-append.mjs: one record on stdin, appended to
<data dir>/<kind>-stats.jsonl. The data dir is CLAUDE_PLUGIN_DATA, else
~/.claude/plugins/data/voyage-ktg-plugin-marketplace (the yardstick's
default). A failed write exits 1 with a reason: reported, never silent.
/trekbrief Phase 7 and /trekplan Phase 12 now run it instead of
"append to ${CLAUDE_PLUGIN_DATA}/…; skip silently". intent-approval's
resolveApprovalDataDir delegates to the same resolver.

Chose a stdin heredoc over a --json argument because a JSON record in a
shell argument breaks on quotes in task text. Only trekbrief and trekplan
are rewired (økt 2's countable form needs exactly those two); the other
commands' stats prose is unchanged and docs/architecture.md says so.

Red a358059 7/7 → green 7/7. Suite 1208: 1206 pass / 0 fail / 2 skip.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-09-23 09:17:52 +02:00
0799d6e914 feat(stats): add claude-fable-5 to PRICE_TABLE 2026-07-02 17:15:36 +02:00
46d51f8088 feat(observability): opt-in token capture in Stop hook (VOYAGE_TOKEN_METER) 2026-06-26 14:42:58 +02:00
62ebc28e3f feat(stats): aggregate token/cost totals in cache-analyzer 2026-06-26 14:38:16 +02:00
708ba04571 feat(stats): add pure token-usage parser + cache-aware cost derivation 2026-06-26 14:32:10 +02:00
c909466c99 feat(voyage)!: bulk content rewrite ultra -> voyage/trek prose [skip-docs]
Sed-pipeline (16 patterns, longest-match-first) sweeper residuelle ultra*-treff
i prose, command-narrativ, agent-prompts, hook-kommentarer, doc-prosa.

Pipeline-utvidelser fra V4-prompten:
- BSD-syntax [[:<:]]ultra[[:>:]] istedenfor \bultra\b (BSD sed mangler \b)
- 6 compound-patterns for ultraplan/ultraexecute/ultraresearch/ultrabrief/
  ultrareview/ultracontinue uten -local-suffiks
- ultra*-stats glob -> trek*-stats glob
- Linje-eksklusjon redusert til ultra-cc-architect (Q8); session-state-
  eksklusjonen var over-protektiv
- File-eksklusjon utvidet til settings.json, package.json, plugin.json,
  hele .claude/-treet (gitignored + V5-territorium)

Q8-undantak holdt: architecture-discovery.mjs + project-discovery.mjs urort.
Filnavn-konvensjon holdt: .session-state.local.json + *.local.* preservert.

Manuell narrative-fix: tests/lib/agent-frontmatter.test.mjs linje 10
mangled "/ultra*-local" til "/voyage*-local" (ingen slik kommando finnes);
korrigert til "/trek*".

Residualer utenfor scope (V5 handterer): package.json + .claude-plugin/
plugin.json (Step 12-14 versjons-bump). .claude/* er gitignored
spec-historikk med tilsiktet BEFORE/AFTER-narrativ.

Part of voyage-rebrand session 3 (Wave 4 / Step 10).

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-05-05 15:08:20 +02:00
d22ec05fed feat(voyage)!: rename stats filenames, settings keys, hook prefixes [skip-docs]
- lib/stats/event-emit.mjs: STATS_FILENAME -> trekexecute-stats.jsonl + comment
- hooks/scripts/post-bash-stats.mjs: stats target + comment -> trekexecute-stats.jsonl
- lib/stats/cache-analyzer.mjs: help-text + comment -> trekexecute-stats.jsonl
- tests/lib/stats-event-emit.test.mjs (lines 104, 117): fixture assertions
- settings.json: ultraplan/ultraresearch -> trekplan/trekresearch keys + statsFile values
- tests/lib/doc-consistency.test.mjs: allowlist (line 83) + accessor cfg.ultraplan?.* -> cfg.trekplan?.* (lines 91, 93) — atomic-pair, prevents vacuous undefined assertions
- scripts/q3-cache-prefix-experiment.mjs: STATS_JSONL hardcoded path -> voyage data dir + trekexecute filename
- hooks/scripts/pre-bash-executor.mjs (2 lines), pre-compact-flush.mjs (2 lines), pre-write-executor.mjs (1 line): [ultraplan]/[ultraplan-local] stderr prefix -> [voyage]
- commands + agents/review-orchestrator.md + CLAUDE.md: prose stats filename literals -> trek* equivalents

Atomic per session-spec: settings.json scope keys + doc-consistency.test.mjs
allowlist + property accessors committed together to prevent silent vacuous
undefined-equals-undefined assertions.

Part of voyage-rebrand session 2 (W3.7 / Step 9).

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-05-05 14:49:03 +02:00
aa4f486f41 feat(spor-c): add Q3 cache-prefix experiment harness + analyser [skip-docs]
Implements Spor C of post-v3.4.0 roadmap. Zero-dep harness measures
CLAUDE_CODE_FORK_SUBAGENT cache-prefix preservation across 3 fork-children
with identical --allowedTools at 150-250K parent context.

Harness uses --append-system-prompt-file (avoids stdin buffer cap at
>200K bytes) + --exclude-dynamic-system-prompt-sections (prevents
per-child cache-prefix divergence from cwd/env/git-status).

Companion analyser summarizes accumulated ultraexecute-stats.jsonl:
percentile wall_time (p50/p90/max), total events, ISO time range.
Output: JSON via --json <path> CLI shim.

Result file is gitignored (*.local.md). Master-plan thresholds
(<= 1.5K positive / >= 3.5K negative) gate the v3.5.0 Path C decision.

Brief: .claude/projects/2026-05-04-spor-c-q3-cache-prefix-experiment/brief.md
Master-plan: .claude/projects/2026-05-04-post-v3.4.0-roadmap/master-plan.md
2026-05-05 09:27:32 +02:00
a8ae5b65f6 feat(ultraplan-local): add stats event-emit for autonomy lifecycle events
Step 6 of plan-v2 (ultra-pipeline-speedup).

lib/stats/event-emit.mjs (NEW)
  Atomic JSONL append to ${CLAUDE_PLUGIN_DATA}/ultraexecute-stats.jsonl.
  Every record carries:
    ts          : ISO-8601 timestamp (REQUIRED per SC4)
    event       : caller-supplied name
    known_event : true for { brief-approved, main-merge-gate, user_input },
                  false for everything else (still emitted — audit-complete)
    payload     : caller object (defaults to {})

  Stats failures NEVER block workflow: missing CLAUDE_PLUGIN_DATA, missing
  dir, mkdir failure, append failure → all return { written: false, reason }
  without throwing.

  CLI shim:
    node lib/stats/event-emit.mjs --event NAME [--payload JSON]
  Always exits 0 (telemetry is best-effort).

Tests: 12 (record-build + ISO-8601 ts + known/unknown distinction + silent
skip + dir-on-demand + CLI shim happy-path + bad-payload tolerance +
concurrent-append smoke).

[skip-docs]
2026-05-04 06:31:52 +02:00