我如何重写历史logging,以便除了已经移动的文件之外的所有文件都在子目录中?

我有一个项目下git 。 有一天,我将所有项目文件从当前目录移动到项目下的foo/bar/ 。 我用git mv 。 然后,我添加了一些更多的文件,并对已经存在的文件做了一些修改

因此,现在当我查看foo/bar/file.c的历史logging时,我只能看到我在移动文件后所做的更改。

我试图以各种方式解决这个问题( filter-branch与子目录filter等),但没有什么帮助,所以我在这里相当堆叠。 我会感谢您可以给我的任何帮助。 谢谢!

用移动的文件重写历史logging:

如果你想让项目的历史看起来像所有的文件一直在目录foo/bar ,那么你需要做一个小小的手术。 使用git filter-branch和“tree filter”来重写提交,以便在任何地方foo/bar不存在,创build它并将所有文件移动到它:

 git filter-branch --prune-empty --tree-filter ' if [ ! -e foo/bar ]; then mkdir -p foo/bar git ls-tree --name-only $GIT_COMMIT | xargs -I files mv files foo/bar fi' 

现在,历史logging将被logging为所有文件总是位于foo/bar

要查看移动文件的历史logging:

如果你只是想看看在过去的某个时间点被移动或重命名的文件的历史logging,那么只需使用--follow选项来git log

 git log --follow foo/bar/file.c 

总结这里是我所做的一个简短的总结。 为我工作的命令是:

 if [ ! -e foo/bar ]; then mkdir -p foo/bar; git ls-tree --name-only $GIT_COMMIT | grep -v ^foo$ | xargs -I files mv files foo/bar || echo ""; fi 

我在最后添加的echo命令确保即使mv失败,整个命令也会继续运行。 它没有移动foo / bar / foo的内容,但我可以忍受。

非常感谢Dan Molding (!!!)和Jefromi的帮助。