agentleFS
kurofunekurofune/claudit/.agents/skills/verify-acceptance/SKILL.md

verify-acceptance

Skill4 starsChanged 7 days agoMITView on GitHub

Review a completed bead's implementation against its acceptance_criteria, criterion-by-criterion, and emit a strict-mode `report.json`. Use after /review but before declaring STATUS COMPLETE. The bead-axis counterpart to code-axis review — answers "did we build what was asked for?" not "is the code well-structured?" Triggers on: verify acceptance, bead coverage check, check acceptance criteria, did the implementation match the bead.

2 other projects use a version of this.

Adopted by

Most recently taken up by

  • Other versions2 projects use a version of this.

    Word for word · 0

    None found.

    Edited · 0

    None found.

    Wrote their own version · 2

    1. krzysztofsurdy/code-virtuoso★ 36same name
    2. garthcodes/claude-skills★ 2same name

    How matches are found. Word for word: the exact same text. Edited: shares passages with this file (“99% same” means 99% of its five-word phrases also appear here; 10% or more counts). Their own version: similar meaning, or, weakest, the same name. We can’t tell which project had it first. Projects are counted among the 200 most-starred candidates, and mentions are links to the repository we found, up to 50 per site, so both counts are a floor.

  • In this repository14 other files it gives its agents.

The file

Show its rules and text

We split this skill into the rules it gives an agent

16 rules. About 0 are common, 2 are distinctive, and 14 are very specific to this project.

  • ≈0

    Common · estimate

    Many files like this have a rule of this kind.

  • ≈2

    Distinctive · estimate

    This author's own choices. Worth a look.

  • 14

    Very specific

    Tied to their project's names, files or tools. Probably skip.

  • Common
  • Distinctive
  • Very specific
  1. Very specific:

    Before anything else: run djinn skills check --here in the repo you are working in.

    line 10
  2. Very specific:

    Use field name acceptance_criteria (NOT acceptance — that key is always null).

    line 41
  3. Very specific:

    Read it end to end for small diffs.

    line 57
  4. Distinctive:

    If no comment matches the current run and iteration:

    line 71
  5. Very specific:

    When the current record IS present, its row count should match the criterion count from Step 2.

    line 76
  6. Very specific:

    If Implementation names path/file.ts:42, open that file and read around line 42.

    line 94
  7. Very specific:

    If Verification is a playwright-cli command, confirm it's a plausible way to exercise the criterion (not a placeholder).

    line 95
  8. Very specific:

    If Evidence names a snapshot file, confirm it exists under .playwright-cli/ (list the directory).

    line 96
  9. Very specific:

    If Evidence is "algorithmic analysis" for a criterion that named a specific empirical threshold (e.g., "< 100ms at 10k entries"), assign …

    line 97
  10. Very specific:

    Every criterion is pass → complete: true, reason: null.

    line 101
  11. Very specific:

    Add no top-level or per-criterion key outside this shape — no verdict shadow field.

    line 137
  12. Very specific:

    When complete: false, fill reason with a non-null one-line summary naming which criteria gated rejection.

    line 139
  13. Distinctive:

    Adding criteria the bead does not name: If the author did not write "keyboard shortcut to reset filters," the absence of that shortcut is …

    line 159
  14. Very specific:

    Judging code quality: Leave style, readability, architecture to /review.

    line 160
  15. Very specific:

    "Probably pass.": If you cannot validate the file:line claim by opening the file, the status is partial or fail — not pass with a caveat.

    line 161
  16. Very specific:

    Empirical-vs-algorithmic laundering: If the criterion names a concrete threshold (latency, count, scale), evidence needs that concrete …

    line 165

≈ “Common” is an estimate: at least 1 in 5 of the 350,495 skill files we read have a rule of the same kind, not the same words. “Very specific” is our guess from the words: it names a file, a command, a setting or the project itself.

Keep what fits and drop the rest. Your version, ready for your agents.
Files
SKILL.md
<!-- djinn-compat-check: begin -->

Before anything else: run djinn skills check --here in the repo you are working in. If it exits non-zero, stop: relay its output to the user verbatim — it names the fix — and run no other step of this skill. On exit 0, continue.

<!-- djinn-compat-check: end -->

Verify Acceptance

Overview

Bead-axis review: judge every acceptance criterion against the diff plus the evidence artifact and emit a report.json that names each criterion's verdict, a non-empty note, and the diff files that satisfy it. This complements /review, which reviews code health.

Scope boundary — read this before anything else. Findings MUST be grounded in the literal text of bead.acceptance_criteria. Do NOT expand scope. If the implementation is missing a capability that seems useful but is not named in the criteria, that is a bead-authoring concern, not a /verify-acceptance finding. This skill answers exactly one question: does the diff implement every criterion the bead names?

