关于 gh-stack
用于管理堆叠分支和 Pull Request 的 GitHub CLI 扩展,面向按依赖关系拆分开发工作的团队。它支持线性分支栈的提交、同步、变基和按栈合并,并提供 JSON 状态输出。
主要功能
- 01创建并浏览线性分支栈
- 02提交分支并创建 PR
- 03同步远程栈并执行变基
- 04按 PR 或栈合并
- 05以 JSON 输出栈状态
适用场景
- 01将多阶段功能拆成依赖分支
- 02逐层提交代码供审查
- 03同步栈并处理分支变基
- 04按顺序合并关联 PR
安装
复制下面的命令,在终端中运行。
npx skills add https:/ / github.com/ github/ gh-stack --skill gh-stack安装后在 Claude Code 中输入/gh-stack确认已加载。
包含的文件
除 SKILL.md 外,安装时一起下载的参考资料和脚本。
references/commands.mdstack-design.mdtroubleshooting.md详细介绍
gh-stack
gh stack 是用于堆叠分支和拉取请求的 GitHub CLI 扩展。堆叠是以主干分支为根的有序分支链,每个分支都有一个基于其下方分支的 PR,因此审查者只会看到该层的差异。
gh stack 会从主干开始,从左向右打印堆叠:
(main) <- auth <- api <- frontend
左侧是底部,右侧是顶部。auth 基于 main,并最先合并;frontend 最后合并。up 朝顶部移动,远离主干;down 则朝主干移动。基础工作放在底部,依赖它的代码放在上方。有关如何选择各层,请阅读 references/stack-design.md。
设置
需要 Git 2.36+ 和已通过身份验证的 GitHub CLI。
gh extension install github/gh-stack
git config rerere.enabled true # remember conflict resolutions
git config remote.pushDefault origin # required if the repo has more than one remote
非交互式使用
gh stack 会根据 stdout 是否为 TTY 来选择行为。通过管道运行时,大多数命令会正常报错或打印静态文本;在 PTY 下运行时,相同命令会打开提示或全屏 TUI,并一直阻塞。不同 Agent harness 的行为各异,因此请始终传入下方的标志,不要依赖这种检测机制。
多个远程仓库: 除非已配置 remote.pushDefault,否则运行 push、submit、sync、rebase 或 link 时必须指定 --remote <name>。checkout 和 trunk 没有 --remote 标志,因此需要配置该项。
| 始终运行 | 切勿直接运行 | 原因 |
|---|---|---|
gh stack view --json | gh stack view | 在 PTY 下会打开 TUI |
gh stack submit --auto | gh stack submit | 每个新 PR 都会提示输入标题 |
gh stack merge <target> --yes | gh pr merge | gh pr merge 无法合并堆叠 |
gh stack init <branch>... | gh stack init | 会提示输入分支名称 |
gh stack add <branch> | gh stack add | 会提示输入名称,即使通过管道运行也会失败 |
gh stack checkout <target> | gh stack checkout | 会打开选择菜单 |
gh stack up / down / top / bottom | gh stack switch | switch 仅支持菜单操作 |
| — | gh stack modify | 仅支持 TUI,没有非交互式用法 |
view --short在两种模式下都安全,但输出格式面向用户。要解析输出,请使用--json。- 当其他本地堆叠已包含目标分支时,无法强制执行
checkout <pr>。 先运行gh stack unstack --local(这会保留 GitHub 上的堆叠),然后重试。 - 工作树: 本地堆叠共用一个公共目录目录。使用
--print-path配合导航命令或指定目标的checkout,以定位由其他工作树持有的分支,而不抢占其检出状态。未被占用的目标会优先在当前工作树中检出。更改目录前请检查退出状态;仅解析路径模式成功时的 stdout,切勿解析状态消息。
分支放置
- 开始多部分工作: 在编写文件前创建堆叠。不要先在主干上实现所有内容,再将其拆分。每层放置一个有依赖关系的关注点,从底部向上排列。
- 编辑现有堆叠: 编辑前先检出负责该更改的层。切勿在当前顶部提交属于较低层的关注点。运行
gh stack view --json;如果无法确定归属,请检查git log --all -- <path>。然后检出所属分支,编辑、提交、向上游变基,最后返回顶部。
gh stack down # or: gh stack checkout api
git add ... && git commit -m "Add get-user endpoint"
gh stack rebase --upstack # replay every branch above onto the change
gh stack top # return to where you were
gh stack push
核心循环
gh stack init auth # create the stack and check out its branch
git add ... && git commit -m "Add auth middleware"
gh stack add api # next layer, branched from the current one
git add ... && git commit -m "Add API routes"
gh stack submit --auto # push every branch and open draft PRs
gh stack view --json # confirm
在 submit 中添加 --open,即可创建可供审查的 PR,而不是草稿。分支名称会原样保留——gh stack add refactor/foo 会创建 refactor/foo。
保持同步
gh stack sync # fetch, reconcile with GitHub, rebase, push, refresh PR state
gh stack sync --prune # also delete local branches for merged PRs
非交互式运行时,只有指定 --prune 才会进行清理。如果本地堆叠与远程堆叠已分叉,sync 会打印两条链,不做任何更改,并以退出码 0 结束,同时显示 Sync aborted——请参阅 references/troubleshooting.md。
合并
使用参数限定合并范围:
gh stack merge 42 --yes # PR #42 plus every unmerged PR below it
gh stack merge 7 --yes # every unmerged PR in stack #7
gh stack merge 42 --yes --squash # or --merge, --rebase, --merge-method <method>
传入 PR 编号,可合并该 PR 以及所有排在它之后、尚未合并的 PR;传入堆栈编号,可合并该堆栈中所有尚未合并的 PR。该操作要么全部成功,要么全部失败:如果其中任何一个 PR 无法合并,则一个也不会合并。
如果不指定方法标志,则会沿用上次使用的方法。如果基分支使用合并队列,则会改为将整个堆栈加入队列,由队列决定合并方法,并忽略你传入的任何标志,同时给出警告;排队的 PR 可能会分成不同批次合并。
读取状态
gh stack view --json 会将 JSON 写入 stdout。状态消息会写入 stderr——不要解析这些消息,而应根据退出代码进行分支处理。
trunk string
currentBranch string
branches[] name, head, base, isCurrent, isMerged, isQueued, needsRebase
branches[].pr number, url, state ("OPEN" | "MERGED" | "QUEUED"); absent when no PR exists
base 是父分支保存的 SHA,表示此分支上次确认包含的父分支提交。它可能早于父分支当前的最新提交。若当前父分支最新提交已不再是此分支的祖先,则 needsRebase 为 true。
退出代码
| 代码 | 含义 | 恢复方法 |
|---|---|---|
| 0 | 成功 | — |
| 1 | 一般错误 | 查看 stderr |
| 2 | 不在堆栈中 | 运行 gh stack init,或运行 gh stack checkout <target> |
| 3 | 变基冲突 | 按照下方的退出代码 3 恢复步骤操作 |
| 4 | GitHub API 失败 | 检查 gh auth status,然后重试 |
| 5 | 参数无效 | 修正调用方式;参见 <command> --help |
| 6 | 需要消除歧义 | 分支属于多个堆栈;请切换到非共享分支 |
| 7 | 变基已在进行中 | 运行 gh stack rebase --continue 或 --abort |
| 8 | 堆栈文件已锁定 | 另一个 gh stack 进程正在写入;约 5 秒后重试 |
| 9 | 堆叠 PR 不可用 | 仓库未启用此功能;请告知用户 |
| 10 | 需要恢复修改操作 | 运行 gh stack modify --abort |
退出代码 3 的恢复步骤:
- 在运行
gh stack rebase后:解决文件冲突,运行git add,然后运行gh stack rebase --continue;运行gh stack rebase --abort可还原堆栈。 - 在运行
gh stack sync后:堆栈已还原。运行gh stack rebase重新触发冲突,然后按照上述步骤解决冲突并继续。
限制
- 堆栈严格线性:只有一个父分支,最多有一个子分支。并行工作请使用独立的堆栈。
rebase和sync会自动更新受影响的干净工作树;它们不会自动暂存更改,也不会创建或删除工作树。修改操作在整个克隆中串行执行;暂停的操作必须在其记录的所属位置恢复。modify支持分布式堆栈分支,但其编辑器仍仅支持 TUI。操作会在受影响的干净所属工作树中运行;未被占用的分支使用 origin。被丢弃或折叠的源分支和工作树会保留。恢复标志可从任何工作树运行,并使用记录的原生操作所属位置;除非诊断信息明确指出,否则切勿在调用方的工作树中解决冲突或暂存更改。- 不支持以非交互方式重新排序或移除。错误可能会建议运行
gh stack modify,但它仅支持 TUI——请改用unstack,然后运行init来调整结构。 - PR 标题和正文会自动生成。之后可使用
gh pr edit修改。
更多详情
关于标志和参数,以 gh stack <command> --help 为准。请注意,gh stack help <command> 无法使用——它会打印顶层帮助信息。
打开触发条件与任务匹配的参考文档;无需预先加载全部三份。
references/stack-design.md——创建堆栈、决定使用多少层、确定每层的内容,或判断工作是否应属于新堆栈之前,请阅读此文档。references/commands.md——命令意外失败,或需要了解其前置条件、副作用、原子性或顺序保证时,请阅读此文档。references/troubleshooting.md——发生变基冲突、压缩合并后、本地与远程分叉、调整堆栈结构,或通过其他工具操作堆栈时,请阅读此文档。