2498e75f6a
* fix(daemon): keep run evidence off shared /tmp and reap it ourselves The test step wrote evidence to os.TempDir()/no-mistakes-evidence. The daemon's service unit exports only HOME, PATH, and proxy variables, so TMPDIR is unset and that resolved to the shared /tmp - which Ubuntu has mounted as a systemd tmpfs since 24.10, putting every screenshot and rendered-HTML artifact in RAM. Nothing in this program ever removed it, either. The directory was a fixed name that accumulated one subdirectory per run, cleaned only by an OS timer we do not control and that has no equivalent on Windows. On one developer machine that was 876 run directories over ten days, 823 of them empty: the test step creates the directory before the agent decides whether it has anything to write. Evidence now lives at <NM_HOME>/evidence/<runID>, owned by internal/paths like every other location. The app root is disk backed on macOS, Linux, and Windows alike, so there is no runtime.GOOS branch and the macOS path is not regressed - it improves, since /var/folders is periodically purged and that silently broke the local artifact paths older PR bodies fall back to. Cleanup is now ours, in three layers: a finished run's empty directory is removed at run cleanup, a reaper bounds the directory by age and count oldest-first after every run and at daemon startup, and the pre-relocation temp directory is drained under the same policy. All three reuse the existing pending/running guard, so a run still in flight is never touched. test.evidence gains local_root, retention, and max_runs. They are global-only: a repository does not get to name a filesystem path this machine's daemon writes to, nor set the retention budget for a directory every repository on the machine shares. There is deliberately no environment variable - the service unit preserves only proxy keys, so an env-gated value would be dropped on the next update. Also removes the second, independent copy of the evidence path in the agent steering preamble, which rebuilt it from os.TempDir() on its own. The executor now resolves the path once and both consumers read it. * no-mistakes(review): Protect unowned directories from evidence reaping * no-mistakes(document): Clarify managed evidence storage scope * no-mistakes: apply CI fixes * no-mistakes: apply CI fixes * fix(daemon): clean run evidence at the recovered-run completion boundary Evidence ownership claims cleanup runs after each run, but only the fresh-run defer called cleanupRunEvidence. A run parked at an approval gate when the daemon stopped is finished by resumeRecoveredRun, which has its own completion defer, so a resumed run kept its empty evidence directory until some later run or a restart happened to sweep it. There are exactly two completion boundaries and both are now covered. The regression test drives resumeRecoveredRun and asserts the directory is gone afterwards; every outcome of a resumed run shares that defer, so the boundary is the thing worth asserting on. * ci: give the test job a budget the Windows leg actually fits in The Windows leg was cancelled at timeout-minutes twice in a row with no verdict, on a suite where every package that reported had passed. It is process-spawn bound rather than compute bound, so it compiles every test binary and then runs the git-backed packages at roughly 10x their Linux cost, and 25 minutes no longer covered that. An evidence-free cancellation is worse than a slow job: it is reported as a check failure and reads as a defect in the change under test, which is exactly how it was read here. The cap stays a runaway guard rather than a target. Linux and macOS finish far inside it, 40 minutes still keeps a wedged runner well short of the six-hour default, and go test -timeout is deliberately unchanged so a genuine hang still produces a goroutine dump first. This does not close the coherence gap behind it: -timeout bounds each test binary while timeout-minutes bounds the whole job including compile, so total wall can still exceed the cap with no binary reaching its own deadline. Bounding per-job wall properly is follow-up work. * chore: pin review auto-fix to the product default in this repo The code default for auto_fix.review is 0 so review findings park for a human decision, but this repo carried no auto_fix block and therefore inherited whatever an operator set globally. With it enabled, a one-line CI timeout change drew a speculative review finding that the auto-fixer answered with a new DB table, a schema migration, and a new package, then spent three rounds finding errors in its own invention. None of it was asked for, and a parked finding would have surfaced the question instead of quietly answering it. Only review is pinned. The deterministic steps keep whatever the operator configured, because a lint or test finding has an objective checker and does not need a human to decide whether the fix belongs. * no-mistakes(review): Reject evidence roots inside managed worktrees * no-mistakes(document): Clarify evidence storage constraints
38 lines
2.0 KiB
YAML
38 lines
2.0 KiB
YAML
# no-mistakes' own dogfood config.
|
|
# Local Test is intentionally empty: the Test step is targeted validation of the
|
|
# requested intent (agent-driven smallest relevant checks + evidence), never a
|
|
# repository-wide regression suite. Broad race-enabled Go coverage stays in
|
|
# remote CI (`go test -race ./...` in .github/workflows/ci.yml) and remains
|
|
# mandatory before a PR is ready. See docs/src/content/docs/reference/repo-config.md
|
|
# (commands.test) and docs/src/content/docs/reference/pipeline-steps.md (Test).
|
|
# Lint and format stay explicit so those gates stay deterministic.
|
|
|
|
commands:
|
|
lint: "make lint"
|
|
format: "gofmt -w ."
|
|
|
|
# Pin review auto-fix to the product default so this repo does not inherit an
|
|
# operator's global override. Review findings park for a human decision; other
|
|
# steps keep their configured behavior.
|
|
auto_fix:
|
|
review: 0
|
|
|
|
# Documentation ownership map for the document step's placement policy.
|
|
document:
|
|
instructions: |
|
|
Configuration keys are owned by docs/src/content/docs/reference/global-config.md
|
|
(global fields) and docs/src/content/docs/reference/repo-config.md (repo fields).
|
|
Environment variables and the telemetry local/remote split are owned by
|
|
docs/src/content/docs/reference/environment.md.
|
|
The daemon lifecycle model (singleton lock, lifecycle guard, crash recovery)
|
|
is owned by docs/src/content/docs/concepts/daemon.md.
|
|
Agent-driving guidance is owned by the skill body in internal/skill/skill.go
|
|
and the live axi output strings; docs/src/content/docs/guides/agents.md keeps
|
|
only the canonical invariant sentences pinned by internal/cli/axi_guidance_test.go.
|
|
Guides and troubleshooting pages explain purpose and symptoms and link to the
|
|
owners above instead of restating their tables, examples, or key semantics.
|
|
AGENTS.md holds invariants plus pointers to the authoritative implementation
|
|
and regression tests. Do not duplicate generic command catalogs, but retain
|
|
its project-specific verification sequence and other load-bearing operating
|
|
guidance.
|