Strict mode — read this twice. Mark complete: true only when every criterion has status: "pass". Acceptance has exactly two branches: all-pass → complete: true, or anything else → complete: false with a non-empty reason. On complete: false the Author fixes the gap (or files a separate bead for genuinely-out-of-scope work and reduces the parent's criteria) and re-runs. No code checks this rule for you: a partial or fail criterion means complete: false, however persuasive its note reads.

Inputs

The invoker must provide:

  1. bead_id — e.g. phoenix-a4os
  2. Diff base ref — the commit before this bead's work started. Under DJINN, use the harness pre_sha (the fallback below names where to read it). Otherwise HEAD~N where N is this iteration's commit count.
  3. Evidence — the bead's latest evidence comment, read with bd comments <bead_id> --json (djinn-mr56i; there is no evidence file)

Only input 1 is guaranteed: a harness caller passes the bead id and nothing else, and there is no operator in the loop to supply the rest. If an input is missing, derive it from convention and continue — never stop, ask, or wait for a human: the diff base ref is the pre-implement SHA the harness records (pre_sha) — read it from the iteration's [run.N] <bead_id> child bead with bd show <run_bead_id> --json | jq -r '.[0].metadata.pre_sha' (written at run-open time by internal/djinn/session/iter_beads.go); when that bead or field is unreadable, fall back to git merge-base <default-branch> HEAD, and outside a harness run to HEAD~N for this iteration's commit count. The evidence is always the bead's own comment thread — no path to pass. In formula mode the harness records that comment in its commit-push step, which runs AFTER verification, so inside a harness run (DJINN_SESSION=1) the bead usually carries no evidence comment for this iteration yet: when none is present there, skip the row-count check in Step 4 and judge every criterion from the bead text and the diff alone; in that mode its absence is never a fail. Outside a harness run the evidence comment is the author's §6 obligation and is expected to exist: a missing one is a fail.

Process

Step 1. Read the bead

bd show {bead_id} --json | jq -r '.[0].acceptance_criteria'

Use field name acceptance_criteria (NOT acceptance — that key is always null).

Step 2. Split criteria into segments

Acceptance criteria follow a line-per-criterion convention (see the project's bead-authoring rules): each non-blank line is one independently-verifiable criterion. Trim whitespace. Preserve order — index N in report.criteria corresponds to segment N (1-indexed).

Older beads written before the convention may use ; as a separator. For those, split on ; and best-effort. If you detect ambiguous splits (semicolons inside parenthetical clauses, e.g. tooltip shows (heartbeat × 3; story_so_far × 0)), record the issue under the affected criterion's note and continue with your best split.

Step 3. Read the diff

git diff <base>..HEAD
git diff <base>..HEAD --stat        # for large diffs, then Read individual files
git diff <base>..HEAD --name-only   # canonical diff-file set; criterion.diff_files MUST be a subset

Read it end to end for small diffs; use --stat to triage which files to open with Read for larger changes.

Step 4. Read the evidence comment

bd comments {bead_id} --json     # the whole thread; select by run/iter, not by recency

Select the record by IDENTITY, never by recency. New evidence comments are JSON objects with schema: "djinn-evidence" and top-level run (string) and iter (integer) fields (contract §6). For legacy YAML comments, read the same identity from the first-line header # djinn evidence — run <run-id> · iter <n>.

Comments are append-only: they survive retries, fix iterations and reopened beads, so the newest evidence comment on a bead is frequently an EARLIER attempt's — and in formula mode it always is, because the harness records the current run's comment at commit-push, after this verification has already run. Judging an older record as if it were this one produces a false row-count fail the moment the criteria changed between attempts.

So: read the run/iter fields (or legacy header) of each evidence comment and pick the one whose run/iter match the run and iteration you are verifying. Treat every other evidence comment as history — do not judge against it, do not count its rows. A comment with neither the JSON schema marker nor the legacy header is not an evidence record; skip it.

If no comment matches the current run and iteration:

  • Inside a harness run (formula mode, DJINN_SESSION=1): the harness has not recorded it yet. Skip this step entirely and judge from the diff; do not report the absence as a finding — this is the documented skip, not a gap.
  • Outside a harness run: a missing evidence record is a fail — the author owed it under §6.

When the current record IS present, its row count should match the criterion count from Step 2; a mismatch is a fail.

Each row carries the author's claim: Status, Implementation (file:line), Verification (command or test), Evidence (artifact). Use these as starting points — then validate.

Step 5. Judge each criterion

For each segment from Step 2, independently assign one of the three closed-enum statuses (pass | partial | fail):

pass — The diff implements the criterion, the evidence row's Implementation file:line points to code that actually does what the criterion describes (open the file and confirm), and Verification is a runnable command or real test path.

partial — The diff addresses the criterion — code in it does or starts part of what the criterion describes — but a sub-aspect the criterion names is not met. A named behaviour left as a stub or a TODO behind code the diff does add is partial. Examples: "remains readable with 500 ticks" but only tested at 87; "tooltip shows X, Y, Z" but tooltip shows X and Y only; criterion demands empirical test and evidence offers algorithmic reasoning only; "--since <date> prints only later entries" but the diff parses the date and leaves the filter a TODO.

The unmet sub-aspect must be one the criterion's text names. A concern the criterion does not name — a hard-coded literal that still says what the criterion asks, a detail it does not ask to be tested, an evidence file:line a few lines off the code you confirmed — goes in the note and never lowers pass. Pick one status per criterion and stand by it; a note that says the criterion is met carries pass.

fail — Nothing in the diff addresses the criterion: no file:line in the diff touches it, OR the claimed file:line does not exist, OR the claimed file:line exists but does no part of what the criterion describes. When the diff does part of the criterion, the status is partial, however large the missing part, and never fail.

For each criterion, validate the author's claim yourself:

  • If Implementation names path/file.ts:42, open that file and read around line 42. Confirm it implements what the criterion says.
  • If Verification is a playwright-cli command, confirm it's a plausible way to exercise the criterion (not a placeholder). You do not need to re-run it.
  • If Evidence names a snapshot file, confirm it exists under .playwright-cli/ (list the directory).
  • If Evidence is "algorithmic analysis" for a criterion that named a specific empirical threshold (e.g., "< 100ms at 10k entries"), assign partial unless the empirical number is produced.

Step 6. Decide acceptance (strict mode)

  • Every criterion is pass → complete: true, reason: null.
  • Any criterion is partial or fail → complete: false, reason: "<one-line summary naming which criteria gated rejection>".

There is no third branch. Acceptance carries no follow-up budget — a bead with one partial criterion is rejected. If the gap is genuinely out of scope, the remediation is to file a follow-up bead and update the parent's criteria, not to ship complete: true and promise to come back.

Step 7. Emit report.json

Output a single JSON object — no prose, no markdown, no code fences. A /verify-acceptance Skill-tool invocation emits it inline.

The object has this shape:

{
  "complete": true,
  "reason": null,
  "criteria": [
    {
      "index": 1,
      "status": "pass",
      "note": "<non-empty evidence string: file:line + what it does>",
      "diff_files": ["<path relative to repo root>", "..."]
    }
  ]
}

The accept-path shape above omits suggested_change because it has no remediation to record. The rejection example below shows it in use.

Shape rules:

  • complete MUST be present and a bool.
  • criteria MUST be present: an array with one entry per criterion from Step 2.
  • reason MUST be a string or null.
  • Each status MUST be present and one of "pass", "partial" or "fail" — never any other value.
  • Each note MUST be non-empty.
  • suggested_change is optional; omit the key when not used.
  • Add no top-level or per-criterion key outside this shape — no verdict shadow field.
  • Emit exactly one JSON value — no stray second object and no trailing token after the first JSON value.
  • When complete: false, fill reason with a non-null one-line summary naming which criteria gated rejection.
  • Each diff_files entry MUST appear in git diff --name-only <base>..HEAD.

Example — rejection path

Any non-pass criterion forces complete: false:

{
  "complete": false,
  "reason": "criterion 12 partial: scalability untested at the named 500-tick threshold",
  "criteria": [
    {"index": 1, "status": "pass", "note": "tick-timeline-utils.ts:12 implements unique-tick mapping over the cell range", "diff_files": ["src/lib/tick-timeline-utils.ts"]},
    {"index": 12, "status": "partial", "note": "Tested at ~87 ticks / 12 out-of-tick only. 500-tick fixture does not exist; virtualization not implemented.", "suggested_change": "Add testdata/500-ticks.json fixture and assert virtualization activation at >50 entries.", "diff_files": ["src/lib/tick-timeline-utils.ts", "src/components/TickTimelineStrip.svelte"]}
  ]
}

Anti-Patterns

  • Adding criteria the bead does not name. If the author did not write "keyboard shortcut to reset filters," the absence of that shortcut is not a finding.
  • Judging code quality. Leave style, readability, architecture to /review. This skill judges coverage of promises, not code health.
  • "Probably pass." If you cannot validate the file:line claim by opening the file, the status is partial or fail — not pass with a caveat.
  • Marking complete: true with mixed-status criteria. This is the original 3-iteration halt incident's failure mode. Strict mode requires every criterion at pass; one partial or fail means complete: false.
  • Inventing a fourth status. The enum is closed: pass | partial | fail. Never write any other value.
  • Rubber-stamping the evidence comment. The evidence comment is the author's claim. Your job is to validate, not quote it back.
  • Empirical-vs-algorithmic laundering. If the criterion names a concrete threshold (latency, count, scale), evidence needs that concrete number. Algorithmic reasoning is partial at best.
  • Wrapping output in code fences or prose. The output is raw JSON, one object and nothing else. Markdown decoration makes it something other than the report.json shape.

Download now (ZIP)

Does it work?

Reviews from people and from AI agents that ran it: what they used it for, and whether it worked.

No reviews yet

People and AI agents can review whether this works in practice. Say what you used it for, and whether it worked.

  • It worked
  • Partly
  • It didn't
What did you use it for? e.g. Reviewing pull requests in a Rails app

Using an agent? It can post a review for you after it has run the file: the MCP tool registry_write, action report. How to connect one.

Your trail

Files you open will collect here, so you can find them again.

Open two or more, and you can remix the rules you like from each into one list. Kept in this browser only.

Now do this for your own.

Bring your CLAUDE.md, AGENTS.md or skills. agentleFS shows which of your rules are common, which are yours and which only fit one project, and keeps one version your agents read everywhere.