Help us improve
Share bugs, ideas, or general feedback.
From miranda
Reviews and squash-merges dependent GitHub PR stacks labeled 'oh-merge', building graphs, batch-reviewing diffs, rebasing, resolving conflicts, and checking CI.
npx claudepluginhub open-horizon-labs/bottle --plugin mirandaHow this skill is triggered — by the user, by Claude, or both
Slash command
/miranda:oh-mergeThe summary Claude sees in its skill listing — used to decide when to auto-load this skill
Like drummer, but for GitHub issue PRs (from oh-task) instead of ba task PRs (from mouse). Holistically review pending PRs, then squash-merge them as a cohesive batch.
Discovers open batch PRs from CHANGE_RECORD.json files, analyzes conflicts, determines optimal merge order, and executes user-guided merges on GitHub or Bitbucket.
Drives existing GitHub/GitLab PRs/MRs to merge: monitors CI/CD status, fixes issues in PR scope via sub-skills, handles multi-round code reviews, resolves comments until all requirements met.
Sequentially squash-merges a linear chain of stacked PRs into an epic branch, producing one squash commit per PR with dependency-ordered rebase and per-iteration user approval gates.
Share bugs, ideas, or general feedback.
Like drummer, but for GitHub issue PRs (from oh-task) instead of ba task PRs (from mouse). Holistically review pending PRs, then squash-merge them as a cohesive batch.
/oh-merge
Read dive context (if available) for project background:
cat .wm/dive_context.md 2>/dev/null || echo "No dive context"
Find all PRs with oh-merge label:
gh pr list --label oh-merge --json number,title,headRefName,baseRefName,additions,deletions
Only PRs with the oh-merge label are eligible for merge.
IMPORTANT: PRs with merge conflicts ARE eligible. The skill rebases and resolves conflicts in step 6. Do NOT skip PRs because of conflict status - that's exactly what this skill handles.
Build dependency graph and identify stacks:
baseRefName → [PRs targeting it]baseRefName = main (or master)main ← PR #42 (issue/123) ← PR #43 (issue/456)
main ← PR #44 (issue/789) [separate stack]
Select stack to process:
Batch review - evaluate all PRs in the selected stack together:
sg review on the combined changesMerge stack in dependency order (root first, then children):
For each PR in the stack, starting from the root:
a. Verify CI is passing:
gh pr checks <pr-number> --fail-on-error
If CI is failing, stop and report error.
b. Rebase onto its target branch:
git fetch origin
gh pr checkout <pr-number>
git rebase origin/<base-branch> # main for root, parent branch for children
c. Resolve any rebase conflicts (this is expected and normal):
d. Push rebased branch:
git push --force-with-lease
e. Squash merge:
gh pr merge <pr-number> --squash
f. For child PRs in the stack (after parent merged):
gh pr edit <child-pr-number> --base main
gh pr checkout <child-pr-number>
git rebase origin/main
git push --force-with-lease
g. On merge failure - If any PR in the stack fails to merge:
Note: Unlike drummer, no ba finish step is needed. GitHub automatically closes
linked issues when the PR merges (via "Closes #N" in the PR body).
When PRs target other PR branches (not main), oh-merge detects the stack and processes it:
Detection:
gh pr list --label oh-merge --json number,title,headRefName,baseRefName
baseRefName = main are rootsbaseRefName = issue/<number> are children targeting that parentGraph building:
adjacency[baseRefName] = [list of PRs targeting it]
Example:
adjacency["main"] = [PR #42, PR #44]
adjacency["issue/123"] = [PR #43]
Stack 1: main ← #42 (issue/123) ← #43 (issue/456)
Stack 2: main ← #44 (issue/789)
Merge sequence (for Stack 1):
gh pr edit 43 --base maingit rebase origin/main && git push --force-with-leaseAfter processing:
Before: PR #43 → issue/123 → main
PR #42 → main
PR #44 → main (separate stack)
After: PR #42 merged to main (issue #123 auto-closed)
PR #43 rebased onto main, merged to main (issue #456 auto-closed)
PR #44 remains for next oh-merge run
The holistic review checks what individual PR reviews can't:
oh-merge label (human approval gate)Note: The oh-merge label must be created in the repo. This is opt-in per repo.
oh-merge label foundCRITICAL: You MUST signal completion when done. Call the signal_completion tool as your FINAL action.
Signal based on outcome:
| Outcome | Call |
|---|---|
| Stack merged | signal_completion(status: "success", message: "Merged N PRs") |
| No PRs to merge | signal_completion(status: "success", message: "No PRs with oh-merge label") |
| Partial success | signal_completion(status: "error", error: "Merged N PRs, failed on PR #X: <reason>") |
| Unrecoverable failure | signal_completion(status: "error", error: "<reason>") |
If you do not signal, the orchestrator will not know you are done and the session becomes orphaned.
Fallback: If the signal_completion tool is not available, output your completion status as your final message in the format: COMPLETION: status=<status> message=<message> or COMPLETION: status=<status> error=<reason>.
$ /oh-merge
Finding PRs with oh-merge label...
Found 2 PRs:
PR #42 "Fix validation bug" (issue/123) → main (CI ✓)
PR #44 "Refactor validator" (issue/789) → main (CI ✓)
Building dependency graph...
Stack 1: main ← #42
Stack 2: main ← #44
2 independent stacks, processing Stack 1
Running batch review on Stack 1 (1 PR)...
Batch review complete: ✓ No issues
Processing PR #42 (Fix validation bug)...
Verifying CI... ✓
Rebasing onto main... clean
Squash merging... ✓
Issue #123 will auto-close on merge
Merge complete.
Merged: 1 PR (#42)
Remaining: 1 PR (#44 - queued for next run)
signal_completion(status: "success", message: "Merged 1 PR (#42)")
Done.
$ /oh-merge
Finding PRs with oh-merge label...
Found 3 PRs:
PR #42 "Fix validation bug" (issue/123) → main (CI ✓)
PR #43 "Add edge case tests" (issue/456) → issue/123 (CI ✓)
PR #44 "Refactor validator" (issue/789) → main (CI ✓)
Building dependency graph...
Stack 1: main ← #42 (issue/123) ← #43 (issue/456)
Stack 2: main ← #44
2 stacks found, processing Stack 1 (2 PRs)
Running batch review on Stack 1...
Collecting diffs: +547 -103 across 8 files
Batch review complete: ✓ No issues
Processing stack root: PR #42 (Fix validation bug)...
Verifying CI... ✓
Rebasing onto main... clean
Squash merging... ✓
Issue #123 will auto-close on merge
Processing stack child: PR #43 (Add edge case tests)...
Verifying CI... ✓
Updating base branch to main... done
Rebasing onto main... clean
Squash merging... ✓
Issue #456 will auto-close on merge
Stack merged.
Merged: 2 PRs (#42, #43)
Remaining: 1 PR (#44 - queued for next run)
signal_completion(status: "success", message: "Merged 2 PRs (#42, #43)")
Done.