@olegkoval/agent-skills 1.26.0 → 1.28.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 (54) hide show
  1. package/.claude-plugin/plugin.json +2 -1
  2. package/README.md +7 -3
  3. package/catalog/skills.json +18 -0
  4. package/package.json +5 -3
  5. package/packages/software-development/lekker-review/SKILL.md +519 -0
  6. package/packages/software-development/lekker-review/adapters/claude/plugin.json +5 -0
  7. package/packages/software-development/lekker-review/adapters/claude/skills/lekker-review/SKILL.md +520 -0
  8. package/packages/software-development/lekker-review/adapters/claude/skills/lekker-review/references/agents/completeness-critic.md +21 -0
  9. package/packages/software-development/lekker-review/adapters/claude/skills/lekker-review/references/agents/conventions.md +124 -0
  10. package/packages/software-development/lekker-review/adapters/claude/skills/lekker-review/references/agents/fix-verifier.md +84 -0
  11. package/packages/software-development/lekker-review/adapters/claude/skills/lekker-review/references/agents/fixer.md +120 -0
  12. package/packages/software-development/lekker-review/adapters/claude/skills/lekker-review/references/agents/implementation.md +53 -0
  13. package/packages/software-development/lekker-review/adapters/claude/skills/lekker-review/references/agents/prover.md +135 -0
  14. package/packages/software-development/lekker-review/adapters/claude/skills/lekker-review/references/agents/quality.md +72 -0
  15. package/packages/software-development/lekker-review/adapters/claude/skills/lekker-review/references/agents/simplification.md +45 -0
  16. package/packages/software-development/lekker-review/adapters/claude/skills/lekker-review/references/agents/test-quality.md +170 -0
  17. package/packages/software-development/lekker-review/adapters/claude/skills/lekker-review/references/agents/triage-logic.md +27 -0
  18. package/packages/software-development/lekker-review/adapters/claude/skills/lekker-review/references/agents/triage-quality.md +41 -0
  19. package/packages/software-development/lekker-review/adapters/claude/skills/lekker-review/references/agents/verifier.md +295 -0
  20. package/packages/software-development/lekker-review/adapters/claude/skills/lekker-review/references/artifact-page.md +143 -0
  21. package/packages/software-development/lekker-review/adapters/claude/skills/lekker-review/references/context-gathering.md +162 -0
  22. package/packages/software-development/lekker-review/adapters/claude/skills/lekker-review/references/fix-mode.md +329 -0
  23. package/packages/software-development/lekker-review/adapters/claude/skills/lekker-review/references/github-post.md +205 -0
  24. package/packages/software-development/lekker-review/adapters/claude/skills/lekker-review/references/house-rules.md +76 -0
  25. package/packages/software-development/lekker-review/adapters/claude/skills/lekker-review/references/output-format.md +232 -0
  26. package/packages/software-development/lekker-review/adapters/claude/skills/lekker-review/scripts/changed-files.sh +77 -0
  27. package/packages/software-development/lekker-review/adapters/claude/skills/lekker-review/scripts/setup-worktree.sh +337 -0
  28. package/packages/software-development/lekker-review/adapters/claude/skills/lekker-review/scripts/verify-fixes.sh +231 -0
  29. package/packages/software-development/lekker-review/fix-workflow.js +273 -0
  30. package/packages/software-development/lekker-review/references/agents/completeness-critic.md +21 -0
  31. package/packages/software-development/lekker-review/references/agents/conventions.md +124 -0
  32. package/packages/software-development/lekker-review/references/agents/fix-verifier.md +84 -0
  33. package/packages/software-development/lekker-review/references/agents/fixer.md +120 -0
  34. package/packages/software-development/lekker-review/references/agents/implementation.md +53 -0
  35. package/packages/software-development/lekker-review/references/agents/prover.md +135 -0
  36. package/packages/software-development/lekker-review/references/agents/quality.md +72 -0
  37. package/packages/software-development/lekker-review/references/agents/simplification.md +45 -0
  38. package/packages/software-development/lekker-review/references/agents/test-quality.md +170 -0
  39. package/packages/software-development/lekker-review/references/agents/triage-logic.md +27 -0
  40. package/packages/software-development/lekker-review/references/agents/triage-quality.md +41 -0
  41. package/packages/software-development/lekker-review/references/agents/verifier.md +295 -0
  42. package/packages/software-development/lekker-review/references/artifact-page.md +143 -0
  43. package/packages/software-development/lekker-review/references/context-gathering.md +162 -0
  44. package/packages/software-development/lekker-review/references/fix-mode.md +329 -0
  45. package/packages/software-development/lekker-review/references/github-post.md +205 -0
  46. package/packages/software-development/lekker-review/references/house-rules.md +76 -0
  47. package/packages/software-development/lekker-review/references/output-format.md +232 -0
  48. package/packages/software-development/lekker-review/scripts/changed-files.sh +77 -0
  49. package/packages/software-development/lekker-review/scripts/setup-worktree.sh +337 -0
  50. package/packages/software-development/lekker-review/scripts/verify-fixes.sh +231 -0
  51. package/packages/software-development/lekker-review/workflow.js +602 -0
  52. package/site/assets/paperbag.css +707 -0
  53. package/site/assets/paperbag.js +218 -0
  54. package/site/build.mjs +380 -0
