Git 用于搜索提交消息的别名

Git alias for searching for commit messages

我确实在网上找到了别名:

find = "log --decorate -i --all --date=short --grep"

search = "!f() { git log --decorate --grep= -i --all --date=short; }; f"

他们都做同样的事情:在提交消息中搜索。有没有一个 "superior" 到另一个?为什么?

问题 -- 我们如何编写别名来搜索消息中包含特定单词的提交?

例如,其中:

git search-msg foo bar baz

匹配包含单词 foobarbaz 的提交,无论顺序如何?

答案 -- 此处格式更好(来自 LeGEC):

search-msg = "!f() { str=\"git log --all-match\"; \
                     for var in \"$@\"; do \
                         str=\"$str --grep '$var'\"; \
                     done; \
                     eval $str; }; f"

通常,使用带有匿名 bash 函数的 git 命令可以让我们获得额外的好处。

这是我创建的搜索别名的输出,它可以满足您的需求。我使用提交消息“1”、“2”、“3”、“4”创建了 4 个提交:

zrrbite@ZRRBITE MINGW64 /d/dev/git/test (new)
$ git ls -4
d0ebbb3 (HEAD -> new) 4 [Martin Kjeldsen]
174f539 3 [Martin Kjeldsen]
43d6a01 2 [Martin Kjeldsen]
05e7e0a 1 [Martin Kjeldsen]

zrrbite@ZRRBITE MINGW64 /d/dev/git/test (new)
$ git search 1 2 3 4
commit 05e7e0a232e093ddfcbd90d8071dc4a84e4295b7
Author: Martin Kjeldsen <kjeldsen@gmail.com>
Date:   Fri Nov 15 23:09:02 2019 +0100

    1
commit 43d6a019742a38c1b06aa7a40bc8f34d46d0dcc8
Author: Martin Kjeldsen <kjeldsen@gmail.com>
Date:   Fri Nov 29 00:57:38 2019 +0100

    2
commit 174f539b151533406b5fa7f2c8541dfeb194bfac
Author: Martin Kjeldsen <kjeldsen@gmail.com>
Date:   Fri Nov 29 00:57:46 2019 +0100

    3
commit d0ebbb3eb1071653b0578cfdd14c0d6a7c112b1f
Author: Martin Kjeldsen <kjeldsen@gmail.com>
Date:   Fri Nov 29 00:58:01 2019 +0100

    4

另一个测试:

zrrbite@ZRRBITE MINGW64 /d/dev/git/test (new)
$ git search 2 4
commit 43d6a019742a38c1b06aa7a40bc8f34d46d0dcc8
Author: Martin Kjeldsen <kjeldsen@gmail.com>
Date:   Fri Nov 29 00:57:38 2019 +0100

    2
commit d0ebbb3eb1071653b0578cfdd14c0d6a7c112b1f
Author: Martin Kjeldsen <kjeldsen@gmail.com>
Date:   Fri Nov 29 00:58:01 2019 +0100

    4

这是简单地遍历每个参数并调用 git log --grep 的别名。相当于调用 git log --grep <a> --grep <b> --grep <c> ...:

[alias]    
search = "!f() { for l in \"$@\"; do git log --grep \"$l\"; done; }; f"

您可能想要添加历史记录以搜索整个存储库,方法是将 rev-list 添加到您的 git log

git log --grep 'Something relevant in my commits' $(git rev-list --all)

类似的东西应该在 .gitconfig 文件中工作

[alias]
    search = "!f() { git log --grep \"\" $(git rev-list --all); }; f"
[log]
    date = iso

这里的 date = iso 东西是为了获得更好的约会(当前格式是 2019-11-26 17:35:30 +0100

首先谈谈 git 日志的 --grep option :

  • 可以多次指定
  • 默认的多重 grep 是 "match any of the patterns"
  • 多了一个--all-match flag,表示"match all of the patterns"

示例:

# two commits contain 'foo' in their message (one of them also contains 'bar'):
$ git log --oneline --grep foo
b76121c bar baz foo
b7a342f foo

# two commits contain 'bar' in their message (one of them also contains 'foo'):
$ git log --oneline --grep bar
bbb27f3 (HEAD -> master) bar
b76121c bar baz foo

# if I look for both patterns : I get the union of both searches (3 commits)
$ git log --oneline --grep foo --grep bar
bbb27f3 (HEAD -> master) bar
b76121c bar baz foo
b7a342f foo

# if I add '--all-match' : only the commit which contains both is kept
$ git log --oneline --grep foo --grep bar --all-match
b76121c bar baz foo

回答您的问题:这是一个示例脚本,它接受参数列表,并将它们转换为 git log --all-match --grep aaa --grep bbb 命令:

# in file git-search-msg :

#!/bin/bash

cmd=("log" "--all-match")

for var in "$@"
do
        cmd+=('--grep')
        cmd+=("$var")
done

git "${cmd[@]}"

如果您将其粘贴到名为 git-search-msg 的文件中,并将其放在您的 PATH 上的某个位置,那么 git search-msg foo bar baz 将执行您想要的操作。


以下在普通 sh 中有效,但使用 eval :

#!/bin/sh
str="git log --all-match"

for var in "$@"
do
    # This loops takes arguments one by one and adds
    # them as '--grep' args to the 'git log' command.
    str="$str --grep '$var'"
done

# tech note : this sample script does not escape single quotes
eval $str

如果你设法将它连成一行(并正确转义),你可以在别名中使用它。

注意与 eval 混合的转义问题...