Git 分支与工作流

让 Agent 把分支命名、合并策略、保护规则与 hotfix 路径写成新人可读的一页纸,并与实际平台设置一致。

默认主线(main 或等价 trunk)应始终处于「可部署」或「可发版候选」状态;功能分支寿命、与主线同步方式(rebase / merge)、以及是否 squash,都应在 SKILL 里写死,避免口口相传。

将「平台里实际配置的分支保护」与「文档里的流程图」对齐:必填评审、状态检查、线性历史、签名提交等按优先级列出,并写明例外审批与审计要求。

原则与主线

无论采用哪种流派,Agent 生成的约定都应回答:谁有权直接推主线、集成频率、冲突由谁在什么时间点消化、以及回滚与 cherry-pick 的默认策略。

  • 命名:是否强制 feat/fix/chore/ 等前缀,以及工单号(如 PROJ-1024)是否必须出现在分支名中。
  • 同步:长期分支如何定期与 main 对齐,避免「巨型合并」与隐性集成风险。
  • 权限:谁可绕过分支保护、紧急 hotfix 是否需要双人复核或事后补票。
# 分支命名规范与创建示例
# 格式:/-

# 功能开发
git checkout -b feat/PROJ-1024-oauth-refresh-fix

# 缺陷修复
git checkout -b fix/PROJ-2048-payment-race-condition

# 紧急补丁(从 main 或当前 release 分支拉出)
git checkout main && git pull
git checkout -b hotfix/v1.4.3-session-hijack

# 发布准备
git checkout -b release/v1.5.0

# 文档 / 重构
git checkout -b docs/update-api-auth-guide
git checkout -b chore/upgrade-node-18

# ── Merge 策略选择(团队约定后写入 SKILL)──────────────────────
# Squash merge(线性历史,推荐 Trunk-Based):
git merge --squash feat/PROJ-1024-oauth-refresh-fix

# Rebase + Fast-forward(保留原子提交,需 commit 已规范):
git rebase main && git merge --ff-only

# Merge commit(保留分支上下文,常见于 GitFlow release/hotfix):
git merge --no-ff hotfix/v1.4.3-session-hijack -m "Merge hotfix v1.4.3"
写作提示:若团队同时维护多版本(LTS),在 SKILL 中单开一小节写「版本线 ↔ 分支/tag ↔ CI 任务」的对应关系,避免 Agent 把 hotfix 画到错误的维护分支上。

Trunk-Based 与 GitFlow:何时用哪一种

二者并非互斥标签,而是集成节奏与发布责任的两种常见打包方式。在 SKILL 里应写清「我们更接近哪一种」以及允许的例外(例如发布窗口内临时冻结)。

  • 更倾向 Trunk-Based Development:小步高频合并进主线;功能用短生命周期分支或特性开关隐藏未完成代码;CI 对 main 持续绿;适合交付节奏快、自动化测试与发布流水线成熟的小型到中大型团队。
  • 更倾向 GitFlow(或其裁剪版):需要长期 develop 集成线、明确发布分支与版本并行;适合发布周期固定、需严格区分「下一版集成」与「线上修复」的组织——但分支与合并成本更高,需在文档中写清谁负责合并与删枝。
