Git 过滤分支 : keep only commits in subdir

标签 git git-filter-branch

我如何编辑分支的历史记录以仅保留影响特定子目录的提交(以及部分提交)?

基本上,我有一个大的仓库,其中有一些子目录是相当独立的,但不是完全独立的。过去,这些都是单独的存储库,但事实证明这是有问题的,因此我们将它们 merge 为 1 个存储库。这通常很好,但在 RoboCup 进行了一周的黑客攻击之后,我们希望将 1 个大分支拆分为几个较小的分支,以便于审查和单独的 pull 请求。

我在分支 robocup 上有子目录 challenge_gpsr,我想为其创建一个单独的分支。 robocup 是从 189bd987 分支出来的,因为我目前在分支 robocup 上,HEAD 指向最后的提交那个分支。

运行

git filter-branch -f --index-filter "git rm --ignore-unmatch --cached -qr -- . && git reset -q \$GIT_COMMIT -- challenge_gpsr" --prune-empty -- "robocup" 189bd987..HEAD

只留下challenge_gpsr,但这不是我想要的,也就是有其他目录,但它们的状态基本上应该是189bd987,而以下提交仅影响子目录 challenge_gpsr

如果可行,我将对其他子目录重复此方法,并且可以分别查看每个子目录。

最佳答案

我之前没有使用过 git filter-branch 也不知道它的存在所以谢谢你 :D,但我很确定我能看出这里出了什么问题...

Leaves only challenge_gpsr, but that is not what I want.

这就是我对您的过滤器命令的期望,请查看每个步骤:

# 1 Remove everything from root-tree (from the new revision)
git rm --ignore-unmatch --cached -qr -- .

# 2 Restore challenge_gpsr sub-tree (from original revision)
git reset -q \$GIT_COMMIT -- challenge_gpsr    

这针对 189bd987..HEAD 之间的每个修订运行,这将导致在 189bd987 之后的第一次提交删除 challenge_gpsr 之外的所有内容,之后,所有提交都将只修改 challenge_gpsr 下的对象。

...have the other directories as well, but their state should essentially be that at 189bd987

不是删除所有内容,而是将整个树恢复189bd987然后恢复子树challenge_gpsr >$GIT_COMMIT.

git filter-branch -f --index-filter " \
    git reset -q 189bd987 -- . && \
    git reset -q \$GIT_COMMIT -- challenge_gpsr \
" --prune-empty -- "robocup" 189bd987..HEAD

关于Git 过滤分支 : keep only commits in subdir,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/51506024/

相关文章:

Git 恢复一个大的 PUSHed 文件

带有 Windows 客户端的 ubuntu 机器上的 Git

android - 从git克隆后如何删除错误包名称和Gradle

git - Visual Studio git-push 到两个存储库

git - 我如何解释这个 git bisect 输出?

git - 将子目录分离(移动)到单独的 Git 存储库中

git - 在 git 中提取一个已重命名的子目录历史记录

git - 我如何重写历史记录,以便所有文件(我已经移动的文件除外)都位于子目录中?

git - 撤消 "git filter-branch ... -- --all"?在一个命令中?

git filter-branch 导致断开连接的历史记录 : how to get rid of the old commits?