最近有了一次代码弄错分支的经历,理解错误了领导的要求,在develop分支上辛辛苦苦撸了一通代码后开发出功能模块A,B,C,D。
要提测时发现弄错分支了,develop分支上的代码已经测试完成要上线了,新写的还只是提测阶段。
怎么办?一个办法就是,根据develop重新建一个分支,然后再把develop回退到之前的版本。
这种做法不是不行,但是有更好的办法,那就是git所提供的cherry-pick功能。
cherry-pick类似于一个定制化的merge,它可以把其它分支上的commit一个个摘下来,合并到当前分支。
举例来说,代码仓库有master和feature两个分支。
a - b - c - d Master
\
e - f - g Feature
现在将提交f应用到master分支。
# 切换到 master 分支
$ git checkout master
# Cherry pick 操作
$ git cherry-pick f
上面的操作完成以后,代码库就变成了下面的样子。
a - b - c - d - f Master
\
e - f - g Feature
废话不多说,直接上实例。
比如我现在有个文件a.c,我在develop分支完成了三个功能模块:feature A,feature B,feature C。
如下图:
现在只要feature A,feature B,我们现在用cherry-pick命令直接把feature A,feature B的提交合并到master分支里,如下操作:
可以看到,功能模块feature A,feature B已经被合并到master分支里。
请注意,合并到master分支里的提交哈希值发生了改变,与原来的不同。
可以看出,cherry-pick命令使用方法很简单,即:
git cherry-pick commitID
刚刚是一个个提交cherry-pick到master分支,但如果有100个commit要合并到master分支呢?总不能这样一个个操作吧?
git一样帮你想到了,它提供了一个区间操作方法。具体来讲是这样的:
git cherry-pick commit1..commit100
但是要注意,这是一个左开右闭的操作,也就是说,commit1不会被合并到master分支,而commit100则会。
这样的话上面的需求可以如下操作来实现:
注意:上面讲到cherry-pick命令每拣选一个commit就会提交一次生成一个新的commit id。
如果我们想让每个commit 拣选后暂缓提交,等到所有commit都拣选完成后,自己手动commit,应该怎么办呢?答案是用-n
选项:
怎样,是不是很简单?
cherry-pick的使用场景
-
合并单个提交:当我们只想应用某个分支上的一个提交到当前分支时,可以使用cherry-pick命令,而不需要合并整个分支。
-
修复bug:当我们在一个分支上修复了一个bug,并希望将这个修复应用到其他分支上时,可以使用cherry-pick命令。
-
提取特定功能:当我们在一个分支上开发了一个新功能,并希望将该功能应用到其他分支上时,可以使用cherry-pick命令。
示例1:合并单个提交
假设我们有一个分支feature,其中有一个提交abc123,我们想将该提交应用到master分支上。可以使用以下命令:
git cherry-pick abc123
这将在master分支上创建一个新的提交,包含与abc123相同的更改。
示例2:修复bug
假设我们在bugfix分支上修复了一个bug,并希望将这个修复应用到develop分支上。可以使用以下命令:
git cherry-pick bugfix
这将在develop分支上创建一个新的提交,包含bugfix分支上的修复。
示例3:提取特定功能
假设我们在feature1分支上开发了一个新功能,并希望将该功能应用到feature2分支上。可以使用以下命令:
git cherry-pick feature1
这将在feature2分支上创建一个新的提交,包含feature1分支上的功能。
cherry-pick的注意事项
在使用cherry-pick命令时,有一些注意事项需要了解:
cherry-pick会创建一个新的提交,因此可能会引入冲突。如果发生冲突,需要手动解决冲突后再继续应用提交。
cherry-pick只能应用一个提交,如果要应用多个提交,可以使用git rebase -i命令进行交互式变基。
cherry-pick不会自动合并提交的作者和提交日期,而是使用当前分支的作者和日期。如果需要保留原有的作者和日期信息,可以使用--no-commit选项,并手动修改提交信息后再提交。
ending.gif
网友评论