【发布时间】:2020-10-05 08:13:58
【问题描述】:
注意:有一个类似的问题How to keep commit hashs not change when use git filter-repo rewrite the history,但答案集中在 Git 无法做到这一点。在这个问题中,我想探讨理论上是否可以编写一个自定义脚本来保留提交哈希。
Git filter-branch 和 BFG Repo-Cleaner 是从回购历史中删除大文件和其他内容的两个流行工具。它们导致不同的提交 SHA / 哈希,这就是 Git 的工作方式,因为它“指纹”了提交的内容、其父级等。
但是,我们遇到了不幸的大文件提交发生在不久前的情况,并且我们有各种对较新提交的引用,例如在 GitHub 问题(“查看提交 f0ec467”)和其他外部系统中。如果我们使用 filter-branch 或 BFG,很多东西都会坏掉。
所以我来这里询问是否有一些肮脏的低级技巧如何即使对于重写的提交也保留提交 ID/SHA-1。我想对于我们想要重写的错误提交,自定义脚本将创建一个 新的 Git 对象,但“硬编码”相同/旧的 SHA-1,跳过它的计算。我认为较新的提交(它的孩子/后代)应该继续工作(?!)。
如果这不起作用,我想了解为什么。 Git 是否会定期检查哈希值是否与实际内容一致?它是否只在某些操作期间这样做,例如 gc 或 push 或 pull?
(我知道这是一块非常薄的冰,我只是在技术上探索我们的选择,然后我们才能接受我们将永远在我们的存储库中拥有一个大型二进制文件,这会带来所有影响,比如永远拥有更大的备份、完整的克隆需要更长的时间等)
更新:现在有一个公认的答案,但同时,没有答案提到git replace,这可能是解决这个问题的方法吗?我做了一些基本的实验,但还不确定。
【问题讨论】:
-
唯一的办法就是破解SHA-1算法。见a related question。
-
也许可以hack Git 来实现你想要的,但我不推荐它。 Git 强制为重写的提交创建一个新的 SHA-1 以用于审计目的,因此很明显那里已经完成了一些工作。
-
@TimBiegeleisen 你知道它的任何细节吗?我还猜想它会在 some 情况下导致 some 问题,但我想知道 Git 何时验证 SHA-1 实际上是正确的。
-
"如果我们使用 filter-branch 或 BFG,很多东西都会坏掉。" 他们会吗?大概没有代码会破坏,只是 cmets 和问题中的引用。
-
您试图实现的正是像 SHA-1 这样的哈希函数旨在不允许您做的事情。因此,您尝试解决的问题比重写历史时可能遇到的问题要困难得多。找到在新旧提交哈希之间构建匹配表的最佳方法,您的临时问题得到“解决”
标签: git