如何合并一个 git 分支,它只导致一次提交(比如使用 --squash),但允许未来的合并而不会发生冲突?

How to merge a git branch that results in only a single commit (like using --squash), but allowing future merges without conflicts?

我有一个分支,自创建以来其中有很多提交,我想使用单个提交进行单个合并提交以将其移回主分支。所以我知道的唯一解决方案是使用 git merge --squash branchname。这很好用,但是如果有人向 branchname 添加更多提交并且我再次将其合并到 master 中,我会从 branchname 上的初始新提交中得到冲突。如何防止合并冲突,同时仍然只在 master 中为每个合并保留一个提交?我已经研究过使用 git merge --no-ff 但这仍然将所有提交从 branchname 移动到 master.

echo $(git rev-parse $result $result^ $merged) > .git/info/grafts
git merge topic

其中 $result 是由压缩合并产生的提交,$merged 是您合并的提交(即给定 git checkout master; git merge topic$resultmaster,合并后$mergedtopic)。

info/grafts 文件包含临时的本地回购祖先覆盖。上面的 echo 记录,仅在此 repo 中,挤压合并的结果也将挤压合并提交作为其父项——即它记录了准确的合并历史。未记录的合并只有在两个分支的后续合并仍然以相同的方式看到合并的更改时才有效。

不要忘记 rebase 和 filter-branch 也会看到嫁接的祖先,如果他们重写 $result 提交,他们会在新提交中记录该祖先。


合并功能分支当然很常见,只是不记录它就不会这样做,因为这使得 git(或任何 vcs)不可能总能找到正确的合并基础。许多未记录的合并在历史记录中根本没有留下正确的合并基础,您必须创建一个才能在以后获得良好的合并。只要在进一步的修改掩盖匹配的更改块之前通过记录的合并来支付技术债务,Cherry-picks 和 squash 合并就很棒。

如果您要合并的历史很丑陋,您会喜欢交互式变基。它可以让您创建提交历史记录,如果您首先有远见地这样做的话。为发布清理更改是许多项目工作流程的基本组成部分。