压缩旧的git提交记录(不包括最新的提交记录)

45

我的git历史非常混乱。我想把一堆较早的提交压缩成一个(不包括最后一个)。

我知道如何压缩我的最后n个提交。但这是不同的。这里我有连续的提交n1到n2,我想将它们压缩成一个,而在n2之后,我有一系列的提交历史,我想保留到最后一个。

因此,如果我的当前历史看起来像这样:

---- n1 --- n2 -------- m

我希望将n1压缩到n2,使其最终看起来像这样:

Translated text:

我希望将n1压缩到n2,使其最终看起来像这样:

---- n1n2 -------- m

其中n1n2是一个包含从n1n2的压缩内容的单个提交。

我该如何操作?对于从n2m的历史记录会有什么影响?

也就是说,由于我想要做的事情,从n2m的每个提交的哈希值是否会发生变化?


1
  1. 交互式变基,请参见https://git-scm.com/book/en/v2/Git-Tools-Rewriting-History。
  2. 从n1开始的每个提交,也会被重写,是的。
- jonrsharpe
@jonrsharpe 确认一下,从 n2+1m 的所有提交也会得到新的哈希值吗? - a06e
1
是的,因为它们现在都有新的父提交。 - jonrsharpe
@jonrsharpe,因此提交“1,...,n1”将保留它们的哈希值,即使其中一些包含在交互式变基中但使用“pick”。 - a06e
不一定,提交中包括时间戳等几个要素:https://dev59.com/P2Ag5IYBdhLWcg3wQ5Il#28917694。 - jonrsharpe
1个回答

52

根据文档这篇博客文章,你可以进行交互式的rebase。

  1. 开始一个交互式 rebase:

    git rebase -i HEAD~n
    
  2. (其中,n 是你想要回溯历史的步数)

  3. 你的默认编辑器将会打开。在顶部,以相反的顺序显示你最近的 n 次提交记录。例如:

  4. pick a5f4a0d commit-1
    pick 19aab46 commit-2
    pick 1733ea4 commit-3
    pick 827a099 commit-4
    pick 10c3f38 commit-5
    pick d32d526 commit-6
    
  5. 指定squash(或快捷键s)用于需要合并的所有提交。例如:

  6. pick a5f4a0d commit-1
    pick 19aab46 commit-2
    squash 1733ea4 commit-3
    squash 827a099 commit-4
    pick 10c3f38 commit-5
    pick d32d526 commit-6
    

    Git会把这个变更和紧接着的前一个变更合并,并让你把提交信息合并在一起。

  7. 保存并退出。

  8. Git将应用所有更改并再次打开您的编辑器以合并三个提交说明。 您可以修改提交消息,或者将其保持不变(如果是这样,所有提交的提交消息将被连接)。

  9. 完成了! 您选择的提交将全部与前一个提交合并为一个。


10
确认一下,在你提供的这个案例中,提交2、3和4将被压缩成一个单独的提交,我们称之为提交“2”。我的新历史记录将包含提交“1, 2, 5, 6”。此外,“1”将保留其原有的SHA-1值,但“2*, 5, 6”都将获得新的SHA-1哈希值。我理解的正确吗? - a06e
6
@becko 正确 -- 提交 2* 因为提交的内容已经改变而获得了新的哈希值;提交 5 和 6 获得了新的哈希值,因为它们的父提交 ID 已经改变。更多细节请参考:https://dev59.com/b4_ea4cB1Zd3GeqPQpxK#32854964 - ludovico
那么如果我已经将刚刚压缩的提交推送到远程,我该如何推送这个新的提交呢?在编辑提交信息后,我看到“您的分支和'origin/main'已经分叉,并且各自有4个和10个不同的提交。(使用“git pull”将远程分支合并到您的分支中)”。 - pretzlstyle
@pretzlstyle 交互式变基更改了 Git 提交历史记录。如果您已经推送并且正在与其他开发人员一起工作,应避免修改 Git 提交历史记录,因为它可能会产生重要的影响。如果您理解这些影响,“--force”将是一个选项(警告:“除非您绝对确定自己知道在做什么,否则不要使用 --force 标志”)。 - ludovico

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接