Context
The check-ticket-archaeology.mjs guard (built via #12294) catches decay-prone ticket/Epic/Discussion/ADR refs in durable .mjs comments/JSDoc. Two gaps make it leak:
- It scopes to staged-ADDED lines (#13717/#13718) — so touching a pre-drifted file only gates your new anchors and leaves the file's grandfathered ones. That freezes the debt (240 grandfathered anchors repo-wide today) instead of reducing it.
- It runs only in
.husky/pre-commit — git commit --no-verify fully bypasses it (empirically: PR #14273 shipped 5+ #14186 anchors that way; 6th family-wide recurrence).
Operator directive (2026-06-28): this is the boy-scout rule and it is NOT optional — touch a file, clean ALL its ticket-archaeology, fully intentional, exactly like block-formatting (check-block-alignment already whole-touched-file-scans and forces the fix). Scope is all touched files in a PR, NOT the entire repo.
The Problem
A debt-freezing added-lines gate + a --no-verify-bypassable pre-commit-only layer. The fix is (a) make the gate whole-touched-file so it reduces the 240 as files are naturally touched, and (b) add a CI mirror so the merge-gate is bypass-proof.
The Architectural Reality
buildScripts/util/check-ticket-archaeology.mjs — guard. Default-mode (whole-repo find) + staged-mode (file-args, currently filters to getStagedAddedLines). Exports findTicketRefs / TICKET_PATTERNS / ESCAPE_MARKER. Comment-context-only (string literals — e.g. test.describe('…#N') — already exempt).
check-block-alignment.mjs --staged — the precedent: whole-touched-staged-file (forces fixing the file's full drift). The archaeology gate must match this shape.
- Data path:
data-sync-pipeline.yml + SyncService sync_all commit generated resources/content/ (legitimately full of ticket-refs) with --no-verify + [skip ci]. They need a targeted skip for the archaeology gate (cleaner than blunt --no-verify).
- Sibling CI-lint:
.github/workflows/skill-manifest-lint.yml, check-retired-primitives.yml.
The Fix
- Whole-touched-file — remove the staged-added-lines filter; scan each touched in-scope file in full (revert the #13717 scoping for this guard; it matches
check-block-alignment). Reuse the existing comment-context + ESCAPE_MARKER + TICKET_PATTERNS.
- CI mirror —
.github/workflows/ticket-archaeology-lint.yml: on pull_request → dev, run the guard over the PR's touched in-scope files (whole-file), mirroring skill-manifest-lint.yml.
- Skip-flag — a
--skip flag or NEO_SKIP_TICKET_ARCHAEOLOGY=1 env honored by the guard; wired into data-sync-pipeline.yml + SyncService.sync_all so the generated-data class bypasses the archaeology gate specifically.
Contract Ledger Matrix
| Target Surface |
Source of Authority |
Proposed Behavior |
Fallback |
Docs |
Evidence |
check-ticket-archaeology staged/CI scope |
the guard |
whole-touched-file (was: added-lines) |
— |
script --help |
unit test: a grandfathered anchor on an untouched line of a TOUCHED file is now flagged |
--skip / NEO_SKIP_TICKET_ARCHAEOLOGY (NEW) |
the guard |
bypass for the generated-data class |
gate runs (default) |
script --help |
data-sync / sync_all commit succeeds with the flag |
ticket-archaeology-lint.yml (NEW CI) |
.github/workflows/ |
fail a PR whose touched files carry archaeology |
none — new gate |
the workflow |
a PR with an anchor fails |
Decision Record impact
none — tooling/CI. Aligns with the §15.6 Source-comment intent filter (learn/agentos/AGENTS_ATLAS.md). Note: supersedes #13717's added-lines-scoping for this guard per the operator's boy-scout directive (the churn #13717 avoided is now the intended debt-reduction mechanism).
Acceptance Criteria
Out of Scope
- A bulk pass over all 240 grandfathered anchors (they reduce organically as files are touched — that's the point).
- Block-alignment / whitespace CI-mirrors (separate; this is archaeology-only).
- The autonomous-loop CommitGate (#9844 — different concern).
Avoided Traps
- Diff-vs-base / added-lines-only — REJECTED (my own first draft): it freezes the 240 grandfathered debt forever. The operator's boy-scout whole-touched-file is intended, like block-formatting.
- Whole-repo CI scan — REJECTED: 240 anchors → false-fails every PR. Scope is touched-files-in-the-PR.
Related
#12294 (guard), #13717/#13718/#12609 (added-lines scoping — superseded here for this guard), #13816 (error msg), #9844 (autonomous CommitGate — different), PR #14273 (6th-recurrence anchor).
Live latest-open sweep: checked latest 20 open issues 2026-06-28; no equivalent. A2A in-flight claim sweep: none on this scope.
Origin Session ID: f4bc5569-9c5f-477b-a810-7fb084867d6a
Retrieval Hint: "boy-scout ticket-archaeology whole-touched-file CI gate data-sync skip"
🤖 Authored by Ada (@neo-opus-ada · Claude Opus 4.8, Claude Code).
Context
The
check-ticket-archaeology.mjsguard (built via #12294) catches decay-prone ticket/Epic/Discussion/ADR refs in durable.mjscomments/JSDoc. Two gaps make it leak:.husky/pre-commit—git commit --no-verifyfully bypasses it (empirically: PR #14273 shipped 5+#14186anchors that way; 6th family-wide recurrence).Operator directive (2026-06-28): this is the boy-scout rule and it is NOT optional — touch a file, clean ALL its ticket-archaeology, fully intentional, exactly like block-formatting (
check-block-alignmentalready whole-touched-file-scans and forces the fix). Scope is all touched files in a PR, NOT the entire repo.The Problem
A debt-freezing added-lines gate + a
--no-verify-bypassable pre-commit-only layer. The fix is (a) make the gate whole-touched-file so it reduces the 240 as files are naturally touched, and (b) add a CI mirror so the merge-gate is bypass-proof.The Architectural Reality
buildScripts/util/check-ticket-archaeology.mjs— guard. Default-mode (whole-repofind) + staged-mode (file-args, currently filters togetStagedAddedLines). ExportsfindTicketRefs/TICKET_PATTERNS/ESCAPE_MARKER. Comment-context-only (string literals — e.g.test.describe('…#N')— already exempt).check-block-alignment.mjs --staged— the precedent: whole-touched-staged-file (forces fixing the file's full drift). The archaeology gate must match this shape.data-sync-pipeline.yml+SyncServicesync_allcommit generatedresources/content/(legitimately full of ticket-refs) with--no-verify+[skip ci]. They need a targeted skip for the archaeology gate (cleaner than blunt--no-verify)..github/workflows/skill-manifest-lint.yml,check-retired-primitives.yml.The Fix
check-block-alignment). Reuse the existing comment-context +ESCAPE_MARKER+TICKET_PATTERNS..github/workflows/ticket-archaeology-lint.yml: onpull_request→dev, run the guard over the PR's touched in-scope files (whole-file), mirroringskill-manifest-lint.yml.--skipflag orNEO_SKIP_TICKET_ARCHAEOLOGY=1env honored by the guard; wired intodata-sync-pipeline.yml+SyncService.sync_allso the generated-data class bypasses the archaeology gate specifically.Contract Ledger Matrix
check-ticket-archaeologystaged/CI scope--help--skip/NEO_SKIP_TICKET_ARCHAEOLOGY(NEW)--helpticket-archaeology-lint.yml(NEW CI).github/workflows/Decision Record impact
none— tooling/CI. Aligns with the §15.6 Source-comment intent filter (learn/agentos/AGENTS_ATLAS.md). Note: supersedes #13717's added-lines-scoping for this guard per the operator's boy-scout directive (the churn #13717 avoided is now the intended debt-reduction mechanism).Acceptance Criteria
data-sync-pipeline.yml+sync_alluse the targeted skip-flag (not relying solely on blunt--no-verify) for the archaeology gate..github/workflows/ticket-archaeology-lint.ymlfails a PR whose touched files carry archaeology; passes when clean.Out of Scope
Avoided Traps
Related
#12294 (guard), #13717/#13718/#12609 (added-lines scoping — superseded here for this guard), #13816 (error msg), #9844 (autonomous CommitGate — different), PR #14273 (6th-recurrence anchor).
Live latest-open sweep: checked latest 20 open issues 2026-06-28; no equivalent. A2A in-flight claim sweep: none on this scope.
Origin Session ID: f4bc5569-9c5f-477b-a810-7fb084867d6a Retrieval Hint: "boy-scout ticket-archaeology whole-touched-file CI gate data-sync skip"
🤖 Authored by Ada (@neo-opus-ada · Claude Opus 4.8, Claude Code).