Git 将功能正确合并到主功能中

Git 将功能正确合并到主功能中,git,svn,merge,Git,Svn,Merge,问题: 当涉及到几个相关的特性分支时,我总是遇到同样的问题 master ---A---B---C \ feature1 D---E---F \ feature2 G---H 我有这样的东西。假设这两个分支都已审核,我将把feature1合并到master。然后签出并拉入master,然后签出并将feature2重设为master。这样做,我总是一次又一次地看到同样的冲突,特别是在几个分支上 mas

问题:

当涉及到几个相关的特性分支时,我总是遇到同样的问题

master ---A---B---C
           \
feature1    D---E---F
                     \
feature2              G---H
我有这样的东西。假设这两个分支都已审核,我将把
feature1
合并到
master
。然后签出并拉入
master
,然后签出并将
feature2
重设为
master
。这样做,我总是一次又一次地看到同样的冲突,特别是在几个分支上

master ---A---B---C
           \
feature1    D---E---F
                     \
feature2              G---H
良好的重定基调:

我在网上看到,在上面的示例中,首先我应该这样做,以确保我正确地重新定基:

feature1
重设为
master

feature2
重设为新的
feature1
提交

我将使用git-rebase-on-feature1-feature1@{1}feature2来实现这一点

混乱:

据我所知,最好像这样重新设置基址,因为当您重新设置基址时,您的分支实际上将包含全新的提交(即上面的
F
F'
),这可能会导致不必要的冲突

考虑到所有这些,正确的方法是什么:

  • feature1
    合并到
    master
  • 功能2
    合并到主功能中`

我想尝试并学习一种推荐的方法,在这种方法中,我可以确信我不会每次都与几个从属分支发生痛苦的冲突。

注意,这个答案分为两部分。第一个是关于重新基础的机制,第二个是重新基础与合并

master ---A---B---C
           \
feature1    D---E---F
                     \
feature2              G---H
复杂地基的力学 我将使用git rebase--On feature1 feature1@{1}feature2来实现这一点

是:这是通过将参数拆分为rebase来实现的:它不再只是
feature1
,而是
——到feature1 feature1@{1}

通常,我们运行
git-rebase-name
,例如,
git-rebase-feature1
。我们必须首先
git签出功能2
。将
feature2
添加到命令末尾(如上所述)只会为我们执行这一
git checkout
步骤。因此,在这里调用“normal”的情况下,
git-rebase
只有一个参数,通常是另一个分支名称,如
feature1

但是,
git-rebase
所做的是复制一些提交,要做到这一点,它需要知道两件事:

  • 复制内容(提交列表),以及
  • 把新副本放在哪里
只有一个参数,
feature1
,对这两个参数都起着重要作用。当它工作时,这很好,但是对于在已经重新基调的
功能1上重新基调
功能2
,它并不总是工作

它不起作用的原因(当它不起作用时)与您绘制的图形有关。你用一种奇怪的方式画它们,左边是分支名称。这种绘图具有误导性:它意味着每次提交都在一个分支上,这是不正确的

这又是第一张图:

master ---A---B---C
           \
feature1    D---E---F
                     \
feature2              G---H
问:提交
A
在哪个分支上?(诡计问题!)

所有的树枝上都有

master ---A---B---C
           \
feature1    D---E---F
                     \
feature2              G---H
绘制这些图时,应该将提交放在左边,标签放在右边,标签指向一个特定的提交,因为在Git中这些东西实际上就是这样工作的。这是相同的图表,重新绘制:

--A--B--C   <-- master
   \
    D--E--F   <-- feature1
           \
            G--H  <-- feature2
这就是
git-rebase
的split-up参数的作用

通常,Git会使用以下方法查找Git rebase将要复制的提交集:

git rev-list <argument>..<current-branch>
由于回流通常是不可见的,所以我们可以完全放下图表的下半部分

重设基础与合并 据我所知,最好像这样重新设置基址,因为

最好是个很滑的学期

重基有两个问题:

  • 它复制提交,然后放弃原件,取而代之的是新的副本。还有人有原件吗?如果是这样的话,你也给他们带来了困难:他们也必须放弃原件,取而代之的是新的副本

  • 它复制提交。新的副本至少与原件有些不同(否则它们实际上就是原件)。确切地说,副本之间有什么不同?重要吗?您是否在过程中破坏了某些东西,即引入了bug

使用
git merge
可以避免这些问题。相反,它插入了自己的问题:

  • 历史现在变得错综复杂。如果有必要弄清楚到底发生了什么,那么无论是谁在探索历史,都可能不得不看不起合并的两条腿。有些人认为,这是一个积极的,而不是消极的,因为这是真实的历史,而不是一个后来,清理,人工历史

    (我倾向于支持经过清理的历史,但这一论点的双方都有好处。)

  • 合并本身可能会引入bug

如果您有一组非常好的测试,这将有助于解决这两个“引入bug”问题

如果它足够有用,它只会留下一个重定基础问题(假设你足够聪明,或者有一个很好的工具,来做你自己的复杂重定基础,就像这个例子):其他人有原始的吗?平衡你对这个问题的回答和你对纠结的历史是否糟糕的回答,以便决定合并还是重新基础


如果你没有很好的测试,那么…:-)

您的
Rebase feature2
图表有问题,并且不会因为上面显示的图表而产生问题。没有硬性规定,但在
主控
上重新设置
功能2
(将
功能1
合并到
主控
后)不一定会导致合并冲突。请记住,feature2的大部分功能已经在master中,并且从功能点重新应用了一些新的提交
                  G'-H'   <-- feature2
                 /
          D'-E'-F'   <-- feature1
         /
--A--B--C   <-- master
   \
    D--E--F   [reflog: feature1@{1}]
           \
            G--H  [reflog: feature2@{1}]