使用 BFG Repo-Cleaner 修改 Git 提交历史

为什么要修改 Git 提交历史

修改 Git 历史,一般有以下两个原因:

  • 删除密码、API Key 等敏感数据,因为即使你在最新的提交删除了他们,在历史提交里也存在;
  • 删除超大文件。

超大文件问题经常出现在当你从一个 Git 托管网站换到另一个时,常因为后者不支持大文件,导致推送不上去。即使最新版删除了大文件,因为大文件存在在历史中,依然不能推送。

目前我测试几个网站的文件大小限制:

操作步骤

本文演示删除历史中的大文件步骤。

安装 bfg

如果是 MacOS,直接安装即可:

brew install bfg

如果是其他系统,可以下载 1.13.0 版的 jar 包,并将下面命令中的 bfg 替换成 java -jar path/to/bfg-1.13.0.jar

克隆仓库

git clone --mirror git@xxxxxx.com:jitao/project.git

这里使用 --mirror 参数,表示克隆出来的是一个 bare 仓库。

这一步最好备份一下仓库。

改历史

bfg --delete-files home.mp4 project.git

删除 home.mp4 这个文件,注意参数只能是文件名,不包含路径。如果传入一个路径,会报错:

Error: *** Can only match on filename, NOT path *** - remove '/' path segments

正常运行大概输出如下:

Using repo : /Users/jitao/workspace/project.git

Found 527 objects to protect
Found 2 commit-pointing refs : HEAD, refs/heads/master

Protected commits
-----------------

These are your protected commits, and so their contents will NOT be altered:

 * commit 9bbd9c4e (protected by 'HEAD')

Cleaning
--------

Found 336 commits
Cleaning commits:       100% (336/336)
Cleaning commits completed in 435 ms.

Updating 1 Ref
--------------

    Ref                 Before     After
    ---------------------------------------
    refs/heads/master | 9bbd9c4e | bc0c11c6

Updating references:    100% (1/1)
...Ref update completed in 24 ms.

Commit Tree-Dirt History
------------------------

    Earliest                                              Latest
    |                                                          |
    .............................DDDDDmmmmmmmmmmmmmmmmmmmmmmmmmm

    D = dirty commits (file tree fixed)
    m = modified commits (commit message or parents changed)
    . = clean commits (no changes to file tree)

                            Before     After
    -------------------------------------------
    First modified commit | 4021098d | ce77dc85
    Last dirty commit     | d73ece33 | e26922da

Deleted files
-------------

    Filename   Git id
    ------------------------------
    home.mp4 | 8ab9914d (114.1 MB)


In total, 187 object ids were changed. Full details are logged here:

    /Users/jitao/workspace/project.git.bfg-report/2020-03-15/15-02-30

BFG run is complete! When ready, run: git reflog expire --expire=now --all && git gc --prune=now --aggressive

信息的最后 bfg 还夹带了点私货:

--
You can rewrite history in Git - don't let Trump do it for real!
Trump's administration has lied consistently, to make people give up on ever
being told the truth. Don't give up: https://www.rescue.org/topic/refugees-america
--

呵呵。

清理仓库

cd project.git
git reflog expire --expire=now --all && git gc --prune=now --aggressive

推送

git push

参考文章

本文首发于微信公众号:肖念青,转载请保留原始出处信息。

我的个人网站:https://www.jitao.tech

©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容

  • 背景 Git 操作时,经常“不小心”上传一些不必要的(大)文件,或者私密数据,等等。 当然可以从本地把这些文件删除...
    不忘初心2017阅读 1,634评论 0 1
  • Git清理删除历史提交文件 既然来到这里,想必你认为你的Git工程已经处于臃肿状态了,一些很久之前引入的大文件,而...
    牧晓逸风阅读 22,976评论 7 10
  • git /gɪt/ 是一个开源的分布式版本控制系统 最初是 Linus Torvalds 为了帮助管理 Linux...
    TurboSnail阅读 1,307评论 0 0
  • 创建版本库 什么是版本库呢?版本库又名仓库,英文名repository,你可以简单理解成一个目录,这个目录里面的所...
    景岳阅读 823评论 0 3
  • 吃纤美善酵素片有什么优点和反应呢?原理是什么?吃酵素能减肥吗? 酵素也就是“酶”,减肥原理: 1:酵素补充了脂肪代...
    微澜董事洛洛阅读 311评论 0 0