git 如何将提交从一个分支复制到另一个分支?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/2474353/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-10 08:05:20  来源:igfitidea点击:

How to copy commits from one branch to another?

gitbranching-and-merging

提问by Bob Walsh

I've got two branches from my master:

我从我的主人那里得到了两个分支:

  • v2.1: (version 2) I've been working on for several months
  • wss: that I created yesterday to add one specific feature to my master (in production)
  • v2.1: (version 2) 我已经研究了几个月
  • wss:我昨天创建的,为我的主人添加了一个特定的功能(生产中)

Is there a way to copy yesterday's commits from wss to v2.1?

有没有办法将昨天的提交从 wss 复制到 v2.1?

采纳答案by Cascabel

You should really have a workflow that lets you do this all by merging:

你真的应该有一个工作流,让你通过合并来完成这一切:

- x - x - x (v2) - x - x - x (v2.1)
           \
            x - x - x (wss)

So all you have to do is git checkout v2.1and git merge wss. If for some reason you really can't do this, and you can't use git rebaseto move your wss branch to the right place, the command to grab a single commit from somewhere and apply it elsewhere is git cherry-pick. Just check out the branch you want to apply it on, and run git cherry-pick <SHA of commit to cherry-pick>.

所以你所要做的就是git checkout v2.1git merge wss。如果由于某种原因你真的不能这样做,并且你不能使用git rebase将你的 wss 分支移动到正确的位置,那么从某处获取单个提交并将其应用到其他地方的命令是git cherry-pick。只需检查您要应用它的分支,然后运行git cherry-pick <SHA of commit to cherry-pick>.

Some of the ways rebase might save you:

一些 rebase 可能会拯救你的方法:

If your history looks like this:

如果您的历史记录如下所示:

- x - x - x (v2) - x - x - x (v2.1)
           \
            x - x - x (v2-only) - x - x - x (wss)

You could use git rebase --onto v2 v2-only wssto move wss directly onto v2:

您可以使用git rebase --onto v2 v2-only wss将 wss 直接移动到 v2:

- x - x - x (v2) - x - x - x (v2.1)
          |\
          |  x - x - x (v2-only)
           \
             x - x - x (wss)

Then you can merge! If you really, really, reallycan't get to the point where you can merge, you can still use rebase to effectively do several cherry-picks at once:

然后就可以合并了!如果你真的,真的,真的无法达到可以合并的程度,你仍然可以使用 rebase 一次有效地进行几个挑选:

# wss-starting-point is the SHA1/branch immediately before the first commit to rebase
git branch wss-to-rebase wss
git rebase --onto v2.1 wss-starting-point wss-to-rebase
git checkout v2.1
git merge wss-to-rebase

Note: the reason that it takes some extra work in order to do this is that it's creating duplicate commits in your repository. This isn't really a good thing - the whole point of easy branching and merging is to be able to do everything by making commit(s) one place and merging them into wherever they're needed. Duplicate commits mean an intent never to merge those two branches (if you decide you want to later, you'll get conflicts).

注意:这样做需要一些额外的工作的原因是它正在您的存储库中创建重复的提交。这真的不是一件好事 - 轻松分支和合并的全部意义在于能够通过将提交放在一个地方并将它们合并到任何需要的地方来完成所有事情。重复提交意味着永远不会合并这两个分支的意图(如果您稍后决定要合并,则会发生冲突)。

回答by Benjamin Bannier

Use

git cherry-pick <commit>

to apply <commit>to your current branch.

申请<commit>到您当前的分支机构

I myself would probably cross-check the commits I pick in gitkand cherry-pick them with right-clicks on the commit entry there instead.

我自己可能会交叉检查我选择的提交,gitk并通过右键单击那里的提交条目来挑选它们。



If you want to go more automatic (with all its dangers) and assuming all commits since yesterday happened on wss you could generate the list of commits using git log(with --prettysuggested by Jefromi)

如果你想更自动化(有所有危险)并假设自昨天以来所有提交都发生在 wss 上,你可以使用git log--pretty由 Jefromi 建议)生成提交列表

git log --reverse --since=yesterday --pretty=%H

so everything together assuming you use bash

所以一切都在一起假设你使用 bash