决策参考:若「从合并到上线」通常小于几天、且主干几乎总能保持可部署,优先在 SKILL 中描述为 Trunk-Based,并单独列出发布 tag 与 hotfix 规则。若存在多条并行发布线或强合规门禁,再显式引入 develop / release/* 等结构。

分支拓扑与合并节奏

下图是经典 GitFlow 的简化示意;若团队已裁剪(例如取消 develop、仅保留 main + release/*),应在 SKILL 中重画等价拓扑并标注「已废弃」的边。

  main (生产 / 仅经发布合并)
    ●──────────────●──────────────●  tag: v1.2.0 …
    ↑ \            ↑              ↑
    │  \  hotfix   │  release/*   │
    │   *──*───────┘   只收修复    │
    │                              │
 develop (日常集成)                 │
    ●───●───●───●───●──────────────┘
     \   \   \   \
      \   \   \   └── feat/fix 分支(短周期,合并回 develop)
       \   \   \
        └───┴── 可选:长期 topic 分支(须写清同步策略)

对 Trunk-Based,可改为「所有功能分支直接对 main 开 PR、合并前 rebase(或 merge)」的单 hub 图,并写明每日/每周与主线对齐的最低频率。

  [ 功能分支准备合并 ]
            │
       ┌────┴────┐
       ▼         ▼
  偏好线性历史   偏好保留合并上下文
  (常配合       (保留 merge commit
   squash)       与分支拓扑)
       │         │
       ▼         ▼
  rebase 后 fast-forward    merge --no-ff(或平台等价选项)
       │         │
       └────┬────┘
            ▼
    [ 通过 CI + 评审 + 分支保护 ]
            ▼
         进入主线

保护规则与权限

按「阻断级」排序写出规则,便于 Agent 生成检查清单时与 GitHub/GitLab 等平台的设置项一一对应。

  • 主线:禁止 force push、要求 PR/MR、要求通过必需检查、要求 up-to-date 再合并(若启用)。
  • 评审:最少审批人数、CODEOWNERS 或路径级规则、是否禁止自批。
  • 合规:签名提交、禁止直接推敏感分支、审计日志保留要求。
# GitHub 保护分支配置(gh CLI)
gh api repos/myorg/myapp/branches/main/protection \
  -X PUT -H "Accept: application/vnd.github+json" \
  -f 'required_status_checks[strict]=true' \
  -f 'required_status_checks[contexts][]=ci/test' \
  -f 'required_status_checks[contexts][]=ci/lint' \
  -f 'enforce_admins=true' \
  -f 'required_pull_request_reviews[required_approving_review_count]=2' \
  -f 'required_pull_request_reviews[dismiss_stale_reviews]=true' \
  -f 'required_pull_request_reviews[require_code_owner_reviews]=true' \
  -f 'restrictions=null' \
  -f 'allow_force_pushes=false' \
  -f 'allow_deletions=false'

# CODEOWNERS 文件示例(.github/CODEOWNERS)
# 格式: @owner1 @owner2
*                       @myorg/core-team       # 默认所有文件
/src/auth/              @myorg/security-team   # 鉴权目录必须安全团队 review
/infra/                 @myorg/sre-team        # 基础设施需 SRE 审批
/src/payment/           @myorg/payment-team @myorg/security-team
*.sql                   @myorg/dba-team        # 所有 SQL 变更需 DBA 审批

发布、标签与 hotfix

发布分支与 tag 约定(SemVer、预发布 -rc、LTS 维护分支)若存在,应与 CI 发版流水线写在一起:谁打 tag、tag 是否触发部署、回滚是否走 revert 还是重打 tag。

hotfix 路径须写清:从哪条线拉出(mainrelease/x.y)、合并回哪些分支、是否必须双向上游合并以免漂移。

# 发布标签与 Hotfix 完整流程

# 1. 发布候选(Release Candidate)
git tag -a v1.5.0-rc.1 -m "Release candidate 1 for v1.5.0"
git push origin v1.5.0-rc.1
# CI 检测 -rc tag → 部署到 staging 环境

# 2. 正式发布(Production)
git tag -a v1.5.0 -m "Release v1.5.0: OAuth refresh fix + perf improvements"
git push origin v1.5.0
# CI 检测 v* tag → 触发生产部署流水线

# 3. Hotfix 流程(从 main 拉出)
git checkout main && git pull
git checkout -b hotfix/v1.5.1-cve-2024-1234
# ...修复代码...
git commit -m "fix(security): patch CVE-2024-1234 in auth middleware"

# Hotfix PR 合并到 main 后打 patch tag
git checkout main && git pull
git tag -a v1.5.1 -m "Hotfix v1.5.1: security patch CVE-2024-1234"
git push origin v1.5.1

# 若维护多版本线(LTS),还需 cherry-pick 到对应维护分支
git checkout release/1.4.x && git cherry-pick 
git tag -a v1.4.8 -m "Hotfix backport to v1.4.x"

# 4. 冲突解决策略
# theirs(接受传入):git checkout --theirs path/to/file && git add .
# ours  (保留本地):git checkout --ours   path/to/file && git add .
# manual(手动编辑):打开文件解决 <<<< ==== >>>> 冲突标记

SKILL 大纲(供 Agent 生成团队约定)

---
name: git-branch-workflow
description: 分支命名、Merge 策略、保护规则与 Hotfix 路径
version: 2.0
---
# 工作流选型
- GitHub Flow(Trunk-Based):短分支直接对 main 开 PR
- GitFlow 变体:main + develop + release/* + hotfix/*
- 决策:合并到上线 < 3 天 → GitHub Flow;多版本并行 → GitFlow

# 分支命名约定
- feat/<ticket>-<description>  (新功能)
- fix/<ticket>-<description>   (缺陷修复)
- hotfix/v<x.y.z>-<keyword>   (紧急补丁,从 main 拉)
- release/v<x.y.z>             (发布分支,只收修复)
- chore/ docs/ refactor/        (无用户可见变更)

# Merge 策略
- Squash merge:线性历史,Trunk-Based 推荐
- Rebase + FF:保留原子提交,需 commit 已规范
- Merge --no-ff:保留分支上下文,GitFlow release/hotfix

# 保护规则(main 分支)
- force push 禁止,PR 必须,required checks: ci/test + ci/lint
- 最少 2 个 approvals,CODEOWNERS 路径覆盖
- 冲突解决:manual > ours > theirs(按语义选择)

分支命名自检

下方默认规则与文中示例一致:前缀为 featfixchoredocshotfixrelease,后跟 / 与不含空格的描述段(可含字母数字、连字符、下划线、点)。可按团队模板改写 SKILL 中的正则后再同步修改本页脚本。

本机草稿:输入框内容会在你离开本页或关闭标签前写入浏览器 localStorage(键名 vvskill-git-workflow-branch-draft),下次打开本页自动还原,便于对照团队规范反复修改示例分支名。

返回技能库 更多技能入口