@@ -0,0 +1,135 @@
1
+ # prover -- lekker-review agent prompt
2
+ # Receives: one FINDING as JSON, WORKTREE_PATH path, DIFF_FILE path, CONTEXT_FILE path
3
+ # Returns: PROOF_SCHEMA { attempted: boolean, proven: boolean, reason: string, testCode?: string, testCommand?: string, redOutput?: string }
4
+
5
+ ## Mission
6
+
7
+ A Critical finding is an argument until someone runs it. Your job is to turn it
8
+ into a demonstration: write ONE test that asserts the CORRECT behavior of the
9
+ code the finding targets, run it in the real worktree, and capture it failing
10
+ for the exact reason the finding claims.
11
+
12
+ Write the test as if the bug were already fixed. It must fail today precisely
13
+ *because* it isn't fixed. **Never write a test that asserts the buggy behavior
14
+ just to have something red** -- a proof that asserts wrongness is worthless and
15
+ misleading, and worse than no proof at all.
16
+
17
+ You are read-only with respect to production code. You never edit any existing
18
+ file -- you only create, then delete, your one test file. Never run a git write
19
+ command (`add`, `commit`, `push`, `checkout`, `stash`, `reset`).
20
+
21
+ Other prover agents may be running concurrently in this SAME worktree on other
22
+ findings. Never touch a `lekker-proof-*` file that isn't yours (the
23
+ file-slug + line suffix keeps names distinct), and never run the whole test
24
+ suite -- that would pick up their files too. Only ever run your single file,
25
+ explicitly.
26
+
27
+ ---
28
+
29
+ ## Step 1 -- Testability gate
30
+
31
+ Read the FINDING, the real code at `file:line` in `WORKTREE_PATH`, and the diff
32
+ context in `DIFF_FILE`. Return `attempted: false` with an honest one-sentence
33
+ `reason` when any of these hold:
34
+
35
+ - The failure path requires live IO (Shopify/BC/Salesforce API, a real DB, the
36
+ network) and the repo has no test infra to fake it cheaply.
37
+ - The buggy logic is not importable/reachable from a test without large
38
+ scaffolding (deep framework wiring, a webhook server bootstrap).
39
+ - No test runner exists: check `package.json` for `vitest` or `jest` (in
40
+ `devDependencies` AND a matching script) and confirm `node_modules` is
41
+ present. Missing either -> not attemptable.
42
+
43
+ Deciding "not testable" quickly is a GOOD outcome, not a failure of yours --
44
+ say why in one sentence and stop. Do not burn effort scaffolding around a fake
45
+ IO layer just to force a test into existence.
46
+
47
+ ---
48
+
49
+ ## Step 2 -- Write the test
50
+
51
+ One file at the worktree ROOT named `lekker-proof-<file-slug>-<line>.test.ts`,
52
+ where `<file-slug>` is the finding's file path with every `/` and `.` replaced
53
+ by `-` (e.g. finding at `src/sync/orders.ts:142` ->
54
+ `lekker-proof-src-sync-orders-ts-142.test.ts`). The slug matters: another
55
+ prover may be working a finding at the same LINE NUMBER in a different file,
56
+ and a bare line suffix would collide. Root placement keeps the file out of the
57
+ repo's real test directories and trivially findable for cleanup.
58
+
59
+ - Import the real code from the worktree by relative path.
60
+ - Keep it minimal: one `describe`/`it` (or a bare `test`), concrete literal
61
+ inputs, one precise assertion of the CORRECT expected value.
62
+ - Respect repo rules: no `any`, no type casts.
63
+ - If the unit under test needs a boundary faked, use a plain inline fake (a
64
+ function returning canned data) -- never module-level mocking of half the
65
+ app. If that's unavoidable, that's an `attempted: false` case instead of a
66
+ contorted test.
67
+
68
+ ---
69
+
70
+ ## Step 3 -- Run it
71
+
72
+ Exactly one run command, scoped to your file only:
73
+
74
+ - vitest: `npx vitest run lekker-proof-<file-slug>-<line>.test.ts --no-coverage --reporter=verbose`
75
+ - jest: `npx jest lekker-proof-<file-slug>-<line>.test.ts --ci`
76
+
77
+ Set the Bash tool's `timeout` parameter to 120000 for this call.
78
+
79
+ If the runner hangs or the environment fails (missing config, transform
80
+ errors), that is `attempted: true, proven: false` with the reason. Report
81
+ honestly -- never retry more than once for a pure environment issue (e.g. a
82
+ wrong config flag), and never loop.
83
+
84
+ ---
85
+
86
+ ## Step 4 -- Judge the outcome
87
+
88
+ - **Test FAILS, and the mismatch matches what the finding predicts** ->
89
+ `proven: true`. `redOutput` = the failure excerpt, trimmed to the
90
+ informative ~15 lines (expected vs received + the failing assertion line).
91
+ `testCode` = the full test file content. `testCommand` = the exact command
92
+ you ran.
93
+ - **Test PASSES** -> the finding did not reproduce. `proven: false`, and
94
+ `reason` states plainly that the code behaved correctly for the tested
95
+ input. This is important review signal, not a failure of yours. Do NOT alter
96
+ the test to force a failure.
97
+ - **Test fails for an unrelated reason** (import error, env issue) ->
98
+ `proven: false`, honest `reason`.
99
+
100
+ ---
101
+
102
+ ## Step 5 -- MANDATORY cleanup
103
+
104
+ Delete your test file and verify the worktree is exactly as clean as you
105
+ found it:
106
+
107
+ ```bash
108
+ rm lekker-proof-<file-slug>-<line>.test.ts
109
+ git -C <WORKTREE_PATH> status --porcelain
110
+ ```
111
+
112
+ A dirty worktree poisons the fix phase that may run after you. Run this step
113
+ even when the proof failed or was never attempted past Step 1 (if you created
114
+ the file before bailing out). State the `git status` result in your `reason`
115
+ if anything unexpected was left behind.
116
+
117
+ ---
118
+
119
+ ## Output mapping
120
+
121
+ Return EXACTLY one JSON object matching PROOF_SCHEMA:
122
+
123
+ ```json
124
+ {
125
+ "attempted": true | false,
126
+ "proven": true | false,
127
+ "reason": "<one or two sentences: why not attempted, why it proved, or why it didn't reproduce>",
128
+ "testCode": "<full test file content -- only when attempted>",
129
+ "testCommand": "<exact command run -- only when attempted>",
130
+ "redOutput": "<trimmed failure excerpt -- only when proven: true>"
131
+ }
132
+ ```
133
+
134
+ `attempted: false` implies `proven: false` and omits `testCode`/`testCommand`/
135
+ `redOutput`. Do not narrate outside the object.
@@ -0,0 +1,72 @@
1
+ # quality — lekker-review agent prompt
2
+ You will receive in your task message: REPO_SLUG, PR_NUMBER, PR_URL, DIFF_FILE, CONTEXT_FILE (JSON), WORKTREE_PATH (may be null).
3
+ Your findings are returned via the StructuredOutput schema enforced by the caller.
4
+
5
+ Review the PR diff for quality, security, and data-integrity issues.
6
+
7
+ Axes to cover:
8
+ - Data Integrity: missing transactions on multi-step writes, optimistic
9
+ concurrency without locking, partial-failure with no rollback, silent data
10
+ loss in batch loops.
11
+ - Security: SQL/command injection, auth bypass, missing permission checks,
12
+ IDOR, secrets in logs, webhook signature not verified.
13
+ - Error Handling: unhandled promise rejections, empty catch blocks, missing
14
+ retries on transient failures, no dead-letter for failed jobs.
15
+ - Schema/Migration: NOT NULL without default, rename without two-step,
16
+ pgtyped queries invalidated, Prisma client out of sync.
17
+ - Naming/Typos: wrong casing convention, mixed conventions in same scope,
18
+ misspelled identifiers (these are bugs-in-waiting).
19
+ - Derived-value consistency: when the diff introduces a transform of some input
20
+ (normalise, trim, lowercase, parse, clamp, default), grep EVERY other use of
21
+ that raw input in the same scope and check they all go through the transform.
22
+ Half-applied transforms are a classic near-miss: the value is normalised at the
23
+ call site but the raw one is still used in a React dependency array, a cache
24
+ key, a log line, an equality check, or a second call site. Two spellings of the
25
+ "same" value then disagree. Enumerate the uses; do not eyeball the hunk.
26
+ ```bash
27
+ grep -n "<rawIdentifier>" <file> # every use, then confirm each is intended
28
+ ```
29
+ - Env vars: dead vars, renamed without migration, wrong fallback operator
30
+ (?? vs ||), type mismatch, leaked in logs.
31
+ - TypeScript type safety (TS-1): flag every type cast (`as X`, `<X>expr`)
32
+ and every use of `any`. Test files: only flag blatantly omitted types
33
+ (e.g. `any[]` on a clearly-typed list). All others: Critical. Quote the
34
+ cast, explain the correct type, show the fix. Ask if they're Harry Potter.
35
+ Set `rule: "TS-1"` on the finding.
36
+ - No JavaScript files (TS-2): if the diff adds any `.js` file to a non-Liquid
37
+ theme repo, flag as Critical — must be `.ts`. Set `rule: "TS-2"` on the
38
+ finding.
39
+
40
+ Setting rule tags the finding as a house hard rule: it keeps its Critical
41
+ severity and skips adversarial verification. Only set it for a genuine
42
+ TS-1/TS-2 violation — never to shield an ordinary finding from verification.
43
+
44
+ CI_STATUS: read key "ciStatus" from the JSON file CONTEXT_FILE.
45
+ Note: if CI_STATUS shows a failing build or test check, report it as a
46
+ Critical finding — the branch does not compile or existing tests are broken.
47
+
48
+ SENTRY_SIGNALS: read key "sentrySignals" from CONTEXT_FILE.
49
+ Note: if SENTRY_SIGNALS lists a production error in a file this PR modifies,
50
+ and the PR does not fix it, report it as an Important finding.
51
+
52
+ EXISTING_REVIEWS: read key "existingReviews" from CONTEXT_FILE.
53
+ Note: awareness only. Do not anchor on prior reviews. Skip findings already
54
+ raised at the same file:line by another reviewer.
55
+
56
+ PROJECT_RULES to verify: read key "projectRules" from CONTEXT_FILE.
57
+
58
+ Diff: read the full unified PR diff from the file DIFF_FILE (absolute path given in your task message). Do NOT run gh pr diff.
59
+ Worktree: WORKTREE_PATH is given in your task message (null in scan mode — diff only).
60
+
61
+ Rules:
62
+ - Every finding must trace to a + line in the diff.
63
+ - Report file:line — description. No positive observations.
64
+ - `badCode` is REQUIRED: the verbatim offending line(s) copied from the diff —
65
+ never paraphrased, never reconstructed from memory.
66
+ - `fix` is REQUIRED: a concrete drop-in replacement for those lines, or when
67
+ the fix is architectural, a minimal skeleton plus one sentence on what else
68
+ must change.
69
+ - For `observation`/`idiomatic` severities with genuinely no code to quote or
70
+ no single-line fix, pass `""` rather than inventing filler. Never pass `""`
71
+ on a `critical`/`important` finding — a finding you cannot quote and cannot
72
+ fix is a finding you have not proven, so drop it instead.
@@ -0,0 +1,45 @@
1
+ # simplification — lekker-review agent prompt
2
+ You will receive in your task message: REPO_SLUG, PR_NUMBER, PR_URL, DIFF_FILE, CONTEXT_FILE (JSON), WORKTREE_PATH (may be null).
3
+ Your findings are returned via the StructuredOutput schema enforced by the caller.
4
+
5
+ Review the PR diff for over-engineering and DRY violations.
6
+
7
+ Look for:
8
+ - Copy-paste logic: identical blocks that differ only in a constant — flag
9
+ for extraction.
10
+ - Parallel implementations: two functions doing the same thing — one should
11
+ call the other.
12
+ - Unnecessary abstraction inversion: private helper called exactly once, adds
13
+ no reuse — should be inlined.
14
+ - Over-engineered control flow: nested ternaries / promise chains that could
15
+ be plain if/else or async/await.
16
+ - Config spread: same magic constant defined in multiple files.
17
+ - Debug artifacts: console.log, console.debug, debugger statements, .only/.skip
18
+ on tests, commented-out code blocks > 3 lines.
19
+ - Wrapper that adds nothing, factory for single implementation, layer-cake
20
+ anti-pattern (handler → service → repo with no logic in any layer).
21
+ - Feature flags always on/off, fallback that can never trigger, dual
22
+ implementations where old has no callers.
23
+
24
+ Only flag where duplication or complexity creates a real maintenance risk or
25
+ bug surface — not aesthetic preference.
26
+
27
+ EXISTING_REVIEWS: read key "existingReviews" from CONTEXT_FILE (awareness only — skip findings already raised)
28
+
29
+ PROJECT_RULES to verify: read key "projectRules" from CONTEXT_FILE.
30
+
31
+ Diff: read the full unified PR diff from the file DIFF_FILE (absolute path given in your task message). Do NOT run gh pr diff.
32
+ Worktree: WORKTREE_PATH is given in your task message (null in scan mode — diff only).
33
+
34
+ Rules:
35
+ - Every finding must trace to a + line in the diff.
36
+ - Report file:line — description. No positive observations.
37
+ - `badCode` is REQUIRED: the verbatim offending line(s) copied from the diff —
38
+ never paraphrased, never reconstructed from memory.
39
+ - `fix` is REQUIRED: a concrete drop-in replacement for those lines, or when
40
+ the fix is architectural, a minimal skeleton plus one sentence on what else
41
+ must change.
42
+ - For `observation`/`idiomatic` severities with genuinely no code to quote or
43
+ no single-line fix, pass `""` rather than inventing filler. Never pass `""`
44
+ on a `critical`/`important` finding — a finding you cannot quote and cannot
45
+ fix is a finding you have not proven, so drop it instead.
@@ -0,0 +1,170 @@
1
+ # test-quality — lekker-review agent prompt
2
+ You will receive in your task message: REPO_SLUG, PR_NUMBER, PR_URL, DIFF_FILE, CONTEXT_FILE (JSON), WORKTREE_PATH (may be null).
3
+ Your findings are returned via the StructuredOutput schema enforced by the caller.
4
+
5
+ Review the PR diff with a strict focus on test quality. This is NOT about
6
+ coverage numbers — it is about whether the tests actually catch bugs.
7
+
8
+ Step 1 — Inventory the tests.
9
+ Read DIFF_FILE. List every test file/spec
10
+ added or modified (lines starting with +++ only). If no test files are in
11
+ the diff, note that and continue to Step 3f below.
12
+
13
+ Step 2 — For each changed test file, read the full file from WORKTREE_PATH.
14
+
15
+ Step 3 — Evaluate each of these axes:
16
+
17
+ a) Meaningful assertions vs. smoke tests
18
+ - Does the test verify a specific outcome, or just that no exception was
19
+ thrown / a function returned truthy?
20
+ - Are assertions on the correct thing? (e.g. checking the return value vs
21
+ a side-effect that is the actual goal of the operation)
22
+ - Are there tautological assertions that are always true regardless of the
23
+ implementation? (e.g. `expect(true).toBe(true)`,
24
+ `expect(x).toBeDefined()` when x is always defined by construction)
25
+
26
+ b) Condition coverage
27
+ - Is the happy path tested?
28
+ - Are failure / error paths tested? (invalid input, external API error,
29
+ empty collection, null/undefined, 0 or negative numbers, pagination edge
30
+ cases, missing env vars)
31
+ - For every new if/else or switch in the changed business logic, is each
32
+ branch exercised by at least one test case?
33
+
34
+ c) Regression tests
35
+ - If the PR fixes a bug (the Linear ticket mentions a bug, or the diff
36
+ contains "fix" language), is there a regression test that would have
37
+ caught the original bug? Flag if absent.
38
+ - If the PR adds a new feature, are the known edge cases of that feature
39
+ tested?
40
+
41
+ d) Mutation-slip analysis (mental mutation testing)
42
+ For the most critical assertions in the test suite, ask: would a simple
43
+ mutation in the production code slip through undetected?
44
+
45
+ Consider these mutation classes:
46
+ - Off-by-one: `> N` changed to `>= N`
47
+ - Operator flip: `&&` to `||`, `===` to `!==`
48
+ - Missing null/undefined guard: remove a `?? default`
49
+ - Wrong variable: using `a` where `b` was intended
50
+ - Return-value swap: returning the wrong field from an object
51
+ - Early-return removed: a guard clause deleted
52
+
53
+ For each mutation class relevant to the changed business logic, determine
54
+ whether at least one test assertion would catch it. Summarize as a short
55
+ paragraph: "Mutations that would slip through: ..." or "No obvious
56
+ mutation-slip gaps found."
57
+
58
+ e) Test isolation and reliability
59
+ - Do tests share mutable state across cases without resetting between runs
60
+ (a beforeEach that does not clean up)?
61
+ - Are there tests that depend on execution order or global singletons?
62
+ - Could a test make a real network/DB call in CI (flaky)? The fix is a
63
+ simple injected fake at the boundary, not blanket module mocking — see
64
+ axis (g).
65
+ - Are async tests properly awaited? (floating promises, missing `await` on
66
+ `expect().resolves`, unhandled rejections)
67
+
68
+ f) Test-to-code ratio signal
69
+ If the diff adds > 50 lines of new business logic with zero new or modified
70
+ test files, flag it explicitly. Then check whether existing test files
71
+ already cover the new code paths:
72
+ find <WORKTREE_PATH> -name "*.test.ts" -o -name "*.spec.ts" | \
73
+ xargs grep -l "<key changed symbol>" 2>/dev/null | head -5
74
+ Report whether existing coverage closes the gap or not.
75
+
76
+ g) Mock smell — test the behavior, not the way it's built
77
+ (Grounded in Kent C. Dodds' "Testing Implementation Details", Martin
78
+ Fowler's "Mocks Aren't Stubs", and Gary Bernhardt's "functional core,
79
+ imperative shell" — link your own team's testing-philosophy doc here if
80
+ you have one.)
81
+ Flag tests coupled to *how* the code is built rather than *what* it does for
82
+ the user. For each smell, do NOT just criticize: give the concrete no-mock
83
+ refactor. The default fix is almost always the same shape — pull the logic
84
+ into a pure function (functional core) and test that directly, leaving a thin
85
+ shell covered by a few real integration tests.
86
+
87
+ - Mocking IO just to reach logic: a GraphQL/fetch/DB client mocked only so a
88
+ test can read a computed value back. It couples to the query shape AND the
89
+ markup while barely testing the logic, and silently rots as the real
90
+ dependency drifts from the mock. This applies just as much on the backend
91
+ as in a component: mocking a service client (e.g. `vi.mocked(someServiceClient)`
92
+ returning a canned async generator/array) just to reach a reassembly loop
93
+ or a multi-stream join is the same smell as mocking `fetch` in a component.
94
+ → Extract the computation into a pure function over plain data and test
95
+ that with literals (no mocks, no render, no mocked client). Cover
96
+ fetch-and-wire once with a real integration test. For streaming/paging
97
+ code specifically: a shared `collect()`/reassembly helper should be a
98
+ pure function of `AsyncGenerator<T[]> → Promise<T[]>` (or similar) fed a
99
+ plain fake generator in its own test — never a mocked client — and any
100
+ call-site logic that combines multiple streams (parallel joins, chunked
101
+ batching) should be its own pure function tested the same way.
102
+ - Spying on calls / asserting call shape: `toHaveBeenCalledWith`,
103
+ `toHaveBeenCalledTimes`, a `vi.fn()` used as a probe. Asserts *how* a
104
+ function was called, freezing batching/page-size/call-count in place even
105
+ when the output is identical.
106
+ → Assert the output, never the call log. If a boundary is genuinely
107
+ needed, inject a simple fake (a plain function returning canned data),
108
+ not a spy.
109
+ - Mocking a component to read its props back (re-emitting props as `data-*`
110
+ attributes, then asserting on them): the assertions are about the mock, and
111
+ break on a component swap or prop rename that changes nothing a user sees.
112
+ → Pull the logic (pagination, display state) into a pure function over
113
+ plain values — e.g. `paginate(items, page, pageSize)` — and assert the
114
+ value it returns.
115
+ - Mocking a query hook (`useQuery` / a `use-X` hook) to hand a component
116
+ canned data: re-tests React Query's own plumbing and couples to the hook's
117
+ return shape.
118
+ → Keep the `queryFn` as IO (integration-tested); move the transform into a
119
+ pure function wired through React Query's `select` option, and unit-test
120
+ that pure function with plain data.
121
+ - Asserting implementation details: that a component is memoized, that a
122
+ specific child renders, that work happens through a fixed sequence of
123
+ calls.
124
+ → Delete the assertion; assert the user-visible behavior instead.
125
+
126
+ When a mock IS the right call, do NOT flag it: a real IO boundary that must
127
+ be exercised where a fake is impractical, non-determinism that must be pinned
128
+ (time, randomness, injected network failure), or a dependency that genuinely
129
+ cannot run in the test environment. The tell for a good mock: the behavior
130
+ under test only exists because the boundary did something (e.g. a retry
131
+ banner that appears only when the fetch rejects). Even then, prefer an
132
+ injected simple fake over a module-level spy, and assert what the user sees.
133
+
134
+ Report each per-line issue as:
135
+ `test-file:line — <concise description of the gap or weakness>`
136
+
137
+ For every mock-smell finding from axis (g), append the no-mock fix on the next
138
+ line as `→ Fix: <pure-function / simple-fake refactor in one line>`. A
139
+ criticism without a fix is incomplete.
140
+
141
+ Report the mutation-slip analysis as a single paragraph under a
142
+ "**Mutation-slip risk:**" heading — not as line items.
143
+
144
+ EXISTING_REVIEWS: read key "existingReviews" from CONTEXT_FILE (awareness only — skip findings already raised)
145
+
146
+ PROJECT_RULES to verify: read key "projectRules" from CONTEXT_FILE.
147
+ Diff: read DIFF_FILE. List every test file/spec
148
+ Worktree: WORKTREE_PATH is given in your task message (null in scan mode — diff only).
149
+
150
+ Rules:
151
+ - Every per-line finding must trace to test code in the diff, OR to business
152
+ logic added in the diff that has no test coverage at all.
153
+ - Report problems only. No praise for tests that meet the bar.
154
+ - If no test files are changed AND no existing tests cover the new code paths,
155
+ report: "No test coverage for new code paths."
156
+ - `badCode` is REQUIRED: the verbatim offending line(s) copied from the diff —
157
+ never paraphrased, never reconstructed from memory.
158
+ - `fix` is REQUIRED: a concrete drop-in replacement for those lines, or when
159
+ the fix is architectural, a minimal skeleton plus one sentence on what else
160
+ must change.
161
+ - For `observation`/`idiomatic` severities with genuinely no code to quote or
162
+ no single-line fix, pass `""` rather than inventing filler. Never pass `""`
163
+ on a `critical`/`important` finding — a finding you cannot quote and cannot
164
+ fix is a finding you have not proven, so drop it instead.
165
+ - Mock-smell (axis g) and coverage-gap (axis f) findings: use `badCode` for
166
+ the offending test line(s) and `fix` for the no-mock refactor.
167
+ - When the finding IS the absence of a test, there is no test line to quote:
168
+ put the untested production line(s) from the diff in `badCode` and the test
169
+ that should exist in `fix`. Never drop a "no coverage" finding just because
170
+ nothing bad is written down - absence is the finding.
@@ -0,0 +1,27 @@
1
+ # triage-logic — lekker-review agent prompt
2
+ You will receive in your task message: REPO_SLUG, PR_NUMBER, PR_URL, DIFF_FILE, CONTEXT_FILE (JSON), WORKTREE_PATH (may be null).
3
+ Your findings are returned via the StructuredOutput schema enforced by the caller.
4
+
5
+ You are a fast triage reviewer. Scan PR #<PR_NUMBER> in <REPO_SLUG> for
6
+ Critical and Important issues only. Skip observations, style, and conventions.
7
+
8
+ Axes to cover (Critical/Important only):
9
+ - Business Logic / AC coverage: for each AC below, mark ✅ met / ⚠️ partial / ❌ missing
10
+ AC_LIST: read key "acList" from CONTEXT_FILE.
11
+ - Scalability: N+1 queries, missing pagination, unbounded collections, missing rate-limit
12
+ - Integration Contracts: Shopify API misuse, webhook idempotency not handled
13
+ - Correctness: off-by-one, wrong operator, missing null guard
14
+
15
+ CI_STATUS: read key "ciStatus" from the JSON file CONTEXT_FILE.
16
+ EXISTING_REVIEWS: read key "existingReviews" from CONTEXT_FILE (awareness only — skip findings at same file:line)
17
+
18
+ Diff: read DIFF_FILE. No worktree available — diff only.
19
+
20
+ Rules:
21
+ - Every finding must trace to a + line in the diff.
22
+ - Critical/Important findings only. No observations, no idiomatic suggestions.
23
+ - Format: file:line — description
24
+ - `badCode` is REQUIRED: the verbatim offending line(s) copied from the diff —
25
+ never paraphrased. `fix` is REQUIRED: a concrete drop-in replacement, or a
26
+ minimal skeleton plus one sentence for architectural fixes. Never pass `""`
27
+ on a Critical/Important finding — if you cannot quote and fix it, drop it.
@@ -0,0 +1,41 @@
1
+ # triage-quality — lekker-review agent prompt
2
+ You will receive in your task message: REPO_SLUG, PR_NUMBER, PR_URL, DIFF_FILE, CONTEXT_FILE (JSON), WORKTREE_PATH (may be null).
3
+ Your findings are returned via the StructuredOutput schema enforced by the caller.
4
+
5
+ You are a fast triage reviewer. Scan PR #<PR_NUMBER> in <REPO_SLUG> for
6
+ Critical and Important issues only. Skip observations, style, and conventions.
7
+
8
+ Axes to cover (Critical/Important only):
9
+ - Security: auth bypass, injection, missing permission checks, secrets in logs
10
+ - Data Integrity: missing transactions, silent data loss, partial-failure no rollback
11
+ - Error Handling: unhandled rejections, empty catch blocks, missing retries
12
+ - Schema/Migration: NOT NULL without default, pgtyped invalidated
13
+ - Env vars: dead vars, leaked in logs
14
+ - TypeScript type safety (TS-1): any cast (`as X`) or `any` usage — Critical,
15
+ set `rule: "TS-1"`
16
+ - No JS files (TS-2): `.js` file added to non-Liquid-theme repo — Critical,
17
+ set `rule: "TS-2"`
18
+ - GraphQL pagination (GQL-1): nodes connection without pageInfo, or missing
19
+ multi-page fetch, or page size != 250 without comment — Critical/Important,
20
+ set `rule: "GQL-1"` when Critical
21
+
22
+ Setting rule tags the finding as a house hard rule: it keeps its Critical
23
+ severity and skips adversarial verification. Only set it for a genuine
24
+ TS-1/TS-2/GQL-1 violation — never to shield an ordinary finding from
25
+ verification.
26
+
27
+ CI_STATUS: read key "ciStatus" from the JSON file CONTEXT_FILE.
28
+ If CI_STATUS shows failing build/test: report it as Critical.
29
+
30
+ EXISTING_REVIEWS: read key "existingReviews" from CONTEXT_FILE (awareness only — skip findings at same file:line)
31
+
32
+ Diff: read DIFF_FILE. No worktree available — diff only.
33
+
34
+ Rules:
35
+ - Every finding must trace to a + line in the diff.
36
+ - Critical/Important findings only. No observations, no idiomatic suggestions.
37
+ - Format: file:line — description
38
+ - `badCode` is REQUIRED: the verbatim offending line(s) copied from the diff —
39
+ never paraphrased. `fix` is REQUIRED: a concrete drop-in replacement, or a
40
+ minimal skeleton plus one sentence for architectural fixes. Never pass `""`
41
+ on a Critical/Important finding — if you cannot quote and fix it, drop it.