你怎么得到git bisect忽略合并的分支?

tdd*_*ing 34 git git-bisect

我知道git bisect在设计上是分支感知的,因此如果在良好提交,G和错误提交之间,B,你在一个分支中合并,它也需要考虑这些变化,因为bug可能被包含在分支中.

在我的情况下,我有一个依赖作为一个侧分支,我不时合并我的主项目的变化.依赖项可以被认为是一个库,它有不同的运行方式,不同的构建系统等来自我的主项目,但我仍然希望通过合并到主分支的最近更改.

问题是,在这种情况下,当你在依赖提交的提交中最终进行不可编译的提交时.

我真的只想在进行二分时将每个分支合并视为单个提交.

到目前为止我找到的一个解决方法是使用git log --first-parent制作一个有效提交G..B的列表,然后在二等分的情况下,如果当前提交不在该列表中,请执行git bisect skip.这需要花费很多时间(每次跳过都要检查/更改大量文件).

所以问题是:有没有办法做 - 第一父与git bisect或提供我觉得有效的提交列表能够避免检查我知道已经不可编译的分支?我们如何只检查图中标记为o的提交?

G---o---o---o---o---o---o---B  main project branch
   /       /       / 
  x---x---x---x---x            dependency
           \ /
            x'                 dependency project taskbranch

编辑:为清晰起见添加了图表

小智 11

我一直在寻找这样的东西.据我所知,git rev-list --bisect --first-parent似乎做了你想做的事情,而rev-list的文档意味着该--bisect选项是bisect在内部使用的 - 但是要git bisect将该标志添加到其调用的rev-list中似乎不那么琐碎:

bisect命令由shell脚本git-bisect实现,后者又使用内置命令bisect--helper实际执行有趣的部分("计算,显示和检出"表示评论......),显然是基于一堆魔法状态.git /中的文件.似乎是rev-list命令正在重复使用bisect - helper中的代码,而不是像你期望的那样.

因此,我认为你必须扩展bisect - helper代码的提交过滤来完成它.

作为一种解决方法,这样的事情可能会起作用:在bisect为你检查一些东西后,重置为另一个使用git rev-list --bisect --first-parent,测试并标记好/坏/跳过并从那里继续.

  • 使用Git 2.4.0,`git rev-list --bisect --first-parent`将不再有效:https://github.com/git/git/commit/f88851c6376f0b2a4cf87c061a848e4ae4438e0a (5认同)

tdd*_*ing 11

我想到了一个可能的解决方案,但我仍然希望找到更优雅的东西:

将所有合并的所有第二父母标记为主要分支

每个标记的所有远程父母合并AS好将考虑所有提交前述他们一样好(并因此由对开跳过).此解决方案还应该足够通用,以处理来自多个分支的多个合并,只留下主分支上的提交.

git rev-list --first-parent --merges --parents GOOD..BAD \
| sed 's/^[^ ][^ ]* [^ ][^ ]* //' \
| xargs git bisect good
Run Code Online (Sandbox Code Playgroud)

(用相关提交替换GOOD和BAD)

sed中的正则表达式删除了每一行的前两个提交; 合并提交本身,以及第一个父级,留下其余的父母(通常只是第二个).

鉴于问题中陈述的历史,运行oneliner会给你:

G---o---o---o---o---o---o---B  main project branch
   /       /       / 
  G---x---G---x---G            dependency
           \ /
            x'                 dependency project taskbranch

这将使bisect遍历仅主分支上的提交:

    o---o---o---o---o---o

如果任何合并的分支间接导致问题,则在通过bisect测试合并提交时会发现它,这可能是在该分支上进一步调查的原因.


Wil*_*ell 9

如果历史看起来像:

A - B - C - H - I - J - K - L
         \              /
          D - E - F - G

L是坏的,B很好,你想忽略DEFG分支,然后运行

$ git bisect start
$ git bisect skip $( git rev-list G ^C )
$ git bisect bad L
$ git bisect good B

其中B,C,G和L各自的shas似乎做你想要的.

  • 我把它变成了一个我推送到 GitHub 的脚本:https://github.com/marczych/git-first-parent-bisect 感谢你的灵感! (3认同)
  • 在我们的例子中,合并只是一种方式,进入我们的主分支,并且它们发生了多次,可能在侧分支上有许多本地任务分支。在这种情况下,它变得有点棘手。 (2认同)

Von*_*onC 9

有什么办法可以--first-parent用 git bisect

是的:在 Git 2.29(2020 年第 4 季度)中,“ git bisectman学习了“ --first-parent” 选项以查找沿第一父链的第一个断裂点。

请参阅Aaron Lipman ( ) 的commit ad464a4commit e8861ffcommit be5fe20commit 0fe305acommit 15a4802(2020 年 8 月 7 日(由Junio C Hamano合并-- --2020 年 8 月 17 日提交 47f0f94 中alipman88
gitster

bisect: 引入第一父标志

签字人:Aaron Lipman

在二分时看到合并提交时,此选项可用于仅跟随第一个父级。

在检测通过合并分支引入的回归时,合并提交将被识别为错误的引入,其祖先将被忽略。

当合并分支包含损坏或不可构建的提交,但合并本身没问题时,此选项在避免误报方面特别有用。

git bisect [--no-checkout] [--first-parent] [<bad> [<good>...]] [--] [<paths>...]
Run Code Online (Sandbox Code Playgroud)

git bisect现在包括在其手册页中

--first-parent

在看到合并提交时,只关注第一个父提交。

在检测通过合并分支引入的回归时,合并提交将被识别为错误的引入,其祖先将被忽略。

当合并分支包含损坏或不可构建的提交,但合并本身没问题时,此选项在避免误报方面特别有用。

  • @rjmunro 仅“git bisect start”:仅为该命令列出“--first-parent”选项。 (2认同)

Bjö*_*ink 5

您可以使用git将历史视为线性使用移植物.要线性化整个第一个父历史记录,您可以使用:

git rev-list --first-parent --merges --parents HEAD | cut -d' ' -f1,2 > .git/info/grafts
Run Code Online (Sandbox Code Playgroud)

完成二分后,只需删除移植文件.


jtn*_*hof 1

但是,根据您当前的解决方案,我没有看到一步法: git bisect skip 可以获取要跳过的提交列表。git logbranchname 将列出分支branchname 上的提交。所以这应该让您指定提交列表。

如果您的依赖项和主代码位于不同的文件系统空间中,您可以指定要包含在 git bisect start 中的路径。根据您的代码布局,这可能是最佳选择。(几乎可以肯定的是,如果您有可能包含该错误的文件列表!)

手册有详细信息;看看也有有趣的阅读。