Miki review loop
Miki's personal pre-self-review loop. Iteratively runs /review on the current PR and addresses obvious issues until only minor nits remain or 3 iterations have run. Surfaces judgment calls back to the user, makes atomic commits per project convention, pushes once at the end. Invoke when the user says "/miki-review-loop", "loop the review", "iterate on the review", or similar after a PR has been created.From its SKILL.md
npx -y skills add mikiwiik/claude-code-skills --skill miki-review-loopAssembled from the repository path, not quoted from the project. Check it against their README if it does not work.
One thing to look at
- 0 stars0 stars. Stars are a popularity signal and not a quality one, but at this level it is likely that nobody has read this closely except its author, and you would be relying on your own review.
SKILL.md
7.7 KB, ~1.8k tokens by cl100k_base, as published. Nobody here has run it
miki-review-loop
What this does
Runs /review → addresses issues → re-runs, up to 3 iterations. Exits when only nits remain, a judgment call surfaces, or the cap is hit. Ends with a written summary of every change and commit.
Preconditions
Verify in order; stop and report on first failure:
- PR identification.
- Argument given (bare
84,#84,PR 84,PR #84, or full PR URL): normalize to a bare number, rungh pr view <n> --json number,title,headRefName,baseRefName,state, announceProcessing PR #N — "<title>" on <head> → <base>, proceed. - No argument: derive from current branch via
gh pr view --json number,title,headRefName,baseRefName,state. AnnounceDetected PR #N — ...and ask to confirm. If ambiguous, list candidates and ask. - No PR or not OPEN: stop.
- Argument given (bare
- Clean working tree (
git status --porcelainempty). - Not on
main/master. - Verification command available (see below). If not, follow the prompt-to-create flow before iteration 1.
Verification command
The loop runs the repo's verification command between iterations to confirm fixes don't break the build. Detect on each run:
package.jsonscripts — try in order:check,verify,validate,ci,test. For each, prefer the:civariant when present (e.g.check:ciovercheck) — tuned for non-interactive runs. First match wins.- Other stacks —
Cargo.toml→cargo check && cargo test;Makefilewithchecktarget →make check;pyproject.tomlwith[tool.<runner>]→ obviouscheck/testtask. CLAUDE.md— grep for a documented verification command (e.g. under a "Verification" header or a fenced block tagged as the canonical check). If present, use it.
One candidate found → use it, tell the user. Multiple plausible → list and ask.
If none can be found
Stop before iteration 1 and tell the user:
I couldn't find a verification command for this repo. The loop runs one between iterations to catch broken intermediate commits before they compound.
Options: (a) Add a
checkscript topackage.jsonaggregating lint + typecheck + test. (b) Document the command in CLAUDE.md under a "Verification" section. (c) Give me the command now — for this run only, won't persist. (d) Skip verification — not recommended; risky on iteration 2+ (broken intermediate commits compound).
For (a) or (b), draft the addition and show it to the user before writing; persist as a separate atomic commit via the user's normal flow.
Auto-merge handling
After preconditions pass, check gh pr view <n> --json autoMergeRequest,reviewDecision. If auto-merge is enabled, disable it (gh pr merge <n> --disable-auto) before iteration 1 and record the merge method (SQUASH/MERGE/REBASE) — otherwise the merge can fire on the pre-fix SHA the moment CI greens. Announce auto-merge paused for loop duration; also mention if reviewDecision is APPROVED (that's why the pause matters).
Restore via gh pr merge <n> --auto --<method> after the final push, and on every exit path: clean (only nits or no findings at all, no commits made), judgment call surfaced, iteration cap reached, build verification failed, push failed. The trivial-clean exit where no commits were made still requires restoration — don't conflate "nothing to push" with "nothing to restore". Restoration is the last action before writing the summary, not something the user has to trigger by saying "please merge". If disable or restore fails, stop and report — don't iterate without the pause, don't leave auto-merge in a different state than you found.
Severity bands
Classify each /review finding:
- Blocker — breaks correctness, security, or build. Fix.
- Major — clear defect or convention violation, single right answer (e.g. missing null check on documented-non-null field). Fix.
- Minor — single obvious right answer, no behavior change (e.g. unused import, typo). Fix.
- Nit — style/preference, multiple valid choices. Skip.
- Judgment call — depends on intent, tradeoffs, or info not in the diff (architecture, naming, public-API contracts, behavior changes, anything needing a new test). Stop and ask.
When in doubt between Minor and Judgment call, treat as judgment.
The loop
For iteration i in 1..3:
- Run
/review. - Classify findings; show the grouped list to the user before acting.
- Any judgment calls → stop, ask one by one. Don't silently skip.
- No Blocker/Major/Minor remain → exit successfully (only nits, or nothing). Restore auto-merge before writing the summary (see Auto-merge handling).
- Address Blocker + Major + Minor. If a finding turns out more ambiguous while fixing it, stop and ask.
- Run the verification command. If it fails, fix the failure and re-verify before committing. If you can't fix cleanly within the same logical change, surface as a judgment call.
- Commit atomically (see below).
- Track every change (file path + one-line) and commit (sha + message) in a running log.
If iteration 3 finishes with non-nit issues remaining, stop and report.
Commit and push cadence
- Atomic commits per project convention (Conventional Commits in most projects — check
git logor CLAUDE.md). Two unrelated findings = two commits. - Amend only when the new edit is part of the same atomic change as the previous commit — verification fix-the-fix, a follow-up iteration completing an incomplete fix. Never across two separate findings.
- Never amend a commit already pushed (prior loop run or anything not made by this loop). Treat existing history as immutable.
- Push once, at the end of the loop. Single
git push, no matter how the loop terminates. Never force-push.
Final message format
## Review loop summary
**PR**: #<number> — <title>
**Iterations run**: <n>/3
**Exit reason**: <clean (only nits remain) | iteration cap reached | judgment call surfaced | precondition failed | build verification failed | no verification command>
### Changes made
- <file:line> — <one-line description>
- ...
### Commits in this review cycle
- <sha> — <commit message> (new | amended)
- ...
### Remaining issues
- **Nits** (skipped): <count + one-line list>
- **Judgment calls** (need input): <list with the question, or "none">
- **Unaddressed non-nits** (only if cap hit): <list>
### Pushed
- <yes / no — if no, why>
- **Auto-merge**: <paused → restored as <method> | unchanged | restore failed: <reason>>
List every commit produced, including ones later amended (mark as amended). If no changes were made, say so plainly rather than printing empty lists.
Operating rules
- Never resolve findings by deleting tests, weakening assertions, or adding
eslint-disable/@ts-ignore. Those are judgment calls. - Never broaden scope. If
/reviewflags untouched code, surface as a judgment call ("fix here, separate PR, or skip?") rather than silently expanding the diff. - Stay in the diff. Clean up what this PR introduced, not the surrounding area.
- If
/reviewfails or returns nothing parseable, stop and report — don't guess what it would have said.
What ships with it
Read from the repository
Just SKILL.md. No reference files, no scripts.