在filter-branch --tree-filter之后从git repo中删除refs / original / heads / master


180

我有一个与此处询问的问题相同的问题:根目录中的新git存储库将一个存在的存储库包含在一个子目录中

我在这里按照以下答案进行操作:根目录中的新git存储库将子目录中的现有存储库包含在内

现在,gitk --all显示两个历史:一个以当前master为高潮,另一个是命名original/refs/heads/master

我不知道这第二个历史是什么,或者如何将其从存储库中删除。我的存储库中不需要两个历史记录。

我该如何摆脱呢?

重现自己:

mkdir -p project-root/path/to/module
cd project-root/path/to/module
mkdir dir1 dir2 dir3 
for dir in * ; do touch $dir/source-file-$dir.py ; done
git init
git add .
git commit -m 'Initial commit'

现在我们有了原始海报的问题。让我们使用上面链接的答案将git repo的根移到project-root:

git filter-branch --tree-filter 'mkdir -p path/to/module ; git mv dir1 dir2 dir3 path/to/module' HEAD
rm -rf path
cd ../../../ # Now PWD is project-root
mv path/to/module/.git .
git reset --hard

现在,看看我当前的问题:

gitk --all &
git show-ref

如何清除refs/original/heads/master所有关联的历史记录?


Answers:


320

refs/original/*是否有备份,以防您弄乱过滤器分支。相信我,这真的是好的主意。

检查结果后,如果您对自己想要的东西很有信心,则可以删除备份的参考:

git update-ref -d refs/original/refs/heads/master

或者,如果您对许多裁判都这样做了,而您想将其全部清除:

git for-each-ref --format="%(refname)" refs/original/ | xargs -n 1 git update-ref -d

(直接取自过滤器分支的联机帮助页。)

这不适用于您,但适用于可能会发现此问题的其他人:如果您执行过滤器分支以删除占用大量磁盘空间的内容,则您可能还希望运行git reflog expire --expire=now --all并使git gc --prune=nowreflog过期并删除现在未使用的对象。(警告:完全,完全不可逆。在操作之前,请务必确保。)


在执行update-ref,reflog过期和gc之后,这两个文件仍然引用原始ref:.git / info / refs和.git / packed-refs看起来也许应该这样说:git update-ref -d refs/original/refs/heads/master
12

1
我猜你不小心把这句话混在一起了:如果我是对的,那应该是git update-ref -d original/refs/heads/master?但是,只有您的第二条命令对我有用。
JJD 2012年

4
这是git update-ref -d refs/original/refs/heads/masterBTW。您可以使用查看全名git show-ref

4
那短些git show-ref refs/original/* --hash | xargs -n 1 git update-ref -d呢?
CharlesB

11

如果您使用的是Windows PowerShell:

git for-each-ref --format="%(refname)" refs/original/ | foreach-object -process { git update-ref -d $_ }

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.