Git 进阶系列 | 7. Git 中的 Cherry-pick 提交

简介: Git 进阶系列 | 7. Git 中的 Cherry-pick 提交

Git 是最流行的代码版本控制系统,这一系列文章介绍了一些 Git 的高阶使用方式,从而帮助我们可以更好的利用 Git 的能力。本系列一共 8 篇文章,这是第 7 篇。原文:Cherry-Picking Commits in Git[1]


本系列的第5部分中,讨论了 rebase 和 merge。虽然git mergegit rebase之间有一些不同,但这两个命令的目标是相同的: 将一个分支的更改集成到另一个分支。


今天我们来看看git cherry-pick,理解它是怎样允许我们将任何分支中被选中的、单独的提交集成到当前的HEAD分支中。这与git mergegit rebase有很大的区别,两者都只能集成来自指定分支的所有新提交。


那么为什么要从一个分支中只选择一个提交集成到另一个分支呢?当然会有不同的原因,但其中一个特别的原因是撤消变更。假设我们不小心在错误的分支上做了一个提交,使用 cherry-pick 处理就不会有什么大问题。我们可以切换到正确的分支,然后 cherry-pick 对于的提交。


Git 进阶系列:


  1. 创建完美的提交
  2. Git中的分支策略
  3. 基于Pull Request实现更好的协作
  4. 合并冲突
  5. Rebase vs Merge
  6. 交互式Rebase
  7. Git 中的 Cherry-pick 提交(本文)
  8. 用 Reflog 恢复丢失的提交


在看实例之前,先警告一下: 不要对 cherry-pick 太过兴奋。你的主要目标应该是在分支级别工作,git mergegit rebase都是为次构建的。cherry pick 只是为了特殊场合,而不是为了代替 merge 和 rebase。


将提交移到另一个分支

image.png


我们通过一个真实的场景来解释什么时候 cherry pick 才是正确的。假设我们向master分支提交了一些本打算用于feature/newsletter的内容。现在怎么办?需要打电话给团队成员或老板来解释这个“错误”吗?


下面的截图显示了这个问题,以及在master分支上意外提交的26bf1b48


image.png


或者,如果在终端输入git log,可以在命令行看到这一情况:


$ git log
commit 26bf1b4808ba9783e4fabb19ec81e7a4c8160194 (HEAD -> master)
Author: Tobias Günther
Date:   Fri Oct 5 09:58:03 2018 +0200
    Newsletter signup page


可以看到,ID 为26bf1b48的提交最终合并到了master中,但其实应该提交到分支feature/newsletter中。我们需要选择特定的提交并将其移到正确的分支。首先切换分支,然后选择提交:


$ git checkout feature/newsletter
Switched to branch 'feature/newsletter'
$ git status
On branch feature/newsletter
nothing to commit, working tree clean
$ git cherry-pick 26bf1b48
[feature/newsletter 7fb55d0] Newsletter signup page
 Author: Tobias Günther <tg@fournova.com>
 Date: Fri Oct 5 09:58:03 2018 +0200
 1 file changed, 0 insertions(+), 0 deletions(-)
 create mode 100644 signup.html


再次运行git log,可以在feature/newsletter分支上看到新的提交:


$ git log
commit 7fb55d06a8e70fdce46921a8a3d3a9de7f7fb8d7 (HEAD -> feature/newsletter)
Author: Tobias Günther <tg@fournova.com>
Date:   Fri Oct 5 09:58:03 2018 +0200
    Newsletter signup page


这背后发生了什么?Git 在feature/newsletter分支上创建了一个具有相同更改的提交副本以及相同的提交信息。然而,这是一个有着新 ID 的全新提交。那么最初的提交呢?


清理其他分支


如果检查master分支,仍然可以看到“错误的”提交。这意味着 cherry pick 不会从原来的分支“移动”被选中的提交,而只是创建一个副本,不会影响原始文件。


现在,为了清理和撤销提交,可以使用git reset


$ git checkout master
Switched to branch 'master'
$ git reset --hard HEAD~1
HEAD is now at 776f8ca Change about title and delete error page


就像什么都没发生过一样。


如果使用像 Tower 这样的 GUI 应用,整个过程是这样的:


20daa03848e3784a106df42715d071e6.gif


用于特殊情况的工具,而不是日常的集成


只要可以使用传统的 merge 或 rebase,就应该这样做。Cherry pick 应该只在git mergegit rebase没用的情况下才用,比方说想要从一个分支把某个提交移到另一个。记住,git cherry-pick创建了“重复”的提交,应该在之后进行清理。


如果想更深入了解高级 Git 工具,可以免费查看“Advanced Git Kit[3]”: 这是关于分支策略、交互式 Rebase、Reflog、子模块等主题的短视频集合。


 

References:

[1] Cherry-Picking Commits in Git: https://css-tricks.com/cherry-picking-commits-in-git/

目录
相关文章
|
6月前
|
人工智能 数据可视化 开发工具
Git log 进阶用法(含格式化、以及数据过滤)
Git log 进阶用法(含格式化、以及数据过滤)
|
Shell 网络安全 开发工具
一些常用的 Git 进阶知识与技巧
一些常用的 Git 进阶知识与技巧
78 0
|
6月前
|
安全 Shell 网络安全
Git学习---Git快速入门、Git基础使用、Git进阶使用、Git服务器使用(IDEA集成GitHub、Gitee、GitLab)、GitHub Desktop客户端
Git学习---Git快速入门、Git基础使用、Git进阶使用、Git服务器使用(IDEA集成GitHub、Gitee、GitLab)、GitHub Desktop客户端
197 0
|
6月前
|
Java 程序员 开发工具
Git Cherry-pick 使用
Git Cherry-pick 使用
|
6月前
|
存储 Linux 开发工具
Python 进阶指南(编程轻松进阶):十二、使用 Git 组织您的代码项目
Python 进阶指南(编程轻松进阶):十二、使用 Git 组织您的代码项目
84 0
|
6月前
|
开发工具 git
git cherry-pick的使用
git cherry-pick的使用
125 0
|
持续交付 开发工具 git
如何保留原提交记录迁移Git项目,你还不知道吗?
如何保留原提交记录迁移Git项目,你还不知道吗?
如何保留原提交记录迁移Git项目,你还不知道吗?
|
6月前
|
Shell 开发工具 git
git 常用命令详解(merge/rebase/cherry-pick)
git常用命令详解。 git merge将已提交的commit(自历史记录与当前分支分开以来的提交)合并到当前分支中。 rebase变基的原理 git-cherry-pick能应用(合并)已经存在的commit,即选择合并某个特定commit
|
安全 网络安全 开发工具
Git的进阶操作,在idea中部署gie
Git的进阶操作,在idea中部署gie
107 0
|
前端开发 Cloud Native Go
《Git进阶:掌握版本控制的高级技巧》
《Git进阶:掌握版本控制的高级技巧》
68 0