【问题标题】:How do I use git cherry to get committer email?如何使用 git cherry 获取提交者电子邮件?
【发布时间】:2017-05-01 16:59:44
【问题描述】:

git cherry 在获取两个分支之间的差异方面优于git log。问题是它的输出是有限的。

我正在尝试提取与提交关联的电子邮件地址(或用户)。这就是我正在做的事情。

git cherry firstbranch secondbranch | awk '/^+/ {print $2}' | awk '{ system("git show $1"); }'

我得到的只是一个提交的细节。而不是我所做的每一次提交:

git cherry firstbranch secondbranch | awk '/^+/ {print $2}'

第二个管道操作出了点问题。

我的问题是:如何使用 git cherry 获取提交者电子邮件?

【问题讨论】:

    标签: git awk pipe git-log git-cherry


    【解决方案1】:

    管道到git log --no-walk --stdinSteven Penny's approach 是正确的方法,并且在最复杂的情​​况下是必需的(选定提交ID 的复杂过滤)。

    有一些技巧可以用于这个特殊的案例。如果您检查(广泛,虽然令人困惑)documentation for git rev-list,您会发现选项--left-right--left-only--right-only--cherry-mark--cherry-pick--cherry

    --left-right 选项适用于任何对称差异,即由A...B 选择的提交,这意味着“在分支A 上的所有提交 分支B,不包括任何both 分支上的提交。"这就是git cherry 做它的第一部分的方式:它找到在对称差异上的提交。但是,git cherry 继续丢弃所有在两个分支上“相同”1 的提交,然后将它们标记在一个一边是-,另一边是+--left-right 选项将所有提交标记为<(左侧)或>(右侧)。

    由于rev-list 是Swiss Army Chainsaw 命令,它 能够丢弃相同的提交。它也有更多的能力:它可以完全丢弃一侧的提交,相同或不同。这就是我们在这种情况下想要的:丢弃“相同的提交”(这样我们只保留“不同”的提交),然后丢弃所有“左侧”提交(这样我们只保留那些在右侧但不是左侧)。我们用--cherry-pick 得到前者:它只保留被认为“不同”的提交。然后我们添加--right-only 以仅保留右侧的那些,即当我们说firstbranch...secondbranch 时,仅保留secondbranch 中既不同的 ...这正是git cherry 会。

    因此:

    git rev-list --right-only --cherry-pick firstbranch...secondbranch
    

    产生与以下相同的提交 ID 列表:

    git cherry firstbranch secondbranch
    

    (唯一的区别是它打印的是+face0ff,而不是+ face0ff...,即+ 标记后没有空格)。

    这看起来很傻:我们需要git rev-list 和一堆选项以及两个分支名称和三个句点,而不是四个单词git cherry 和两个分支名称。我们已经输入了更多的字母来得到几乎相同的东西。所以我们可以只使用更短的命令并将其通过管道传递给git log,但现在我们要解决棘手的问题了。

    git loggit rev-list 几乎是同一个命令

    事实上,它们是从相同的源代码构建的,只是设置了一些不同的内部选项(如果你不指定任何其他起点,git log 会假装你说的是HEAD)。由于我们即将将git rev-list 的输出通过管道传输到git log --pretty='%h %ce',也许我们可以直接在git log 中完成整个操作。

    果然,我们可以。我们需要与git rev-list 相同的所有选项,但现在我们可以运行:

    git log --cherry-pick --right-only --pretty='%h %ce' firstbranch...secondbranch
    

    (你可能也想在这里--no-merges - 我不确定git cherry 对合并做了什么!)。


    1在这种情况下,“Sameness”由git patch-id 的输出决定,它基本上从差异中去除了识别行号(并且还去除了某些空白细节)。因此,如果一个提交被挑选到另一个分支中,那么两个这样的提交通常将具有相同的补丁 ID。 (如果有人必须解决合并冲突,补丁 ID 会有所不同。)

    【讨论】:

    • 啊哈——我想知道的关键点是git cherry 对合并做了什么。我去看看。
    【解决方案2】:

    类似这样的:

    git cherry firstbranch secondbranch | awk '$0=$2' | git log --no-walk --stdin --pretty='%h %ce'
    
    1. --no-walk:只显示给定的提交,但不遍历它们的祖先

    2. %h:缩写提交哈希

    3. %ce:提交者电子邮件

    Source

    【讨论】:

    • @torek true,除了rev-list 做这个愚蠢的废话stackoverflow.com/q/36927089
    • 谢谢@torek - 您能否将其扩展为答案?我不太明白你的意思——这可能是一个更好的答案。
    • 是的,我不是故意在git rev-list 中使用--format,只是你可以使用git rev-list 本身而不是git cherry。由于 rev-list 和 log 基本上是相同的命令,对于这种特殊情况,您也可以在 git log 内执行所有这些操作。对于更复杂的情况(您需要sedawk 选择),您仍然需要--stdin --no-walk
    • @StevenPenny:哦,对不起,它 $0=$2,我以为$0==$2会跳过所有内容!
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-05-27
    • 1970-01-01
    • 2018-11-21
    相关资源
    最近更新 更多