如何撤消 git rebase interactive 的 sha 更改?

How can I undo a sha change from git rebase interactive?

我做了一个交互式变基,其中的提交比我需要更改的要多。我很惊讶不必要的更改的 shas 已更新。不幸的是,我只是在强制推送更新后才意识到发生了这种情况。

我做了什么

起点

X - Y \
A - B - C  *master (C is a merge commit)
         \
          - D - E *feature-branch

我的期望是一切看起来像这样:

X - Y \
A - B - C  *master
         \
          - D1 *feature-branch

当我去 PR 的时候,事情实际上是这样的:

X - Y \
A - B - C  *master
         \
          - A1 - B1 - C1 - D1 *feature-branch

其中 A1B1C1 具有与 ABC 相同的提交消息和更改, 但具有不同的 shas.

问题

如果您只想删除 A1/B1/C1,最简单的方法是执行 git rebase -i C。将 A1 标记为 'reword',将 B1 到 D1 标记为 'fixup'。将 A1 的提交消息编辑为您想要的最终消息。

现在,至于出了什么问题:C 是合并提交。

这意味着您的历史图表实际上可能如下所示:

   A - B - C  *master
          / \
...-X-Y-Z    - D - E *feature-branch

当你说 HEAD~5 时,它占用了 HEAD 的 first parent 五次。假设 C 的第一个父级是 Z 而不是 B。这意味着您将重新定位到提交 X,并且您在那里种植的提交之一是 A。新的 A 得到一个新的提交散列,因为它的祖先(可能还有它的内容)改变了。

您可能没有注意到 YZ 出现在变基交互式编辑器中 window,只是将它们保留为 pick

基本上,rebase 获取您的非线性历史并将其压缩成一条线。我不能说我建议在合并提交中使用变基。

如果您 运行 git revert 为 A1 - B1 - C1,您的新分支实际上就是您想要的分支。而且这个操作比较安全