从旧的 Git 提交中删除私有信息

Posted

技术标签:

【中文标题】从旧的 Git 提交中删除私有信息【英文标题】:Removing private information from old Git commits 【发布时间】:2011-01-14 14:10:23 【问题描述】:

我有一个使用 Git 进行版本控制的项目,我想将其开源,但其中包含一些特定于最初使用它的环境的私人信息。我将更改相关信息以从存储库中未包含的配置文件加载。我意识到我应该首先这样做,但是由于私人信息仍然存在于以前的提交中,我该如何从我的历史记录中删除它?我是否只需要根据最新的提交启动一个新的存储库并丢失我的所有历史记录,或者有没有办法在删除任何私人信息记录的同时挽救当前的存储库?

编辑:澄清一下,我不想完全删除包含此私人信息的文件,因为它们仍在使用中。相反,我想删除/清除/更改其中某些字符串的出现。

【问题讨论】:

这能回答你的问题吗? How to substitute text from files in git history? 【参考方案1】:

我不久前为此编写了一个脚本。你可以在这里找到它:https://gist.github.com/dound/76ea685c05c4a7895247457eb676fe69

(可从archive.org查看原始文章:https://web.archive.org/web/20160208235904/http://dound.com:80/2009/04/git-forever-remove-files-or-folders-from-history/)

脚本建立在 git 附带的 git-filter-branch 工具之上。如果您好奇,可以阅读有关从 git repo here 删除文件的更多信息,但使用上面链接中的脚本应该很容易,并且您真正需要完成删除该私人信息。

【讨论】:

这看起来是一个很棒的工具,但我不确定它是否适用于我的情况。我的问题应该更清楚,但我要删除的是某些字符串的出现 - 我不想完全删除整个文件,因为这些文件仍在使用中。 哦,我明白了。这有点棘手。如果您在提交中输入了这些私有字符串,其中不包含您想要保留的任何其他内容,那么您可以使用 git-filter-branch 仅删除这些提交(而不删除文件)。我的脚本无法为您执行此操作,但如果您查看 git-filter-branch 的手册页,我想您会了解如何使用它来删除单个提交。 此外,您应该能够使用 git-filter-history 对您的文件应用自定义过滤器(脚本)。这听起来可能比简单地删除文件或提交要困难一些,但它应该做你想做的事(听起来比重新启动存储库并在向公众发布时丢失所有历史记录更好)。 如果要替换的文本包含不寻常的字符(即 $、\ 等 - 例如,使用更强的密码),为 git-filter 正确转义字符可能有点繁琐-分支。 ***.com/questions/18647400/… 是针对特定问题的问题。 @DavidUnderhill 上面的链接现在已经死了 - 可能想把它放在一个要点中【参考方案2】:

我建议使用BFG Repo-Cleaner,它是git-filter-branch 的更简单、更快的替代方案,专为从 Git 存储库中删除私有数据而设计。

usage instructions 给出了更详细的步骤,但核心只是:下载BFG's jar(需要 Java 6 或更高版本)并运行以下命令:

$ java -jar bfg.jar  --replace-text replacements.txt  my-repo.git

replacements.txt 文件应包含您想要执行的所有替换,格式如下(每行一个条目 - 请注意不应包含 cmets):

PASSWORD1 # Replace literal string 'PASSWORD1' with '***REMOVED***' (default)
PASSWORD2==>examplePass         # replace with 'examplePass' instead
PASSWORD3==>                    # replace with the empty string
regex:password=\w+==>password=  # Replace, using a regex

将扫描您的整个存储库历史记录,并且所有非二进制文件(大小小于 1MB)都将执行替换:任何匹配的字符串(不在您的 latest 提交中)都将被替换。

全面披露:我是 BFG Repo-Cleaner 的作者。

【讨论】:

以上是关于从旧的 Git 提交中删除私有信息的主要内容,如果未能解决你的问题,请参考以下文章

如何从旧提交创建新的 Git 分支? [复制]

在不使用反向补丁的情况下从分支中删除旧的 Git 提交? [复制]

如何删除旧的 git 历史记录?

要从gitlab repo中删除最新的提交,并删除旧的本地提交

如何在 Git 中标记较旧的提交?

在远程 squash 后提取旧的提交 ID