git log --all在筛选器分支中不起作用

问题描述 投票:1回答:1

我正在编写使用git filter-branch --tree-filtergit log --follow命令来检查在过滤过程中是否应保留或删除某些文件。

基本上,我希望保留包含文件名的提交,即使此文件已重命名和/或已移动

这是我正在运行的过滤器:

git filter-branch --prune-empty --tree-filter '~/preserve.sh' -- --all

这是我在preserve.sh内部使用的命令:

git log --pretty=format:'%H' --name-only --follow --all -- "$f"

结果是,当我在新路径中搜索文件时,将删除创建历史文件的提交,而该文件后来又移至另一个路径,这是不应该的。例如:

提交1:创建foo/hello.txt;

提交2:将foo/hello.txt移至bar/hello.txt

使用git filter-branch传递bar/hello.txt产生仅提交2的历史。

起初,我以为是因为我没有在--all中使用git log而发生问题,也就是说,在分析commit 1时找不到foo/hello.txt,因为它只是在查找过去没有提到bar/hello.txt的历史。但是后来我添加了--all,它可以查看所有提交(包括“未来”提交),但是没有任何变化。

我检出了要在其中创建文件的提交,运行了该日志命令,它就起作用了(列出了foo/hello.txtbar/hello.txt),因此没有任何问题。当它由filter-branch运行时,我还记录了log命令的结果,在这种情况下,我可以看到在commit 1中找不到该文件(仅列出了bar/hello.txt)。

我认为会发生此问题,因为git在内部将每个提交都复制到“新仓库”结构中,因此在分析commit 1时,较新的提交尚不存在。

是否有解决此问题的方法,或解决保留重命名/移动的重写历史记录的另一种方法?

我正在运行this answer中找到的脚本的修改版本。

git git-log git-filter-branch
1个回答
0
投票

或在保留重命名/移动的同时解决重写历史记录问题的另一种方法?

git filter-branch is soon deprecated起,考虑使用新的git filter-branch

但是即使是新工具(基于newren/git-filter-repo / newren/git-filter-repo)也不会跟随重命名的文件。

请参见git fast-export,它间接说明了在考虑重命名文件的同时(使用旧的git fast-export或新的git fast-import命令过滤存储库的挑战。

[...]这与git fast-importnewren/git-filter-repo issue 25newren/git-filter-repo git子命令的工作方式一致。例如。 git filter-branch不会显示该文件被重命名或复制的其他路径的任何历史记录(或文件的部分来源)。您专门使用了filter-repo标志,这是一个大技巧,甚至在rev-list文档中也提到过(它提到它仅在指定单个文件时有效)。如果log /fast-export/ git log -- src/ledger/bin/app/app.cc等具有重命名后的--follow选项,我可以简单地将其从git log中公开,但是尽管有这样一个选项的渴望,但没有人在许多情况下实现它年份。那里也有一些很好的挑战,例如我们可能需要遍历拓扑顺序,并且可能需要两次通过-一次创建拓扑顺序,第二次通过重命名建立其他路径。 (可能需要这样做的情况:某些分支建立在[rev-list]之上,并且在指定的pathspec中具有一些路径,这些路径来自在存在“ master”时对pathspec之外的内容进行重命名。如果存在“ master”在另一个分支之前被遍历,那么我们已经选择了更有限的pathspec并错过了额外需要的路径。)

但是,即使log在多个文件或目录或更多个目录的重命名之后实施,这仍然不一定足够,因为用户可能需要复制检测(即,不是从其他位置重命名的文件,而是它被复制)。但是,通过复制检测并不清楚是否要获取原件的完整历史记录。我可以想象在某些情况下您会,但在其他情况下不会。

并且,如果我们开始进行重命名或复制检测,那么我们将从定义明确的正确行为转变为启发式方法。对于差异,日志或什至合并,这很好,因为结果将由用户解释(即使在合并中,如果检测错误,用户也可以修正冲突并进行其他编辑)。在这里,我们用石头记录了启发式方法的结果。这让我有点担心...这也意味着我们必须打开一堆旋钮(至少要有一个相似性百分比,以及是否需要重命名以外的副本)才能进行配置。

所有这些,我在使用时也想要类似的东西。我想到的最好的折衷方案是让人们事先运行'fast-export',查看重命名子报表,然后根据该信息手动选择其他路径以供其执行filter-repo运行。--follow选项仍然具有filter-repo,但这对于该问题而言最基本。提供它并让用户决定要包括的内容(尽管我什至不担心复制检测),似乎是我所能得到的最好选择。

© www.soinside.com 2019 - 2024. All rights reserved.