for commit in $(git log --reverse --since=yesterday --pretty=%H);
do
    git cherry-pick $commit
done

If something goes wrong here (there is a lot of potential) you are in trouble since this works on the live checkout, so either do manual cherry-picks or use rebase like suggested by Jefromi.

如果这里出现问题(有很大的潜力),您就会遇到麻烦,因为这适用于实时结账,所以要么手动挑选,要么使用 Jefromi 建议的 rebase。

回答by Lyes CHIOUKH

git cherry-pick: Apply the changes introduced by some existing commits

git cherry-pick:应用一些现有提交引入的更改

Assume we have branch Awith (X, Y, Z) commits. We need to add these commits to branch B. We are going to use the cherry-pickoperations.

假设我们有(X, Y, Z) 提交的分支A。我们需要将这些提交添加到分支B。我们将使用这些cherry-pick操作。

When we use cherry-pick, we should add commits on branch Bin the same chronological order that the commits appear in Branch A.

当我们使用时cherry-pick,我们应该按照提交出现在分支A中的相同时间顺序在分支B上添加提交。

cherry-pick does support a range of commits, but if you have merge commits in that range, it gets really complicated

cherry-pick 确实支持一系列提交,但是如果您在该范围内有合并提交,它会变得非常复杂

git checkout B
git cherry-pick SHA-COMMIT-X
git cherry-pick SHA-COMMIT-Y
git cherry-pick SHA-COMMIT-Z

Example of workflow :

工作流程示例:

enter image description here

在此处输入图片说明

We can use cherry-pickwith options

我们可以使用cherry-pick选择

-e or --edit: With this option, git cherry-pick will let you edit the commit message prior to committing.

-e 或 --edit:使用此选项,git cherry-pick 将允许您在提交之前编辑提交消息。

-n or --no-commit: Usually the command automatically creates a sequence of commits. This flag applies the changes necessary to cherry-pick each named commit to your working tree and the index, without making any commit. In addition, when this option is used, your index does not have to match the HEAD commit. The cherry-pick is done against the beginning state of your index.

-n 或 --no-commit:通常该命令会自动创建一系列提交。此标志应用必要的更改来挑选每个命名提交到您的工作树和索引,而不进行任何提交。此外,使用此选项时,您的索引不必与 HEAD 提交匹配。樱桃挑选是针对索引的开始状态完成的。

Here an interesting article concerning cherry-pick.

这里有一篇关于cherry-pick.

回答by Charles Ma

You could create a patchfrom the commits that you want to copy and apply the patchto the destination branch.

您可以从要复制的提交创建补丁并将补丁应用到目标分支。

回答by Petr Sykora

Or if You are little less on the evangelist's side You can do a little ugly way I'm using. In deploy_template there are commits I want to copy on my master as branch deploy

或者,如果你在传道者方面稍逊一筹,你可以用我正在使用的一种丑陋的方式来做。在 deploy_template 中有一些提交,我想在我的 master 上复制作为分支部署

git branch deploy deploy_template
git checkout deploy
git rebase master

This will create new branch deploy (I use -f to overwrite existing deploy branch) on deploy_template, then rebase this new branch onto master, leaving deploy_template untouched.

这将在 deploy_template 上创建新的分支部署(我使用 -f 来覆盖现有的部署分支),然后将此新分支变基到 master 上,使 deploy_template 保持不变。

回答by zeroimpl

For the simple case of just copying the last commit from branch wss to v2.1, you can simply grab the commit id (git log --oneline | head -n 1) and do:

对于只是将最后一次提交从 wss 分支复制到 v2.1 的简​​单情况,您可以简单地获取提交 id ( git log --oneline | head -n 1) 并执行以下操作:

git checkout v2.1
git merge <commit>

回答by Gebb

The cherry-pick command can read the list of commits from the standard input.

cherry-pick 命令可以从标准输入读取提交列表。

The following command cherry-picks commits authored by the user John that exist in the "develop" branch but not in the "release" branch, and does so in the chronological order.

以下命令cherry-picks 由用户John 创作的、存在于“develop”分支中但不存在于“release”分支中的提交,并按时间顺序执行。

git log develop --not release --format=%H --reverse --author John | git cherry-pick --stdin