mandrel 2.4.0 → 2.6.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (70) hide show
  1. package/.agents/audit-checklists/accessibility.md +29 -0
  2. package/.agents/audit-checklists/architecture.md +4 -5
  3. package/.agents/audit-checklists/clean-code.md +10 -0
  4. package/.agents/audit-checklists/data-model.md +22 -0
  5. package/.agents/audit-checklists/dependencies.md +11 -2
  6. package/.agents/audit-checklists/devops.md +4 -0
  7. package/.agents/audit-checklists/navigability.md +3 -0
  8. package/.agents/audit-checklists/performance.md +8 -11
  9. package/.agents/audit-checklists/privacy.md +3 -4
  10. package/.agents/audit-checklists/quality.md +2 -0
  11. package/.agents/audit-checklists/security.md +4 -5
  12. package/.agents/audit-checklists/seo.md +7 -1
  13. package/.agents/audit-checklists/sre.md +14 -12
  14. package/.agents/audit-checklists/ux-ui.md +4 -0
  15. package/.agents/docs/configuration.md +3 -0
  16. package/.agents/docs/workflows.md +4 -3
  17. package/.agents/schemas/agentrc.schema.json +17 -0
  18. package/.agents/schemas/audit-rules.json +134 -19
  19. package/.agents/schemas/audit-rules.schema.json +6 -2
  20. package/.agents/scripts/audit-labels-bootstrap.js +4 -4
  21. package/.agents/scripts/audit-to-stories.js +244 -19
  22. package/.agents/scripts/lib/audit-suite/checklist-threading.js +26 -3
  23. package/.agents/scripts/lib/audit-suite/dispatch-checklist.js +132 -0
  24. package/.agents/scripts/lib/audit-suite/index.js +1 -0
  25. package/.agents/scripts/lib/audit-suite/selector.js +290 -14
  26. package/.agents/scripts/lib/audit-to-stories/audit-lenses.js +2 -1
  27. package/.agents/scripts/lib/audit-to-stories/build-story-body.js +5 -1
  28. package/.agents/scripts/lib/audit-to-stories/dedupe-against-github.js +23 -3
  29. package/.agents/scripts/lib/audit-to-stories/finding-adapter.js +38 -0
  30. package/.agents/scripts/lib/audit-to-stories/ledger.js +256 -0
  31. package/.agents/scripts/lib/audit-to-stories/parse-audit-md.js +41 -7
  32. package/.agents/scripts/lib/audit-to-stories/seed-from-findings.js +20 -2
  33. package/.agents/scripts/lib/command-header.js +1 -1
  34. package/.agents/scripts/lib/config-settings-schema-delivery.js +21 -0
  35. package/.agents/scripts/lib/dynamic-workflow/performance-report-contract.js +5 -3
  36. package/.agents/scripts/lib/feedback-loop/audit-results-graduator.js +56 -0
  37. package/.agents/scripts/lib/findings/route-finding.js +108 -10
  38. package/.agents/scripts/lib/observability/runtime-friction.js +137 -6
  39. package/.agents/scripts/lib/orchestration/retro-proposals.js +0 -0
  40. package/.agents/scripts/lib/orchestration/run-epilogue.js +5 -19
  41. package/.agents/scripts/lib/orchestration/single-story-close/phases/post-land.js +11 -0
  42. package/.agents/scripts/lib/orchestration/story-close/phases/local-lens-review.js +81 -1
  43. package/.agents/scripts/lib/orchestration/story-close/phases/review-core.js +1 -0
  44. package/.agents/scripts/lib/orchestration/story-follow-ups.js +53 -13
  45. package/.agents/scripts/nav-registry-diff.js +449 -0
  46. package/.agents/workflows/audit-accessibility.md +243 -0
  47. package/.agents/workflows/audit-architecture.md +89 -71
  48. package/.agents/workflows/audit-clean-code.md +87 -53
  49. package/.agents/workflows/audit-data-model.md +198 -0
  50. package/.agents/workflows/audit-dependencies.md +143 -28
  51. package/.agents/workflows/audit-devops.md +109 -18
  52. package/.agents/workflows/audit-documentation.md +25 -53
  53. package/.agents/workflows/audit-navigability.md +78 -22
  54. package/.agents/workflows/audit-performance.md +207 -103
  55. package/.agents/workflows/audit-privacy.md +51 -13
  56. package/.agents/workflows/audit-quality.md +71 -61
  57. package/.agents/workflows/audit-security.md +94 -71
  58. package/.agents/workflows/audit-seo.md +80 -25
  59. package/.agents/workflows/audit-sre.md +99 -66
  60. package/.agents/workflows/audit-to-stories.md +44 -5
  61. package/.agents/workflows/audit-ux-ui.md +71 -17
  62. package/.agents/workflows/helpers/audit-dual-path.md +59 -0
  63. package/.agents/workflows/helpers/audit-self-check.md +70 -0
  64. package/.agents/workflows/helpers/audit-severity-scale.md +19 -0
  65. package/.agents/workflows/helpers/deliver-story.md +25 -0
  66. package/docs/CHANGELOG.md +23 -0
  67. package/package.json +1 -1
  68. package/.agents/audit-checklists/lighthouse.md +0 -15
  69. package/.agents/schemas/audit-results.schema.json +0 -69
  70. package/.agents/workflows/audit-lighthouse.md +0 -269
