pr-captain-merge
Captain-only. Merge a PR safely — true merge commit (never squash, never rebase), branch protection respected, --principal-approved gate for --admin override. Prevents the "accidentally squashed via the wide GitHub UI button" failure mode that has burned the fleet.
适合你,如果你需要安全合并PR且避免意外压缩合并
npx oh-my-skill add the-agency-ai/the-agency/pr-captain-mergecurl -fsSL https://oh-my-skill.com/install.sh | bash -s -- the-agency-ai/the-agency/pr-captain-mergenpx oh-my-skill verify the-agency-ai/the-agency/pr-captain-merge怎么用
商店整理自技能原文 · 版本 dd2430b · 表述以原文为准Claude会安全地合并GitHub PR,总是创建真正的合并提交(不压缩、不变基),并尊重分支保护规则。只有使用--principal-approved参数才能启用管理员覆盖。
当Captain在master主检出分支上,且PR已通过CI、principal已批准时,由Captain直接调用或作为/pr-captain-land的一步触发。不能从工作树中触发。
技能原文 SKILL.md
<!-- allowed-tools omitted — inherits Bash() from .claude/settings.json. Subcommand-level restriction (e.g. Bash(gh pr merge )) silently blocked fleet agents in the past (flag #62/#63 / devex dispatch #171). This skill legitimately calls gh + agency/tools/pr-merge + agency/tools/git-* — narrow tool-level restriction would work but would need maintenance as called tools evolve. Inherit Bash(*) is safer. -->
pr-captain-merge
Captain's safe wrapper for merging PRs on GitHub. Always a true merge commit (no squash, no rebase). Respects branch protection by default. --principal-approved is the only way to engage --admin override.
Name pattern: pr- prefix groups with the PR skill family (autocomplete /pr<tab> shows the full kit), captain- qualifier makes captain-only scope visible at a glance.
Why this exists
Raw gh pr merge is too easy to misuse:
- GitHub's UI nudges toward squash (the wide button)
- The
--squashflag is one keystroke away from--merge --adminbypasses branch protection silently- Without discipline, the captain shipped 4 squash merges in one day (pre-v2 incident)
pr-captain-merge is the gate — skill-level enforcement plus the underlying agency/tools/pr-merge tool that does the actual work.
Required reading
Before running, Read the files in required_reading: frontmatter. GIT-MERGE-NOT-REBASE.md explains why we never squash or rebase. SAFE-TOOLS.md covers the safe-tool family this skill composes.
Usage
/pr-captain-merge <pr-number> /pr-captain-merge <pr-number> --principal-approved /pr-captain-merge <pr-number> --delete-branch /pr-captain-merge <pr-number> --dry-run
Preconditions
- Captain is on master in main checkout. Not in a worktree.
- PR number is known. Captain has verified PR is not in draft.
- CI has passed (or deploy-preview flake is understood and ignored).
- Principal has approved — either via GitHub review OR verbally in this conversation.
- For
--principal-approved: the principal's authorization is in THIS conversation. Do not infer from prior sessions.
If any precondition is missing, STOP. Ask the principal to resolve, or use the non-approved path and let branch protection block.
Flow / Steps
Step 1: Pre-flight
- Confirm the PR number (ask if missing).
- Confirm you're not on the PR's branch — captain merges from master or any non-PR branch.
- If you're going to use
--principal-approved, confirm the principal has authorized in THIS conversation. Don't infer from history. - Check for pending post-merge (C#372 Fix B). Run
./agency/tools/post-merge-state check. If exit 1, STOP — a prior PR was merged but its release hasn't been cut yet. Run/pr-captain-post-merge <pending-PR>first, then re-invoke this skill. New work cannot start while a prior PR is in pending state. Exit 0 → continue.
Step 2: Invoke the tool
./agency/tools/pr-merge <N>
Or with explicit principal approval (only when they verbally OK'd in-session):
./agency/tools/pr-merge <N> --principal-approved
Tool enforces:
--mergealways (never--squash, never--rebase)- Branch protection respected by default
--adminonly when--principal-approvedflag is present
Step 3: Handle the outcome
On success (exit 0): report merge URL + next-step recommendation (sync master via ./agency/tools/_sync-main-ref, or wait for /pr-captain-post-merge).
On branch-protection block (exit 3): tool prints the gate. Two resolutions:
- Ask principal to
gh pr review <N> --approvein GitHub UI, then re-run. - If principal authorized in this conversation but not GitHub UI, re-run with
--principal-approved.
On merge conflict (exit 1): resolve locally first:
gh pr checkout <N> ./agency/tools/git-safe merge-from-master --remote # resolve conflicts ./agency/tools/git-safe add <files> ./agency/tools/git-captain merge-continue ./agency/tools/git-push <branch> # then retry /pr-captain-merge <N>
Step 4: Post-merge (handoff or chain)
After successful merge:
- Sync local master:
./agency/tools/_sync-main-ref - If release PR: run
/pr-captain-post-merge(or/pr-captain-post-mergeonce refactored) to create GitHub release + fleet notification. - Notify affected agents:
/dispatch create --type master-updated --to <agent> - Notify cross-repo collaborators:
/collaborateif relevant
Failure modes
- CI failing: do NOT merge. Address the failure; restart from
/pr-prepor captain's diagnosis. - Merge conflicts on agent's branch: sent back for agent to resolve. Captain doesn't resolve agent's conflicts.
- Principal-approved flag without in-conversation authorization: DO NOT PASS. Ask the principal explicitly; wait for their OK; then pass the flag. Captain attests to something real.
- Squash or rebase attempted: blocked by tool. No way in the skill to request.
What this does NOT do
- Does not write commits — merge happens server-side at GitHub.
- Does not delete the local branch — that's captain's next decision (or
/pr-captain-post-merge). - Does not auto-tag a release — explicit
gh release createafterward (or via/pr-captain-post-merge). - Does not push — merge is server-side; no local push.
- Does not squash, does not rebase — blocked by the underlying tool (
agency/tools/pr-merge).
Why never squash, never rebase
Both rewrite history. The-agency framework is built on visible, append-only history:
- Branch commits are individually meaningful (QGRs, fixes, version bumps)
- Merge commits create a permanent record of integration
git log --graphshows the actual flow- Bisecting works against real commits, not synthetic squash blobs
Cost: heavier git log output. Benefit: you can SEE what happened and WHY, which is essential when fleet agents and adopters all have to read the same history.
Captain-only — three-layer defense
Defense in depth against accidental invocation from the wrong context:
paths: [](intentionally empty) — no file-path auto-activation; universally discoverable for the captain but scoped out of worktree contexts.- Name contains
captain-— any reader sees scope in the skill listing. - Runtime precondition — underlying
agency/tools/pr-mergechecks caller context before engaging--admin.
(Historically disable-model-invocation: true was a fourth layer. That flag was removed 2026-04-20 because the captain session IS the principal's session — DMI was blocking the captain from invoking captain-* skills. See REFERENCE-SKILL-CONVENTIONS.md §1.)
Status
active — ships as of agency-skill-version 2 adoption 2026-04-19. Replaces v1 pr-merge skill.
Related
/pr-captain-land— composite skill that calls this as its merge step/pr-prep— the QG-before-PR-create (agent-side)/pr-submit— agent hands branch to captain for landing/pr-captain-post-merge(TBD refactored to/pr-captain-post-merge) — release + fleet-notify after mergeagency/tools/pr-merge— the underlying safe-merge toolclaude/hookify/hookify.block-raw-gh-pr-merge.md— hookify rule that blocks baregh pr mergeagency/REFERENCE-GIT-MERGE-NOT-REBASE.md— the discipline rationale- the-agency#296 — PR lifecycle ownership (the-agency direction)
- the-agency#298 — skill refactor recommendation (the methodology)
OFFENDERS WILL BE FED TO THE — CUTE — ATTACK KITTENS!