简体   繁体   English

如何在git中管理合并和重新定位?

[英]How do I manage merging and rebasing in git?

I git the purpose of rebase. 我给出了rebase的目的。 It makes sense to me. 对于我,这说得通。 Basically i I have a feature branch I'm working on and I'm ready to put it into the master branch I would do a rebase to squash all of my commits into one clean one so that it's easily integrated into master without all the messy history. 基本上我有一个我正在研究的功能分支,我准备把它放到主分支中我会做一个rebase来将我的所有提交压缩成一个干净的一个,这样它就可以很容易地集成到master中而不会让所有的混乱历史。 Right? 对?

Here's what we've been doing. 这就是我们一直在做的事情。

  1. Create a feature branch 创建功能分支
  2. Add a bunch of commits as we build the feature 在我们构建功能时添加一堆提交
  3. Periodically merge the master branch into the feature branch (in order to avoid a painful merge down the road) 定期将主分支合并到功能分支中(以避免在路上进行痛苦的合并)
  4. When everything is done, merge feature branch into master 一切都完成后,将功能分支合并到主服务器中

The problem I'm seeing is that periodically merging master into the feature branch causes problems when rebasing because now I have a bunch of master branch checkins mixed in amongst my feature checkins. 我看到的问题是,定期将master合并到功能分支会导致重新定位时出现问题,因为现在我的功能签入中混合了一堆主分支签到。

What's the right workflow here? 这里的工作流程是什么? Where do the following commads come into play: 以下逗号在哪里发挥作用:

  • git rebase -i Head^# git rebase -i Head ^#
  • git rebase master git rebase master
  • git merge master git merge master
  • git-rerere 混帐rerere
  • git reset --hard HEAD^ git reset --hard HEAD ^

You should only merge to/from master once, at the end of life of the branch. 在分支的生命周期结束时,您应该只与主服务器合并一次。 The idea of a feature/topic branch is that it only contains changes relevant to the feature; 功能/主题分支的想法是它只包含与功能相关的更改; you lose that when you merge in master repeatedly. 当你反复合并master时,你会失去它。 (You can read what Junio Hamano, the git maintainer, says about branches .) (你可以读一下git维护者Junio Hamano对分支的看法。)

You can do a "practice" merge, that you will throw away, and use git-rerere to have Git automatically record your merge resolutions, so that they can be re-used when you really are ready to merge. 你可以做一个“练习”合并,你将扔掉,并使用git-rerere让Git自动记录你的合并分辨率,以便在你真正准备合并时可以重复使用它们。 See http://www.kernel.org/pub/software/scm/git/docs/git-rerere.html for background and tutorial. 有关背景和教程,请参阅http://www.kernel.org/pub/software/scm/git/docs/git-rerere.html This is really cool because it lets you do the work of the merge, without committing it anywhere explicitly, and then get that work back "magically" when you really are ready to create the merge. 这真的很酷,因为它可以让你完成合并的工作,而无需在任何地方明确地提交它,然后当你真正准备创建合并时,“神奇地”恢复工作。 So, instead of one big painful merge at the end, you can do a bunch of smaller, hopefully simpler, intermediate "practice" merges along the way. 因此,在最后,您可以进行一系列较小的,希望更简单的中间“练习”合并,而不是最后一次大的痛苦合并。 Roughly speaking: 粗略地说:

# Enable rerere
git config --global rerere.enabled 1
# Start a feature branch
git checkout -b feature
# Hack hack hack
git commit
git commit
# Practice merge
git merge master
# ...then throw the merge commit away, the work is saved by rerere
git reset --hard HEAD^
# Hack hack hack
git commit
# Really merge to master, reusing any saved work from rerere
git checkout master
git merge feature
git branch -d feature

See also http://progit.org/2010/03/08/rerere.html for another tutorial. 另请参阅http://progit.org/2010/03/08/rerere.html以获取其他教程。

You can also periodically rebase your topic branch on top of master and then just do a merge at the end. 您还可以定期在master上重新分配主题分支,然后在最后进行合并。

To deal with a situation like the one where you are currently in, with a topic branch (say named feature ) that has a series of merges from main mixed with various in-progress commits, the easiest approach would be to do a squashed merge to produce a "merged" working tree and then create a new commit (or series of commits) on to main. 为了处理你当前所处的情况,使用一个主题分支(比如命名feature ),其中包含一系列与main混合的各种正在进行的提交,最简单的方法是将一个压缩合并到生成一个“合并”的工作树,然后在main上创建一个新的提交(或一系列提交)。 For example: 例如:

git checkout master
git merge --squash feature
git commit

This will produce a single commit that represents the state of the tree at the head of feature, merged into master. 这将生成一个提交,表示功能头部的树状态,合并为主。

Of course, you can also just do a regular merge to master for this change, leaving the messy history of feature present, and just work more cleanly in the future. 当然,你也可以做一个定期的合并,以master这种变化,留下的凌乱的历史feature现在,只是在今后的工作中更加干净。 eg, simply 例如,简单地说

git checkout master
git merge feature

and move on. 然后继续前进。

If you're going to rebase (which I suggest you do), then don't ever merge from master. 如果你要改变(我建议你这样做),那么就不要与master合并。 A rebase workflow is based on the idea that a topic branch consists of the path from master to the new feature and nothing else. rebase工作流基于以下想法:主题分支包含从主要到新要素的路径,而不包含任何其他内容。 As master moves forward, then your changes to get toward the new feature move with it. 当主人向前移动时,你对新功能的改变随之移动。

When you're finally ready to bring the changes into master, you have a two main options: 当您最终准备好将更改带入master时,您有两个主要选项:

  1. Rebase against master one final time, then do a normal fast-forward merge which essentially brings all your branch's commits into master one by one. 最后一次重新掌握master,然后进行正常的快进合并,这实际上将你所有分支的提交逐个引入master。 This keeps a more granular history, but if intermediate commits broke the build then you may prefer to squash them. 这保留了更细粒度的历史记录,但如果中间提交破坏了构建,那么您可能更愿意压缩它们。 Interactive rebase (-i) can help arrange these commits. 交互式rebase(-i)可以帮助安排这些提交。

  2. Use merge --squash to make a single commit in master that contains all the branch's changes. 使用merge --squash在master中进行单个提交,其中包含所有分支的更改。

无论如何你要重新定义分支,只要你想要“合并”变化,就可以进行重新定义。在准备好将该分支“合并”为主分支之前,你不必重新加注。

I believe the short answer is: 我相信简短的回答是:

use git merge --squash if: 使用git merge --squash if:

if you have a feature branch and you are pulling from another branch into that branch as you work, for instance you switch to feature and run git merge master periodically to merge in the master branch. 如果您有一个功能分支,并且在工作时从另一个分支进入该分支,例如,您切换到功能并定期运行git merge master以在主分支中合并。 Or you are pulling or pushing that branch to others or to a central repo like github. 或者你正在把那个分支拉到或推到别人或像github这样的中央仓库。

use git rebase if: 使用git rebase如果:

if you have a feature branch that you are not pushing or pulling to others, and you are not merging another branch into periodically, as described above 如果你有一个功能分支,你没有推或拉给别人,你没有定期合并另一个分支,如上所述

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM