Git diff,开发者贡献最多

Jes*_*sen 5 git statistics git-log

我想在我的git存储库中测量"活动开发人员"

git shortlog --summary --numbered oldrelease..newrelease 给我一个最活跃的提交者列表,如下所示:

100  developer 1
 90  developer 2
 80  developer 3
  1  developer 4
Run Code Online (Sandbox Code Playgroud)

但有时我会看到某些开发人员还原其他开发人员(或改进它).

现在,我想看看哪些开发者最积极地为此版本做出了贡献.给予代码更改的开发人员更多的权重,并减轻最终版本中其他人更改代码的开发人员的权重.

git diff oldrelease..newrelease
Run Code Online (Sandbox Code Playgroud)

可以在发布中给我所有更改的行.

我想'责备'所有这些线,以查看触及每个更改线的最后一个开发人员.怎么做?

接下来,对于所有更改的行,我想聚合它,以便最终得到这样的摘要.

git funky_new_command oldrelease..newrelease

developer 2    added 450, removed 200 lines
developer 3    added 500, removed 100 lines
developer 1    added 4, removed 50 lines
developer 4    added 1, removed 0 lines
Run Code Online (Sandbox Code Playgroud)

我认为这将为那些随着时间的推移对源代码库做出贡献的开发人员提供一个更好的想法,而不仅仅是那些提交大量文件的人.

Jon*_*set 3

正确解决这个问题有点棘手,因为您(大概)也想奖励那些也删除了代码行的作者?我下面给出的代码仅检测当前代码库中存在最多代码的作者,这些代码是自之前某个时间点以来添加的。

git diff -z --name-only HEAD~5..HEAD
  | xargs -0 -n1 -- git blame HEAD~5..HEAD --
  | grep -v "\^"
  | sed 's/\(([^)]*\)([^)]*)\([^)]*)\)/\1 \2/'
  | sed 's/^[0-9a-f]* (\([^)]*\) \+[0-9][0-9][0-9][0-9]-[0-9][0-9]-[0-9][0-9] .*).*$/\1/'
  | sort | uniq -c | sort -nr
Run Code Online (Sandbox Code Playgroud)

让我们看看这里发生了什么:

git diff -z --name-only HEAD~5..HEAD列出自上次以来已更改的所有文件。我们用 NULL 而不是换行符 ( -z) 分隔它们,以避免 的分词问题xargs

xargs -0 -n1然后使用这些文件并调用git blame HEAD~5..HEAD --每个文件。第一个--是需要的,以便我们可以--给予git blame。第二个是这样,如果有人给我们一个以破折号开头的文件名,我们就不会崩溃。

grep -v "\^"将仅保留自第一次修订以来已更改的行。该指示符的存在也是我们不使用机器可读--porcelain输出的原因,这将使解析变得更容易(见下文),但没有这种指示符。更智能的脚本可以提取我们开始的修订版本,并忽略该修订版本之后的任何作者行,但我们希望保持“简单”。这里概述了类似的方法。

此阶段的输出如下所示:

118caa41 (Jon Gjengset 2014-01-09 13:09:05 +0000 13) .FORCE:
Run Code Online (Sandbox Code Playgroud)

我们想要提取其中的作者部分,考虑到名称可能包含空格,这并不简单。由于某些存储库的用户名称包含符号(和,这一事实使情况变得更加复杂)。因此,为了简化我们的问题,我们首先用

118caa41 (Jon Gjengset 2014-01-09 13:09:05 +0000 13) .FORCE:
Run Code Online (Sandbox Code Playgroud)

这并不完全漂亮,如果一些烦人的人的()名字中有不匹配的 s ,就会崩溃,但我们会说现在还可以。

为了提取名称本身,我们求助于正则表达式这个怪物。sed它可以通过使用扩展的正则表达式进一步简化,但我决定尽可能地尝试保持兼容性:

sed 's/\(([^)]*\)([^)]*)\([^)]*)\)/\1 \2/'
Run Code Online (Sandbox Code Playgroud)

我们首先确保找到第一个带 1 的括号表达式(代码行也可能包含括号)。然后我们进行匹配,直到找到看起来像上行括号中间的日期的内容,此时我们有作者名字。该点之后的任何内容都可以删除。

此时唯一要做的就是排序和排名,这是我们使用 进行的sort | uniq -c | sort -nr

瞧,这个命令将为您找到一个作者在修订列表中添加的代码行数的有序列表,这些代码行数出现在最后一个修订版中。

警告:您可能不想将其用于任何关键任务。众所周知,基于正则表达式的解决方案很容易出现意外错误。划分输出--porcelain可能git blame是一个更长期的解决方案。