本文首发于 刘星的集体网站

Git 是目前世界上最先进的分布式版本控制系统。它使咱们更不便的跟踪,治理和组织代码。也帮忙了咱们更好的与其余开发者进行合作开发。然而没有规矩不成方圆。合作开发必须有一个标准来束缚各个贡献者的行为。这个标准就是 Git 工作流程(Git Workflow),也为咱们标准各个分支管理策略等行为。

Git 工作流程是无关如何应用 Git 以高效合作开发的规定或策略倡议,下文这些常见工作流程只是作为领导参考,这些工作流不是变化无穷的,咱们应该依据本人的项目选择或制订适合本人的工作流。

集中式工作流

首先咱们来介绍最简略粗犷的集中式工作流,如果你用过SVN,那么你能够无痛切换到 Git 集中式工作流。该工作流只用到 master 这一个主分支来保护咱们的代码,这也是该工作流的次要工作形式。

工作流程示例

1、首先 clone 近程仓库到本地

git clone ssh://user@host/path/to/repo.git

2、而后在本地的 master 分支做出批改实现开发后,创立一个提交

git status # 查看本地仓库的批改状态git add # 暂存文件git commit # 提交文件

3、而后推送到近程仓库

git push origin master

4、 如果此时本地仓库与近程仓库有了一致,Git 将回绝操作并报错。这时咱们就应该先 pull 近程仓库的批改到本地仓库后再解决从新推送

git pull --rebase origin master

5、如果有抵触,Git 会在合并有抵触的提交处暂停 rebase 过程,并报出错误信息,咱们在解决掉抵触后能够应用一下命令将更改退出暂存区后持续只能执行 rebase:

git add <some-file>git rebase --continue

如果遇到一个搞不定的抵触,这能够应用一下命令来终止 rebase

git rebase --abort

次要遵循原则

  • 只用到 master 这一个分支,所有的批改都推送到 master 分支
  • master 分支代表了我的项目的正式公布版本,所以提交历史应该被尊重且是稳固不变的
  • pull 代码时, 最好应用 rebase 而不是生成一个 merge commit

长处

  • 集中式工作流次要长处是简略,非常适合小型团队
  • 对于要从 SVN 迁徙过去的团队来说很敌对

毛病

  • 当您的团队规模扩充时,下面详述的抵触解决过程可能会成为瓶颈
  • 齐全没有施展 Git 的劣势,在理论应用 Git 合作的我的项目开发中很少应用集中式工作流

如果在稍大的团队中应用后面的集中式工作流,那么可能会在解决抵触中节约很多工夫。在理论开发中咱们基本上都是都 性能驱动式开发,基于性能需要,创立相应的分支进行开发,实现开发合并到主分支后再被删除掉。接下来咱们介绍的三个工作流:GitHub Flow,Git Flow 及 Gitlab Flow 都是基于不同的分支管理策略运作的。

GitHub Flow 工作流

GitHub Flow 是一个轻量级的基于分支的工作流程。它由 GitHub 在 2011 年创立。分支是 Git 中的外围概念,并且 GitHub 工作流程中的所有都以此为根底。

最重要的的一点就是:main / master分支中的任何内容始终都是可部署的。其余分支(性能分支)创立用于新性能和谬误修复的工作,并且在工作实现并通过查看后,这些分支将合并回到主分支中后删除。这些分支名应该是具备描述性的如 refactor-authentication, user-content-cache-key, make-retina-avatars

工作流程示例

1、首先 clone 近程仓库到本地

git clone ssh://user@host/path/to/repo.git

2、依据要实现的性能创立一个新的分支,分支名应该具备描述性,如实现鉴权性能:feature-auth

git checkout -b feature-auth

3、而后将新工作提交到该分支下,并定期将工作推送到近程仓库

# 创立一个commitgit status # 查看本地仓库的批改状态git add # 暂存文件git commit # 提交文件# 将分支推送到近程仓库git push --set-upstream origin feature-auth

4、当你须要帮忙或者反馈,或是你感觉你曾经实现该性能的工作筹备合进主分支的时候创立 pull request

5、当你的这部分工作在 pull request 中,被 review 以及 approved 后,则能够合并到主分支。

git checkout mastergit pullgit pull origin feature-authgit push

6、合并到主分支后,应立即对其进行部署

