Git 的 branch 操作详解
Git 教程之分支操作
分支理论
分支 (branch)
在开发软件时,可能有多人同时为同一个软件开发功能或修复 BUG,可能存在多个 Release 版本,并且需要对各个版本进行维护。Git 的分支功能可以支持同时进行多个功能的开发和版本管理。
分支是为了将修改记录的整体流程分叉保存。分叉后的分支不受其他分支的影响,所以在同一个数据库里可以同时进行多个修改。分叉的分支可以合并
在数据库进行最初的提交后, Git 会创建一个名为 main 的分支。因此之后的提交,在切换分支之前都会添加到 main 分支里。
之前默认是 master 分支。可以在命令行中进行修改:
git --version #查看版本 git config --global init.defaultBranch main #git在2.28.0上,重新设置git默认分支为main
分支的运用
分支 (“Merge 分支”和 “Topic 分支” ) 的运用规则。
Merge 分支
Merge 分支是为了可以随时发布 release 而创建的分支,它还能作为 Topic 分支的源分支使用。保持分支稳定的状态是很重要的。如果要进行更改,通常先创建 Topic 分支,最后合并到 Merge 分支上。通常,大家会将 master 分支当作 Merge 分支使用。
Topic 分支
Topic 分支是为了开发新功能或修复 Bug 等任务而建立的分支。若要同时进行多个的任务,则创建多个的 Topic 分支。
分支的切换
若要切换作业的分支,就要进行 checkout 操作。进行 checkout 时,git 会从工作树还原向目标分支提交的修改内容。checkout 之后的提交记录将被追加到目标分支。
HEAD
HEAD 指向的是现在使用中的分支的最后一次更新。通常默认指向 master 分支的最后一次更新。通过移动 HEAD,就可以变更使用的分支。
提交时使用~和^就可以指定某个提交的相对位置。最常用的就是相对于 HEAD 的位置。
HEAD 后面加上~可以指定 HEAD 之前的提交记录。
合并分支会有多个根节点,可以用^来指定使用哪个为根节点。
stash
还未提交的修改内容以及新添加的文件,留在索引区域或工作树的情况下切换到其他的分支时,修改内容会从原来的分支移动到目标分支。但是如果在 checkout 的目标分支中相同的文件也有修改,checkout 会失败的。这时要么先提交修改内容,要么用 stash 暂时保存修改内容后再 checkout。
stash 是临时保存文件修改内容的区域。stash 可以暂时保存工作树和索引里还没提交的修改内容,您可以事后再取出暂存的修改,应用到原先的分支或其他的分支上。
分支的合并
merge 或 rebase 两种方法。
merge
保持修改内容的历史记录,但是历史记录会很复杂。
使用 merge 可以合并多个历史记录的流程。
fast-forward(快进)合并
合并 bugfix 分支到 master 分支时,如果 master 分支的状态没有被更改过。
bugfix 分支的历史记录包含 master 分支所有的历史记录,把 master 分支的位置移动到 bugfix 的最新分支上,Git 就会合并。
如果设定了 non fast-forward 选项,即使在能够 fast-forward 合并的情况下也会生成新的提交并合并。
master 分支的历史记录有可能在 bugfix 分支分叉出去后有新的更新,则修改内容需要汇合起来,master 分支的 HEAD 会移动到该提交上。
rebase
历史记录简单,是在原有提交的基础上将差异内容反映进去。因此,可能导致原本的提交内容无法正常运行。
rebase bugfix 分支到 master 分支, bugfix 分支的历史记录会添加在 master 分支的后面。提交 X 和 Y 有可能会发生冲突,所以需要修改各自的提交时发生冲突的部分。
rebase 之后,master 的 HEAD 位置不变。因此,要合并 master 分支和 bugfix 分支,即是将 master 的 HEAD 移动到 bugfix 的 HEAD 这里。
一些建议:
在 topic 分支中更新 merge 分支的最新代码,请使用 rebase。
向 merge 分支导入 topic 分支的话,先使用 rebase,再使用 merge。
A successful Git branching model
来源:a-successful-git-branching-model
主分支
主分支有两种:master 分支和 develop 分支
mastermaster 分支只负责管理发布的状态。在提交时使用标签记录发布版本号。
developdevelop 分支是针对发布的日常开发分支。
特性分支
特性分支就是前面的 topic 分支。
这个分支是针对新功能的开发,在 bug 修正的时候从 develop 分支分叉出来的。完成开发后,把分支合并回 develop 分支后发布。
release 分支
release 分支是为 release 做准备的。通常会在分支名称的最前面加上 release-。release 前需要在这个分支进行最后的调整。
一般的开发是在 develop 分支上进行的,到了可以发布的状态时再创建 release 分支,为 release 做最后的 bug 修正。到了可以 release 的状态时,把 release 分支合并到 master 分支,并且在合并提交里添加 release 版本号的标签。
要导入在 release 分支所作的修改,也要合并回 develop 分支。
hotFix 分支
hotFix 分支是在发布的产品需要紧急修正时,从 master 分支创建的分支。通常会在分支名称的最前面加上 hotfix-。
例如,在 develop 分支上的开发还不完整时,需要紧急修改。这个时候在 develop 分支创建可以发布的版本要花许多的时间,所以最好选择从 master 分支直接创建分支进行修改,然后合并分支。
修改时创建的 hotFix 分支要合并回 develop 分支。
分支实践
创建分支
创建名为 issue1 的分支。
$ git branch issue1
查看当前分支
不指定参数直接执行 branch 命令。前面有*的就是现在的分支。
切换分支
执行 checkout 命令以切换分支。
创建分支并切换
$ git checkout -b <branch>
合并分支
执行 merge 命令以合并分支。
该命令将指定分支导入到 HEAD 指定的分支。先切换 master 分支,然后把 issue1 分支导入到 master 分支。
$ git checkout master Switched to branch 'master'
已经在 issue1 分支进行了编辑上一页的档案,所以 master 分支的 myfile.txt 的内容没有更改。
$ git merge issue1 Updating 1257027..b2b23c4 Fast-forward myfile.txt | 1 + 1 files changed, 1 insertions(+), 0 deletions(-)
master 分支指向的提交移动到和 issue1 同样的位置。这个是 fast-forward(快进)合并。
删除分支
在 branch 命令指定-d 选项执行,以删除分支。
用 rebase 合并
取消刚才的合并
rebase 合并
rebase 的时候,修改冲突后的提交不是使用 commit 命令,而是执行 rebase 命令指定 --continue 选项。若要取消 rebase,指定 --abort 选项。
$ git checkout issue3 $ git rebase master # 以master为基,合并issue3
在 master 分支的 issue3 分支就可以 fast-forward 合并了。切换到 master 分支后执行合并。
$ git checkout master $ git merge issue3
比较直接 merge 的记录
版权声明: 本文为 InfoQ 作者【timerring】的原创文章。
原文链接:【http://xie.infoq.cn/article/aaffcf66395452f9337f76cdd】。未经作者许可,禁止转载。
评论