Git 分支管理模型

单主干

单主干的分支实践(Trunk-based development TBD)在 SVN 中比较流行。 Google 和 Facebook 都使用这种方式。

trunk 是 SVN 中主干分支的名称,对应到 Git 中则是 master 分支。

TBD 的特点是所有团队成员都在单个主干分支上进行开发。 当需要发布时,先考虑使用标签tag,即 tag 某个 commit 来作为发布的版本。 如果仅靠 tag 不能满足要求,则从主干分支创建发布分支。 bug 修复在主干分支中进行,再 cherry-pick 到发布分支。

git-branch-01.png

GitHub flow

GitHub flow 是 GitHub 所使用的一种简单的流程。

该流程只使用两类分支,并依托于 GitHub 的 pull request 功能。

在 GitHub flow 中,master 分支中包含稳定的代码。 该分支已经或即将被部署到生产环境。 master 分支的作用是提供一个稳定可靠的代码基础。

任何开发人员都不允许把未测试或未审查的代码直接提交到 master 分支。 对代码的任何修改,包括 bug 修复、hotfix、新功能开发等都在单独的分支中进行。 不管是一行代码的小改动,还是需要几个星期开发的新功能,都采用同样的方式来管理。

当需要进行修改时,从 master 分支创建一个新的分支。 新分支的名称应该简单清晰地描述该分支的作用。 所有相关的代码修改都在新分支中进行。 开发人员可以自由地提交代码和 push 到远程仓库。

当新分支中的代码全部完成之后,通过 GitHub 提交一个新的 pull request。 团队中的其他人员会对代码进行审查,提出相关的修改意见。 由持续集成服务器对新分支进行自动化测试。

当代码通过自动化测试和代码审查之后,该分支的代码被合并到 master 分支。 再从 master 分支部署到生产环境。

git-branch-02.png

git-flow

git-flow 应该是目前流传最广的 Git 分支管理实践。

git-flow 围绕的核心概念是版本发布release。 因此 git-flow 适用于有较长版本发布周期的项目。

虽然目前推崇的做法是持续集成和随时发布。有的项目甚至可以一天发布很多次。 随时发布对于 SaaS 服务类的项目来说是很适合的。

不过仍然有很大数量的项目的发布周期是几个星期甚至几个月。 较长的发布周期可能是由于非技术相关的因素造成的,比如人员限制、管理层决策和市场营销策略等。

git-flow 流程中包含5类分支,分别是 master、develop、新功能分支feature、发布分支release和 hotfix。 这些分支的作用和生命周期各不相同。

master 分支中包含的是可以部署到生产环境中的代码,这一点和 GitHub flow 是相同的。

develop 分支中包含的是下个版本需要发布的内容。从某种意义上来说,develop 是一个进行代码集成的分支。 当 develop 分支集成了足够的新功能和 bug 修复代码之后,通过一个发布流程来完成新版本的发布。 发布完成之后,develop 分支的代码会被合并到 master 分支中。

git-branch-03.png

对于开发过程中的不同任务,需要在对应的分支上进行工作并正确地进行合并。 每个任务开始前需要按照指定的步骤完成分支的创建。 例如当需要开发一个新的功能时,基本的流程如下:

1.从 develop 分支创建一个新的 feature 分支,如 feature/my-awesome-feature

2.在该 feature 分支上进行开发,提交代码,push 到远端仓库。

3.当代码完成之后,合并到 develop 分支并删除当前 feature 分支。

在进行版本发布和 hotfix 时也有类似的流程。当需要发布新版本时,采用的是如下的流程:

1.从 develop 分支创建一个新的 release 分支,如 release/1.4

2.把 release 分支部署到持续集成服务器上进行测试。测试包括自动化集成测试和手动的用户接受测试。

3.对于测试中发现的问题,直接在 release 分支上提交修改。完成修改之后再次部署和测试。

4.当 release 分支中的代码通过测试之后,把 release 分支合并到 develop 和 master 分支,并在 master 分支上添加相应的 tag。

因为 git-flow 相关的流程比较繁琐和难以记忆,在实践中一般使用辅助脚本来完成相关的工作。 比如同样的开发新功能的任务,可以使用 git flow feature start my-awesome-feature 来完成新分支的创建,使用 git flow feature finish my-awesome-feature 来结束 feature 分支。 辅助脚本会完成正确的分支创建、切换和合并等工作。