Ail*_*ila 10 git merge github git-submodules merge-strategy
我的用例是:我有一个包含子模块的 repo 的两个分支。我想设置这两个分支的自动集成。但是每当两个分支上都有子模块更新时,我的自动集成脚本就会因子模块冲突而失败。有没有办法让 git 在合并期间忽略子模块指针的变化?或者为merge=ours给定的子模块提供类似的东西?
我在上面的页面中尝试了像这样的子模块文件夹的合并策略(但它只适用于文件)
submodule-name merge=ours
Run Code Online (Sandbox Code Playgroud)
说实话,我也很惊讶,但文档很快解释了发生的事情:
如果子模块历史发生了分歧,并且致力于超级项目中的分歧分支,[...]Git 甚至不会为您尝试进行简单的合并。
我猜“为什么合并策略不起作用? ”这个问题的答案是:因为不同子模块版本之间没有合并过程。如果您需要进行实际合并,文档建议的方法仍然不是那么复杂,但在您的情况下它甚至“更容易”。
假设你已经加入master并且你想加入my_branch其中。有3种情况:
git merge my_branch我已经链接的文档对此进行了很好的解释,因此我没有理由重复它。我仍然建议你阅读它,因为你可能会遇到意想不到的情况。我在答案的最后告诉你这一点。
git merge -Xours my_branch我不知道这是否是解决此问题的正确方法,但有一个非常简单的快捷方式可以清除子模块上的任何冲突。因为 git 不对子模块版本执行任何合并操作,所以它只告诉您不同的版本。所以,如果你查看索引,你仍然会发现 3 个版本来自 3 路合并
(输出git ls-files -s)
100644 acbc19aafbf0c14e67f9a437d465351a7e96388b 0 .gitmodules
100644 3da4fcc7b3a9bc886b50977dc35e10f48a42416b 0 your_files
160000 e826e1b762a17dbc7225b36db4a9f7f6c08774ad 1 submod
160000 fef2abfb901d20ba1f4d1023ba384bbc6afbc392 2 submod
160000 cd5caa8674fe078e0fb875861bb075ccb60cfee0 3 submod
Run Code Online (Sandbox Code Playgroud)
第一个 (e826e1b) 是合并基础,但您对索引为 2 的那个感兴趣。不幸的是,我认为您在将其添加到索引:2:./submod时无法使用 common 引用子模块修订版add,因为它不是真正的路径。我告诉过你的最简单的捷径就是这个:)
git add submod
然后你就可以了commit。它会自动保留master子模块版本,但这当然不是最好的方法,因为行为可能会在 git 的某些未来版本中发生变化。我将向您展示下一个场景的另一种方式。
git merge -Xtheirs my_branch这里事情变得复杂:我们不能使用上面的技巧(简单地add说,现在默认为master子模块修订版),因为现在我们需要索引为 3 的修订版,这:3:./submod不适用于该add命令。
您还可以使用 plumbing 命令更新索引update-index并传递原始缓存信息条目,例如:
git update-index --cacheinfo 160000,cd5caa8674fe078e0fb875861bb075ccb60cfee0,submod
Run Code Online (Sandbox Code Playgroud)
mode160000是用于子模块的模式(更具体地说是用于 git 链接),cd5caa86...是我们要添加到索引的对象,submod也是路径。奇怪的是,在这里输入子模块名称是有效的。如果您需要编写此脚本,显然您不能在那里放置硬编码对象,但您可以使用以下命令检索它
git rev-parse :3:./submod
Run Code Online (Sandbox Code Playgroud)
最后,这是运行以保留theirs子模块版本的命令:
git update-index --cacheinfo 160000,$(git rev-parse :3:./submod),submod
Run Code Online (Sandbox Code Playgroud)
相反,要保留ours版本,请替换:3:为:2:.
此外,这部分在参考文献中得到了很好的解释,但您需要非常小心。总之,git 不会尝试合并你的子模块,除非:
ours或theirs)。以我的拙见,git 团队应该添加一个选项,让我们更好地控制如何处理这些情况。顺便说一句,您始终可以先允许提交,然后再允许--amend它,或者在提交之前使用 修复它git merge --no-commit。在这两种情况下,您都不能使用索引修订版(如:2:./submod),但在第一种情况下使用 和 ,HEAD^1在第二种情况下使用 。如果这是一种非常不可能的情况,请跳过它,否则我会提交,如果可以接受的话。HEAD^2MERGE_HEAD--amend
我希望有一种更简单的方法来合并具有不同子模块修订版的分支,因此不要将此答案视为唯一的可能性。此外,合并后您可能需要deinit重新初始化(或重新sync)您的子模块,但就其可编写脚本而言,这不是真正的问题。如果我是你,我会创建一个包含所有这些操作的别名。
| 归档时间: |
|
| 查看次数: |
1108 次 |
| 最近记录: |