@@ -210,10 +210,37 @@ workflow owns **no** parallel dedup or footer-parsing code: the
210
210
  fingerprint, footer round-trip, and routing all live in that one shared
211
211
  module.
212
212
 
213
+ Dedup runs in **two stages** when a provider resolves (Story #4626): a
214
+ meaning-first **semantic candidate** pass (`searchCandidates`, wired to
215
+ [`lib/findings/semantic-issue-search.js`](../scripts/lib/findings/semantic-issue-search.js))
216
+ runs FIRST and widens the net across open + closed issues; the exact
217
+ **fingerprint / semantic-key** confirmation runs SECOND. A finding whose title
218
+ was reworded but whose *location* is unchanged still confirms against the Issue
219
+ that already tracks that location, because the audit filers stamp a
220
+ location-based `audit-semantic-keys` footer alongside the `audit-fingerprints`
221
+ footer. Close-time filings from the
222
+ [`audit-results-graduator`](../scripts/lib/feedback-loop/audit-results-graduator.js)
223
+ carry the same canonical `audit-fingerprints` footer, so a sweep recognizes a
224
+ graduator-filed issue and never re-files it.
225
+
213
226
  When no provider is available (e.g. air-gapped dev environment), pass
214
227
  `--no-provider` to the `--scan` step — every group is classified
215
228
  `create` and the operator is informed that dedupe was skipped.
216
229
 
230
+ ### Cross-run ledger
231
+
232
+ The `--scan` classifications only see *live* issues. To decay findings across
233
+ runs — recognizing re-detections, suppressing deliberately-rejected findings,
234
+ and flagging genuine regressions — the sweep folds each scan onto a committed
235
+ **ledger** (`baselines/audit-ledger.json`, the arch-cycles-baseline envelope
236
+ shape). Each entry is keyed by the finding's fingerprint plus a location-based
237
+ `semanticKey` and carries a lifecycle `status`
238
+ (`new | filed | fixed | accepted-risk | regressed`). A finding whose tracking
239
+ Issue was closed as `not_planned` becomes `accepted-risk` and is **suppressed**
240
+ on every later scan; a `fixed` finding that re-appears becomes `regressed`. The
241
+ ledger is written by the unattended `--auto` sweep and by any `--scan --ledger`
242
+ run; the plain `--scan` path leaves it untouched.
243
+
217
244
  ## Phase 7 — Summary & cleanup
218
245
 
219
246
  Persist `temp/audits/audit-to-stories-$(date +%Y%m%dT%H%M%S).md`
@@ -253,11 +280,23 @@ When the single-plan path ran, link the Story (or plan-run) the chained
253
280
  To run an unattended maintenance sweep, `/schedule` a nightly (or weekly)
254
281
  job that (1) runs the relevant `audit-*` lens workflows full-scope — no
255
282
  `--paths`, no change-set filter, so the whole target-set union is audited —
256
- writing their `temp/audits/audit-*-results.md` reports, then (2) invokes
257
- `/audit-to-stories` over those results to dedupe and route the findings.
258
- The host scheduler owns the cadence; this workflow owns the routing. (This
259
- paragraph folds in the `loops/nightly-audit.md` starter unit retired in
260
- issue 4482.)
283
+ writing their `temp/audits/audit-*-results.md` reports, then (2) invokes the
284
+ CLI's **`--auto` mode** over those results:
285
+
286
+ ```bash
287
+ node .agents/scripts/audit-to-stories.js --auto [--dry-run] \
288
+ [--glob "temp/audits/audit-*-results.md"] [--severity <floor>]
289
+ ```
290
+
291
+ `--auto` runs with **no interactive gates**: it resolves the severity floor
292
+ from `delivery.auditToStories.severityFloor` (default `high`, overridable with
293
+ `--severity`), applies the two-stage dedup, reconciles the cross-run ledger,
294
+ and prints a run-summary JSON (create / skip-open / skip-reoccurring /
295
+ suppressed-by-ledger tallies, plus the re-detected open Issue numbers an
296
+ operator may want a "re-detected" comment on). `--dry-run` performs zero GitHub
297
+ writes and skips the ledger write, emitting only the summary. The host
298
+ scheduler owns the cadence; this workflow owns the routing. (This paragraph
299
+ folds in the `loops/nightly-audit.md` starter unit retired in issue 4482.)
261
300
 
262
301
  ## See also
263
302
 
@@ -42,21 +42,54 @@ before this section existed.
42
42
  proceed with the full codebase-wide scan defined in the remaining
43
43
  steps.
44
44
 
45
- ## Step 1: Visual Consistency Check
45
+ ## Step 0: Discover the design-system SSOT (run first)
46
+
47
+ **You cannot audit "adherence to the design system" until you have located the
48
+ design system.** There is no universal baseline — a hardcoded `#3b82f6` is a
49
+ defect only when the project defines that colour as a token. Before any
50
+ detection, locate the consumer's design-system sources of truth and read what
51
+ they define:
52
+
53
+ - **Design tokens / theme:** a `tailwind.config.{js,ts}`, CSS custom properties
54
+ (`:root { --color-*, --space-* }`), a `theme/`, `tokens/`, or `design-system/`
55
+ directory, or a `styled-system` / CSS-in-JS theme object.
56
+ - **Component library:** the shared component directory (`components/ui/**`,
57
+ a published design-system package) that raw elements are expected to defer to.
58
+ - **Documented conventions:** `docs/style-guide.md` (and `docs/web-routes.md`
59
+ when routing copy is in scope) — the human-authored rules the mechanical
60
+ detectors below cannot infer.
61
+
62
+ Record the token names, the component roster, and the style-guide rules. Every
63
+ finding downstream is measured against *this discovered baseline*, not a generic
64
+ ideal. If **no** design-system SSOT exists, say so and downgrade findings to
65
+ "no baseline defined — recommend establishing tokens/components first".
66
+
67
+ ## Step 1: Mechanical detector battery, then LLM triage
46
68
 
47
69
  > Apply [`helpers/parallel-tooling.md`](helpers/parallel-tooling.md) when batching the scan below — independent reads belong in one turn, long shells run via `run_in_background` + `Monitor`.
48
70
 
49
- Scan frontend components for:
50
-
51
- - **Hardcoded Values:** Identify "magic" hex codes, font sizes, or spacing
52
- values that bypass the CSS variables/design tokens.
53
- - **Component Re-implementation:** Find places where custom HTML/CSS is used
54
- instead of the standard component library (e.g., custom button instead of
55
- `<Button />`).
56
- - **Interactive States:** Verify that all clickable elements have hover, focus,
57
- and active states.
58
- - **Typography:** Ensure font families and weights are used consistently
59
- according to the hierarchy.
71
+ Run the **mechanical detectors first** (cheap, deterministic greps that surface
72
+ candidates), then apply **LLM triage** to each candidate against the Step 0
73
+ baseline a mechanical hit is a *candidate*, not automatically a finding.
74
+
75
+ - **Hardcoded Values:** grep for raw `#hex` / `rgb()` colour literals and raw
76
+ `px` font-size / spacing literals **outside** the token/theme files. Each hit
77
+ is a candidate bypass of a defined token.
78
+ - **Component Re-implementation:** census raw HTML elements (`<button>`,
79
+ `<input>`, `<select>`, `<a>` styled as a button) versus the design-system
80
+ component that should replace them; a high raw-vs-component ratio is the
81
+ signal.
82
+ - **Inline-style census:** count inline `style=` / `style={{…}}` usages that
83
+ encode spacing, colour, or typography a token should own.
84
+ - **Interactive States:** scan for `:hover` (or `hover:` utilities) without a
85
+ matching `:focus-visible` / `focus-visible:` — a hover state with no keyboard
86
+ focus state is a candidate accessibility-of-interaction gap.
87
+ - **Typography:** flag font families / weights used outside the type scale.
88
+
89
+ > **Detector output is candidates.** Triage each with the discovered baseline
90
+ > before promoting it to a finding — a `px` value inside a token definition file,
91
+ > or a raw `<button>` inside the design-system's own `Button` implementation, is
92
+ > expected, not a defect.
60
93
 
61
94
  ## Step 2: UX Best Practices
62
95
 
@@ -66,14 +99,23 @@ Scan frontend components for:
66
99
  frustrating?
67
100
  3. **Loading States:** Are there skeletons or spinners for async operations?
68
101
  4. **Responsiveness:** Check layouts at mobile, tablet, and desktop breakpoints.
69
- 5. **Accessibility (UX-focused):** Focus on tab order, touch target sizes, and
70
- color contrast.
102
+ 5. **Accessibility (UX-focused):** Focus on tab order, touch-target sizes, and
103
+ whether interaction colours come from a sanctioned token. **WCAG conformance
104
+ is out of scope here** — semantic structure, ARIA correctness,
105
+ keyboard/focus operability, form labelling, media alternatives, and the WCAG
106
+ contrast-ratio verdict are owned by [`/audit-accessibility`](audit-accessibility.md).
107
+ This lens keeps token/component design-system adherence; defer every WCAG
108
+ success-criterion judgement to the accessibility lens so the two never
109
+ double-report.
71
110
 
72
111
  ## Step 3: Output Requirements
73
112
 
74
113
  Generate and save a highly structured Markdown audit report to
75
114
  `{{auditOutputDir}}/audit-ux-ui-results.md`, using the exact template below.
76
115
 
116
+ > Grade every finding's severity on the shared
117
+ > [`Critical | High | Medium | Low` scale](helpers/audit-severity-scale.md).
118
+
77
119
  ```markdown
78
120
  # UX/UI & Design System Audit report
79
121
 
@@ -85,15 +127,17 @@ tokens/components.]
85
127
  ## Detailed Findings
86
128
 
87
129
  [For every inconsistency or UX improvement identified, use the following strict
88
- structure:]
130
+ structure. Lead each title with the primary file the finding lives in:]
89
131
 
90
- ### [Short Title of the Issue]
132
+ ### `path/to/primary-file.ext` — [Short title of the issue]
91
133
 
92
134
  - **Dimension:** [e.g., Visual Consistency | UX Best Practices | Accessibility]
93
- - **Impact:** [High | Medium | Low]
135
+ - **Impact:** [Critical | High | Medium | Low]
136
+ - **Location:** `path/to/primary-file.ext:line`
94
137
  - **Current State:** [What is currently implemented and why it is sub-optimal]
95
138
  - **Recommendation & Rationale:** [The specific UI/UX change and how it improves
96
139
  premium feel or usability]
140
+ - **Acceptance signal:** [the command or observable that proves this finding is remediated — e.g. the token now applied in the rendered component, or a re-run of this lens]
97
141
  - **Agent Prompt:**
98
142
  `[A copy-pasteable, highly specific prompt to execute this UI change independently]`
99
143
 
@@ -107,3 +151,13 @@ structure:]
107
151
 
108
152
  This is a **read-only** audit. Provide the critique and implementation
109
153
  suggestions, but do not modify styles or components.
154
+
155
+ ## Self-cross-check (mandatory — filter false positives before you finalize)
156
+
157
+ Before you write the report artifact from the previous step, run the shared
158
+ adversarial self-cross-check over your Detailed Findings — see
159
+ [`helpers/audit-self-check.md`](helpers/audit-self-check.md). It defines the
160
+ per-finding evidence bar, the exclusion list, and the final re-open-and-drop
161
+ pass whose `kept <k> / dropped <d>` counts you record in the Executive
162
+ Summary, so the sequential single-pass path filters unverified findings just as
163
+ the orchestrated path's adversarial reviewer does.
@@ -0,0 +1,59 @@
1
+ # Audit lens execution strategy (dual-path)
2
+
3
+ > **Single source for the dual-path preamble (Story #4625).** Every lens whose
4
+ > `## Execution strategy (dual-path)` section points here shares this exact
5
+ > contract. Read `audit-<lens>` and
6
+ > `.claude/workflows/audit-<lens>.workflow.js` below as this lens's own name.
7
+
8
+ A lens that references this helper runs along one of two execution paths. Both
9
+ emit the **identical** report contract (the lens's Output Requirements step);
10
+ downstream consumers (`audit-to-stories`) are agnostic to which path produced
11
+ it.
12
+
13
+ - **Orchestrated (dynamic-workflow) path.** When Claude Code's
14
+ [dynamic workflows](https://code.claude.com/docs/en/workflows) are
15
+ available, the saved project workflow
16
+ `.claude/workflows/audit-<lens>.workflow.js` fans the lens's dimensions out
17
+ as parallel read-only subagents, runs an **adversarial cross-check** stage
18
+ (an independent agent reviews each dimension's findings and drops false
19
+ positives before they enter the report), then synthesises the report. The
20
+ orchestrator derives its per-dimension prompts from the *lens* markdown at
21
+ run time — the lens stays the single source of truth; the script does not
22
+ fork a second copy of the spec.
23
+ - **Sequential (single-pass) path.** When dynamic workflows are unavailable,
24
+ follow the lens's Steps turn-by-turn exactly as before. This is the default
25
+ fallback and changes nothing about the existing behaviour.
26
+
27
+ **Strategy selection** is computed by
28
+ [`lib/dynamic-workflow/capability.js`](../../scripts/lib/dynamic-workflow/capability.js)
29
+ (`selectAuditStrategy`). The orchestrated path is chosen only when the runtime
30
+ is Claude Code, `disableWorkflows` is not set (settings.json **or**
31
+ `CLAUDE_CODE_DISABLE_WORKFLOWS`), and the Claude Code version meets the
32
+ research-preview floor (`>= 2.1.154`). Any other runtime, a disabled setting,
33
+ or an older version degrades gracefully to the sequential path.
34
+
35
+ > **Capability degradation, not a contract shim.** This dual path is **not**
36
+ > covered by the No-Shim / hard-cutover rule in
37
+ > [`git-conventions.md`](../../rules/git-conventions.md). That rule forbids
38
+ > running two shapes of the *same contract* side by side. Here there is **one**
39
+ > report contract; only the *execution strategy* is selected from a runtime
40
+ > capability — the same pattern the protocol already endorses for live-docs
41
+ > fallback in [`instructions.md` §1.C/§1.D](../../instructions.md). The full
42
+ > capability-degradation rationale lives in the
43
+ > [`capability.js`](../../scripts/lib/dynamic-workflow/capability.js) module
44
+ > docstring; the orchestrated-run evidence and per-lens cost/precision gate
45
+ > verdicts live in [`docs/roadmap.md`](../../../docs/roadmap.md) (Part 3 —
46
+ > Dynamic-Workflow Orchestration).
47
+
48
+ **Forcing a path (for testing).** Set `MANDREL_AUDIT_STRATEGY=sequential` to
49
+ verify the fallback path with the feature notionally disabled, or
50
+ `MANDREL_AUDIT_STRATEGY=orchestrated` to pin the dynamic path. To exercise the
51
+ real disable signals instead, set `CLAUDE_CODE_DISABLE_WORKFLOWS=1` (env) or
52
+ `disableWorkflows: true` in `.claude/settings.json` and re-run the lens — both
53
+ degrade to the sequential path.
54
+
55
+ > **Read-only on both paths.** The lens is read-only (see its Constraint). The
56
+ > orchestrated subagents run in `acceptEdits` and inherit the session tool
57
+ > allowlist, but the workflow script grants the analysis agents only
58
+ > read/search tools (`Read`, `Grep`, `Glob`) — no write/edit/shell-mutation
59
+ > tools. The single write in an orchestrated run is the final report artifact.
@@ -0,0 +1,70 @@
1
+ # Audit finding self-cross-check (shared)
2
+
3
+ > **Single source of truth for the sequential-path false-positive guard
4
+ > (Story #4627).** Every non-retired audit lens references this file and runs
5
+ > this pass over its Detailed Findings before finalizing its report. The
6
+ > orchestrated dynamic-workflow path already fans out an independent
7
+ > adversarial reviewer; this pass gives the **sequential single-pass** path —
8
+ > the one consumer runs take, where the npm payload ships no per-lens
9
+ > `*.workflow.js` — the same false-positive filter, so a lens cannot report an
10
+ > unverified finding just because it ran single-pass.
11
+
12
+ You are your own adversarial reviewer. After you have drafted the Detailed
13
+ Findings but **before** you write the report artifact, re-open every finding
14
+ and hold it to the bar below. This pass is **read-only** — it filters and
15
+ tightens the findings you already have; it never invents new ones.
16
+
17
+ ## Per-finding evidence bar (keep or drop)
18
+
19
+ Keep a finding only when **all** of the following hold. Drop it otherwise.
20
+
21
+ - **Grounded location** — it names a concrete `path:line` (or a concrete
22
+ symbol / config key) that you have actually read, not a hypothetical or a
23
+ "somewhere in the codebase" claim.
24
+ - **Reproducible evidence** — the problem is backed by an observable: a tool
25
+ reading (a baseline row, a complexity/MI/duplication number, a failing
26
+ command), a quoted code snippet, or a specific standard it violates. A
27
+ finding whose entire basis is "this looks wrong" does not clear the bar.
28
+ - **In-scope** — when a change-set scope filter was supplied (the `Scope`
29
+ block resolved to a file list), the finding lives in that scope or a direct
30
+ dependency the lens explicitly reasons across. A finding outside the scope
31
+ filter is dropped, not reported.
32
+ - **Actionable** — the recommendation is specific enough to execute. Drop
33
+ vague exhortations ("improve error handling generally") that carry no
34
+ concrete change.
35
+
36
+ ## Exclusion list (never a finding)
37
+
38
+ Treat the following as **out of scope by construction** and drop any finding
39
+ that rests on one of them:
40
+
41
+ - **Sanctioned test seams** — exports consumed only by tests, and other
42
+ patterns the `test-seams` rule blesses. Never a production defect.
43
+ - **Entry points & public API surface** — CLI mains, `bin/` scripts, declared
44
+ `exports` / `bin` / `main`, and barrel contracts consumed out-of-tree. A
45
+ zero in-repo consumer count is not death.
46
+ - **Dynamic / framework reachability** — symbols reached via `import()`,
47
+ string-keyed dispatch, decorators, lifecycle listeners, or convention-loaded
48
+ plugin directories. Invisible to static analysis, not dead.
49
+ - **Intentional, documented deviations** — a pattern an in-tree comment, ADR,
50
+ or config explicitly sanctions. Cite it and drop the finding.
51
+ - **Style-only nits already enforced by a formatter/linter** — do not
52
+ re-litigate what the committed tooling already governs.
53
+
54
+ ## Final re-open-and-drop pass (mandatory)
55
+
56
+ 1. Walk your Detailed Findings once more, applying the bar and the exclusion
57
+ list above. Remove every finding that fails.
58
+ 2. Count what you kept (`k`) and what you dropped (`d`).
59
+ 3. Record the outcome in the report's **Executive Summary** as a single line:
60
+
61
+ ```text
62
+ Self-cross-check: kept <k> / dropped <d>.
63
+ ```
64
+
65
+ When `d > 0`, name the dropped findings (title + the bar/exclusion reason)
66
+ in one short list under that line, so the filtering is auditable and never
67
+ silent.
68
+
69
+ A lens that keeps every finding still records `dropped 0` — the line's absence
70
+ is itself a defect (it means the pass did not run).
@@ -0,0 +1,19 @@
1
+ # Audit finding severity scale (shared)
2
+
3
+ > **Single source of truth for the `Severity` axis (Story #4625).** Every audit
4
+ > lens report references this file so the four levels — and the parser that
5
+ > ranks them — never drift per lens.
6
+
7
+ Every finding grades its severity (labelled `Severity` or `Impact` on a given
8
+ lens) on this ordered scale. `parse-audit-md.js` recognizes every level, and a
9
+ surviving **Critical** finding halts the delivery gate
10
+ (`lib/audit-suite/findings.js#hasSurvivingCritical`).
11
+
12
+ - **Critical** — an active, exploitable, or data-losing defect that must be
13
+ fixed before the change can ship (e.g. a leaked secret, an auth bypass, a
14
+ guaranteed production outage or data-loss path).
15
+ - **High** — a serious correctness, security, or maintainability risk that
16
+ should be fixed promptly, but does not by itself block the release.
17
+ - **Medium** — a real problem worth scheduling; contained blast radius, or a
18
+ reasonable workaround exists.
19
+ - **Low** — minor or cosmetic; fix opportunistically.
@@ -132,6 +132,31 @@ Operator/agent responsibilities while in the worktree:
132
132
  read it before you write and self-check as you author. When absent,
133
133
  lens-aware coverage still runs maker-blind at Story-scope review inside
134
134
  the close subprocess.
135
+
136
+ **Producing `checklistPath` at dispatch (Story #4627).** The dispatch that
137
+ spawns this worker threads `checklistPath` the same way it threads
138
+ `docsDigestPath`. Before the spawn, compute the payload from the Story's
139
+ predicted footprint (its `changes[]` / `references[]` path entries) with
140
+ `buildDispatchChecklist` and write it to the run temp dir:
141
+
142
+ ```bash
143
+ node --input-type=module -e '
144
+ import { buildDispatchChecklist } from "<main-repo>/.agents/scripts/lib/audit-suite/index.js";
145
+ import { parse } from "<main-repo>/.agents/scripts/lib/story-body/story-body.js";
146
+ // storyBody is the fetched Story issue body.
147
+ const { changes, references } = parse(process.env.STORY_BODY);
148
+ const { checklistPath } = buildDispatchChecklist({
149
+ storyId: <storyId>, changes, references, runTempDir: "temp/run-<id>",
150
+ });
151
+ console.log(checklistPath ?? "");
152
+ '
153
+ ```
154
+
155
+ A non-empty `checklistPath` is threaded into this worker's prompt; an empty
156
+ footprint match prints nothing and the worker runs with no write-time
157
+ checklist (the maker-blind close-scope pass still covers it). The builder is
158
+ a pure function of the footprint and the on-disk checklists —
159
+ `buildDispatchChecklist` (`lib/audit-suite/dispatch-checklist.js`).
135
160
  2. Implement the changes. When the body has a `## Slicing` / Delivery
136
161
  Slicing table, walk rows as **intra-session checkpoints** (commit +
137
162
  flip each row when done) — never as sibling tickets.
package/docs/CHANGELOG.md CHANGED
@@ -2,6 +2,29 @@
2
2
 
3
3
  All notable changes to this project will be documented in this file.
4
4
 
5
+ ## [2.6.0](https://github.com/dsj1984/mandrel/compare/mandrel-v2.5.0...mandrel-v2.6.0) (2026-07-20)
6
+
7
+
8
+ ### Fixed
9
+
10
+ * **retro:** generalize friction recovery-netting, preserve signal fields on gather, and retire the story-scope singleton auto-file ([#4649](https://github.com/dsj1984/mandrel/issues/4649)) ([#4650](https://github.com/dsj1984/mandrel/issues/4650)) ([bdb8250](https://github.com/dsj1984/mandrel/commit/bdb82507d188bfe53bbd47fea7b18b2c3160439c))
11
+
12
+ ## [2.5.0](https://github.com/dsj1984/mandrel/compare/mandrel-v2.4.0...mandrel-v2.5.0) (2026-07-19)
13
+
14
+
15
+ ### Added
16
+
17
+ * audit findings contract: parse-visible templates, unified severity, deterministic identity, CI conformance gate ([#4625](https://github.com/dsj1984/mandrel/issues/4625)) ([#4635](https://github.com/dsj1984/mandrel/issues/4635)) ([63a4f63](https://github.com/dsj1984/mandrel/commit/63a4f639a5626467c5eb6bbb5ef1944fa431782d))
18
+ * **audit:** activate dormant shift-left tiers — lens delivery, checklist dispatch, self-check guard (refs [#4627](https://github.com/dsj1984/mandrel/issues/4627)) ([#4639](https://github.com/dsj1984/mandrel/issues/4639)) ([3d3b1ee](https://github.com/dsj1984/mandrel/commit/3d3b1ee1493117d11f1e1d000239fbc823c8ac64))
19
+ * **audit:** add audit-data-model lens with persistence-layer applicability probe (refs [#4633](https://github.com/dsj1984/mandrel/issues/4633)) ([#4644](https://github.com/dsj1984/mandrel/issues/4644)) ([c584293](https://github.com/dsj1984/mandrel/commit/c58429323b4cdde8d6aaf2358d71963c85bb7a0a))
20
+ * **audit:** implement advertised dependency checks, reachability-triaged vulns, and supply-chain scoped mode (refs [#4632](https://github.com/dsj1984/mandrel/issues/4632)) ([#4643](https://github.com/dsj1984/mandrel/issues/4643)) ([47f18f6](https://github.com/dsj1984/mandrel/commit/47f18f68fca3c86904ebf77b2558522f21e6b4d2))
21
+ * **audit:** replace audit-lighthouse with WCAG audit-accessibility lens (refs [#4634](https://github.com/dsj1984/mandrel/issues/4634)) ([#4645](https://github.com/dsj1984/mandrel/issues/4645)) ([800c69e](https://github.com/dsj1984/mandrel/commit/800c69e96701f321619febe12a4b2f9f30fd35d7))
22
+ * **audit:** rework audit-performance — measure-first, repo profiling, concurrency dimension (refs [#4631](https://github.com/dsj1984/mandrel/issues/4631)) ([#4642](https://github.com/dsj1984/mandrel/issues/4642)) ([ed5fd9a](https://github.com/dsj1984/mandrel/commit/ed5fd9a39b9fc4b9442484822e17553380ddccc8))
23
+ * **audit:** tool-first detection for ops/security lenses + SRE rewrite (refs [#4629](https://github.com/dsj1984/mandrel/issues/4629)) ([#4640](https://github.com/dsj1984/mandrel/issues/4640)) ([13d0439](https://github.com/dsj1984/mandrel/commit/13d0439b0a6adb6235cf305a16ee5abce61c919d))
24
+ * **audit:** tool-first detection for the code-quality lenses (refs [#4628](https://github.com/dsj1984/mandrel/issues/4628)) ([#4637](https://github.com/dsj1984/mandrel/issues/4637)) ([858f793](https://github.com/dsj1984/mandrel/commit/858f793f4d24a6b6059dc97da2067337a6937713))
25
+ * **audit:** tool-first detection for the seo, ux-ui, and navigability web lenses (refs [#4630](https://github.com/dsj1984/mandrel/issues/4630)) ([#4641](https://github.com/dsj1984/mandrel/issues/4641)) ([3885d22](https://github.com/dsj1984/mandrel/commit/3885d227087311de3a28bdaa4e882c69915b0a00))
26
+ * cross-run audit findings ledger, dedup repair, and unattended /audit-to-stories ([#4626](https://github.com/dsj1984/mandrel/issues/4626)) ([#4638](https://github.com/dsj1984/mandrel/issues/4638)) ([d8ecc2d](https://github.com/dsj1984/mandrel/commit/d8ecc2dbc23840f9ca071ce858c93a65506dfc14))
27
+
5
28
  ## [2.4.0](https://github.com/dsj1984/mandrel/compare/mandrel-v2.3.0...mandrel-v2.4.0) (2026-07-17)
6
29
 
7
30
 
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "mandrel",
3
- "version": "2.4.0",
3
+ "version": "2.6.0",
4
4
  "description": "Claude Code-first opinionated workflow framework: instructions, skills, rules, and SDLC workflows that govern AI coding assistants.",
5
5
  "files": [
6
6
  ".agents/",
@@ -1,15 +0,0 @@
1
- <!-- GENERATED FILE — do not edit by hand.
2
- Source of truth: .agents/workflows/audit-lighthouse.md
3
- Regenerate: node .agents/scripts/generate-lens-checklists.js
4
- Drift is gated by: npm run docs:check
5
- -->
6
-
7
- # Lighthouse Audit & Analysis — authoring checklist
8
-
9
- > Run a Lighthouse audit (Performance / Accessibility / Best Practices / SEO) and produce a structured findings report
10
-
11
- Self-check your change against this lens's concerns before you ship:
12
-
13
- - [ ] Opportunities
14
- - [ ] Diagnostics
15
- - [ ] Failed audits
@@ -1,69 +0,0 @@
1
- {
2
- "$schema": "http://json-schema.org/draft-07/schema#",
3
- "title": "AuditResults",
4
- "description": "Standardized output format for the audit orchestration suite",
5
- "type": "object",
6
- "required": ["summary", "results"],
7
- "additionalProperties": false,
8
- "properties": {
9
- "summary": {
10
- "type": "object",
11
- "required": [
12
- "auditsRun",
13
- "totalFindings",
14
- "critical",
15
- "high",
16
- "medium",
17
- "low"
18
- ],
19
- "additionalProperties": false,
20
- "properties": {
21
- "auditsRun": {
22
- "type": "array",
23
- "items": { "type": "string" }
24
- },
25
- "totalFindings": { "type": "integer", "minimum": 0 },
26
- "critical": { "type": "integer", "minimum": 0 },
27
- "high": { "type": "integer", "minimum": 0 },
28
- "medium": { "type": "integer", "minimum": 0 },
29
- "low": { "type": "integer", "minimum": 0 }
30
- }
31
- },
32
- "results": {
33
- "type": "array",
34
- "items": {
35
- "type": "object",
36
- "required": [
37
- "auditId",
38
- "checkId",
39
- "severity",
40
- "message",
41
- "location",
42
- "recommendation"
43
- ],
44
- "additionalProperties": false,
45
- "properties": {
46
- "auditId": { "type": "string" },
47
- "checkId": { "type": "string" },
48
- "fixId": { "type": "string" },
49
- "severity": {
50
- "type": "string",
51
- "enum": ["Critical", "High", "Medium", "Low", "Info"]
52
- },
53
- "message": { "type": "string" },
54
- "location": {
55
- "type": "object",
56
- "required": ["file"],
57
- "additionalProperties": false,
58
- "properties": {
59
- "file": { "type": "string" },
60
- "line": { "type": "integer" },
61
- "column": { "type": "integer" }
62
- }
63
- },
64
- "recommendation": { "type": "string" }
65
- }
66
- }
67
- }
68
- }
69
- }