次要遵循原则

  1. master 分支中的任何内容都是可部署的
  2. 要进行新的工作,须要从主分支master 创立出一个分支,并给出描述性的名称(如:new-oauth2-scopes
  3. 本地的批改提交到该分支,并定期将你的工作推送到服务器上的同一命名分支
  4. 当你须要反馈或帮忙时,或者你认为分支已筹备好进行合并时,请关上一个Pull Request
  5. 在其他人 Review 并 Approved 该性能后,你能够将其合并到 master
  6. 合并并推送到后主分支master,你能够并且应该立刻进行部署

长处

  • 相比于前文介绍的集中式流程更为正当实用,能够缩小工作中的抵触
  • 因为工作流程的简略性,此 Git 分支策略对进行继续交付和继续集成很敌对。
  • 当须要在生产中保护单个版本时,它是现实的抉择
  • 这个 Git 分支策略非常适合小型团队和 Web 应用程序

毛病

  • 这种 Git 分支策略无奈同时反对多个版本的代码的部署
  • 没有解决部署、环境辨别、 releases、Bug 修复相干的问题
  • 生产代码容易变得不稳固

Git Flow 工作流

基于性能分支的工作流是一中相当灵便的形式。然而问题也是有时候过于灵便。对于大型团队,经常须要给不同分支调配一个更具体的角色。 Git Flow 工作流是治理性能开发、预公布和保护的罕用模式。

Git Flow 是最早诞生并且相当风行的工作流程。它由 Vincent Driessen 于 2010 年创立。Git Flow 工作流定义了一个围绕我的项目公布的严格分支模型。尽管比 GitHub Flow 的性能分支工作流简单一点,但提供了用于一个强壮的用于治理大型项目的框架。

Git Flow 工作流没有用超出性能分支工作流的概念和命令,Git Flow 为不同的分支调配一个很明确的角色,并定义分支之间如何和什么时候进行交互。

工作流程示例

假如你曾经创立好了地方仓库,并且已将其 clone 到本地

1、首先咱们来从主分支创立一个开发分支 develop, 并推送到服务器

git branch developgit push -u origin develop

当前这个分支将会蕴含了我的项目的全副历史,而 master 分支将只蕴含了局部历史

2、接下来咱们开始开发新性能,基于 develop 分支创立新的性能分支

git checkout -b some-feature develop

并在本人的性能分支上进行开发、创立提交:

git status # 查看本地仓库的批改状态git add # 暂存文件git commit # 提交文件

3、当你在你的分支上实现工作,筹备好进行合并时,请关上一个 Pull Request,用于合并到develop分支。如果你的团队没应用 Pull Request 则能够间接合并到本地的 develop 分支而后推送到地方仓库。

git pull origin developgit checkout developgit merge --no-ff some-featuregit push# 删除本地分支git branch -d some-feature

并且在性能分支合并后应该立刻删除

4、当咱们的 develop 分支进行到须要公布时,须要从develop分支创立一个新的公布分支,命名为release-*release/*。这一步也确定了公布的版本号:

git checkout -b release-0.1.0 develop

这个分支是一个预公布的版本,只做 bug 修复、文档生成等面向公布的工作。新性能不再增加到这个分支上

5、通过一系列测试确认没有问题,筹备好了对外公布后,咱们须要将公布分支合并到 master 分支,并打下 tag

git checkout mastergit merge --no-ff release-0.1git push
git tag -a 0.1 -m "release 0.1 publish" mastergit push --tags

6、同时咱们还须要将这个公布分支合并回去 master 分支

git checkout developgit merge --no-ff release-0.1.0git push

最初咱们还须要删除掉这个公布分支 release-0.1.0

7、如果咱们的线上版本呈现问题时,就须要创立一个保护分支,用于疾速给产品打补丁。这个保护分支须要从master分支上创立,提交批改以解决问题,而后再间接合并回master分支:

git checkout -b hotfix-auth master

修复实现后将其合并到 master 分支

git checkout mastergit merge --no-ff hotfix-authgit push

同时打下新的 tag

git tag -a 0.1.1 -m "release 0.1.1 publish" mastergit push --tags

同样也须要将修复分支合并到 develop 分支

git checkout developgit merge --no-ff hotfix-authgit push

最初删除掉这个热修复分支

git branch -d hotfix-auth

次要遵循原则

它基于两个长期的次要分支:

  • 主分支 master 该分支蕴含生产代码。 该分支是稳固的公布版
  • 开发分支 develop 此分支蕴含预生产代码。所有的性能分支实现后须要合并到该分支

其次在开发中还有三种短期分支

  • 性能分支(feature branch)性能分支用于为行将公布的版本开发新性能。从develop分支中检出也必须合并回develop
  • 补丁分支(hotfix branch)补丁分支 用于修复线上 bug, 从 master 分支下面检出。修复完结当前,再合并进 master 和 develop 分支
  • 预发分支(release branch)预公布分支用于生成一个预公布版本进行测试 预公布分支是从 develop 分支下面分进去的,预公布完结当前,必须合并进 Develop 和 Master 分支。它的命名,能够采纳 release-*的模式。

长处

  • 整个我的项目生命周期内,分支状态非常洁净,各个分支各司其职
  • 分支的命名遵循零碎的模式,使其更易于了解
  • masterdevelop 分支别离记录公布和性能开发的历史
  • 因为有公布分支,其余暂不公布的性能的开发不受公布的影响,能够持续提交
  • 保护分支能疾速打补丁,不影响正在开发的性能
  • 当生产中须要多个版本时,它是现实的抉择

毛病

  • 较为简单
  • Git 历史记录变得不可读
  • 须要保护两个长期分支 masterdevelop
  • 不不便继续交付和继续集成

Gitlab Flow 工作流

GitLab Flow 是通过创立工作流 GitLab在 2014 年。它将性能驱动的开发和性能分支以及问题跟踪联合在一起。它是 Git Flow 与 GithubFflow 的综合。它汲取了两者的长处,既有适应不同开发环境的弹性,又有繁多主分支的简略和便当。GitLab Flow 和 GitHub Flow 之间的最大区别是 GitLab Flow 中的环境分支反对(例如stagingproduction),

GitLab Flow 的最大准则叫做"上游优先"(upsteam first),即只存在一个主分支master,它是所有其余分支的"上游"。只有上游分支驳回的代码变动,能力利用到其余分支。

GitLab Flow 分成两种情景来应酬不同的开发流程

继续公布

对于继续公布的我的项目,它倡议在master分支以外,再建设不同的环境分支,每个环境都会有对应的分支。比方,开发环境的分支是master,预发环境的分支是pre-production,生产环境的分支是production

  • 开发分支 master 用于公布到测试环境,该分支为受爱护的分支
  • 预发分支 pre-production 用于公布到预发环境,上游分支为 master
  • 正式分支 production 用于公布到正式环境,上游分支为 pre-production

如果生产环境(production)产生谬误,则要建一个新分支批改完后合并到最上游的开发分支(master)此时就是 Upstream first),且通过测试,再持续往 pre-production branch,要通过测试没有问题了才可能再往下合并到生产环境。

版本公布

对于"版本公布"的我的项目,倡议的做法是每一个稳固版本,都要从master分支拉出一个分支,比方2-3-stable2-4-stable等等。

再呈现 bug 后,依据对应的 release branch 创立一个修复分支,修复工作万和城呢个后,一样要按着上游优选的准则,先合并到 master 分支,通过测试能力到才可能合并到 release 分支,并且此时要更新小版本号。

工作流程示例

和之前一样。首先 clone 我的项目到本地

1、当咱们要实现新性能或是修复 bug 时。从 master 检出新的分支如:feature-auth

git checkout -b feature-auth

2、而后在该分支下进行工作,实现后创立提交

git status # 查看本地仓库的批改状态git add # 暂存文件git commit # 提交文件

推送代码到近程仓库,

git push origin feature-auth

3、代码推送到仓库后,自定运行 GitLab CI

4、当咱们开发实现筹备合并进 master 时,在 GitLab 上创立一个 Merge Request

5、我的项目管理者进行代码审查,通过后,合并到master

6、运行第二次 GitLab CI

7、通过相应的测试后,将master分支合并到stable,如果是新版本则创立一个新的stable分支

8、为stable打上 tag,并进行公布

次要遵循原则

  1. 应用性能分支,不间接提交(commit)到 master 分支
  2. 测试所有的提交,而不仅仅只在 master 分支上
  3. 在所有的提交上,运行所有的测试(如果你的测试工夫长于 5 分钟则让它们并行)
  4. 在合并到 master 之前执行代码审查,而不是预先审查
  5. 部署是主动的,并基于分支或标签(tag)
  6. 标签(tag)是由用户设置的,而不是由 CI 创立
  7. 公布(release)是基于标签(tag)的
  8. 永远不对已推送的提交(pushed commits)进行变基(rebase)
  9. 每个人都从 master 分支开始工作,指标也是 master 分支
  10. 在 master 分支中修改谬误,其次再到公布分支
  11. 提交信息(commit message)应体现用意

长处

  • 它定义了如何进行继续集成和继续交付
  • Git 历史记录洁净、易读

毛病

  • 相比拟于 GitHub Flow 更简单
  • 当须要在生产中保护多个版本时,它可能会像 Git Flow 一样变得复杂

总结及倡议

没有一个万能的适宜所有我的项目的 Git 工作流程及分支策略,无论最终抉择哪种策略,你都能够通过进一步的批改来优化它。就像前文所说的,Git 工作流程对咱们晋升团队生产力十分重要,在制订咱们的工作流程时,应该尽量合乎咱们的我的项目具体业务需要及开发环境。然而也有如下几点小倡议:

  • 长期分支不应该存在太久,每个分支应尽量放弃精简,用完即删
  • 工作流应该尽量简略,同时不便回滚
  • 工作流程应该合乎咱们的我的项目公布打算

参考链接

  • atlassian comparing workflows
  • What are GitLab Flow best practices?
  • A successful Git branching model
  • Understanding the GitHub flow
  • Introduction to GitLab Flow

本文完

欢送能够关注我的公众号,一起游玩。有技术干货也有扯淡乱谈

左手代码右手砖,抛砖引玉