Git强制将开发分支合并到主分支(覆盖所有本地文件)

Git强制将开发分支合并到主分支(覆盖所有本地文件),git,git-merge,merge-conflict-resolution,Git,Git Merge,Merge Conflict Resolution,我在主分支中有一个旧的、不同步的项目代码。几个文件已被删除、添加、重新编写和彻底编辑。我想强制将开发分支中稳定的最新代码合并到主代码中。我试图强制合并,但仍然会出现合并冲突 以下是我遵循的步骤: ➜ project git:(development) git checkout master ➜ project git:(master) git pull ➜ project git:(master) git merge -s recursive -X theirs development

我在主分支中有一个旧的、不同步的项目代码。几个文件已被删除、添加、重新编写和彻底编辑。我想强制将开发分支中稳定的最新代码合并到主代码中。我试图强制合并,但仍然会出现合并冲突

以下是我遵循的步骤:

➜  project git:(development) git checkout master
➜  project git:(master) git pull
➜  project git:(master) git merge -s recursive -X theirs development

CONFLICT (modify/delete): vendors/popup/magnific-popup.css deleted in HEAD and modified in development. Version development of vendors/popup/magnific-popup.css left in tree.
CONFLICT (modify/delete): vendors/popup/jquery.magnific-popup.min.js deleted in HEAD and modified in development. Version development of vendors/popup/jquery.magnific-popup.min.js left in tree.
CONFLICT (modify/delete): vendors/owl-carousel/assets/animated.css deleted in HEAD and modified in development. Version development of vendors/owl-carousel/assets/animated.css left in tree.

... several similar conflicts
我尝试对主分支中的所有文件执行
rm

➜  project git:(master) git reset --hard HEAD
➜  project git:(master) rm -rf *
➜  project git:(master) git merge -s recursive -X theirs development
仍然会有同样的冲突。我做错了什么

编辑:

下面是一个图表,可以更好地了解正在发生的事情。在某种程度上,不相关的历史也被推了出来


一个分支只是一个指针,
master
只是另一个分支。如果您没有在执行过程中合并更改,并且
dev
表示项目的当前稳定状态,那么可以避免您经历所有冲突的一个选项是:

git branch -m master <new-name>
git branch -m dev master
git分支-m主节点
git分支-m开发主机

可能需要调整跟踪关系,这取决于您设置遥控器的方式。

这将只将
主控
设置为与
开发
分支相同-主控中在上次合并
开发
后提交的任何内容都将丢失


git checkout-B master development

我认为您根本不想要这种合并。我认为你想要的是一个“他们的策略”合并,而Git没有提供。这仍然可以做到:看。但在使用之前,请继续阅读,确保这是您想要的


这里发生了两件重要的事情,这两件事都是由您的命令序列捕获的:

(我漏掉了一个没有任何作用的台阶)

首先,大多数合并(包括来自默认的
-s递归
合并策略的合并)都是通过找到一个共同的起点来工作的:一个共享的合并基提交。为了把它画成一个相当简单的例子,请考虑下面的提交图:

          C--D--E   <-- master (HEAD)
         /
...--o--B
         \
          F--G--H   <-- development
E和F的共同祖先是C、B和A,但C是最低的。F和G的共同祖先是B和A;B是最低的。Git的提交图是一个有向无环图或DAG,而不是一棵树,因此“LCA”不像树中那么简单,并且在一个图中给定两个节点时可以有多个LCA(或者根本没有LCA)。Git明智地处理了所有这一切,这在某种程度上是明智的定义

2Git将
-X
调用为策略选项,但这听起来与
-s strategy
参数完全相同。这实际上是战略的一种选择,因此Git的名字选择不当。我认为扩展选项是一个更好的名称,部分原因是它解释了
-X


如果您不想要
-X他们的
:请参阅我链接的其他答案 没什么好说的了:
-s-theres
曾经是Git合并策略。不再是了。你仍然可以通过多种方式合成它。实际上,我最喜欢的是中的卫浴命令

如果你真的想要
-X他们的
:为什么它会抱怨冲突? 我在上面提到过,将
git merge
的一部分合并到一起的合并过程“非常简单……但在某些细节上会变得很棘手。”您刚刚找到了其中一个细节

git通过区分找到的合并基而获得的大量
git diff
s,与您指定的两个提示提交中的每一个相比,都有许多文件被一方完全删除,但被另一方修改的情况:

...--B--o--o--...--o--o   <-- master (HEAD)
      \
       o--o--...--o--o   <-- development

Git将在第1阶段有一个条目作为名称(
vendors/popup/magnific popup.css
),在第3阶段有另一个条目(他们的),但在第2阶段没有条目(我们的)。要解决此问题,请使用
git add
将工作树中的第3阶段条目写入第0阶段的索引:
git add
将删除第1阶段和第3阶段的副本。您只需收集所有此类文件名,并将其全部传递给git add

如果您不想检查所有冲突,是否只想将开发分支作为新的主节点?停止删除文件?Git告诉您存在冲突,因为文件已被多次提交更改,它需要帮助确定您希望保留哪些更改。@evolutionxbox我希望保留最新提交的文件。@DeNovo这是一个可能的选项。不过我不想失去现有的master分支的历史。你关心master中的状态吗?这是非常详细的。您正确地提到了“…被一方完全删除,但被另一方修改的文件…”。这确实是我的用例。由于我对脚本不太熟悉,我不得不手动合并每个文件(超过150个),但最终还是成功了。
     A
     |
     B
   /   \
  C     D
 / \     \
E   F     G
...--B--o--o--...--o--o   <-- master (HEAD)
      \
       o--o--...--o--o   <-- development
CONFLICT (modify/delete): vendors/popup/magnific-popup.css deleted in HEAD and modified in development. Version development of vendors/popup/magnific-popup.css left in tree.