답변:
다음 명령의 출력은 총계를 더하기 위해 스크립트로 전송하기가 합리적으로 쉽습니다.
git log --author="<authorname>" --oneline --shortstat
현재 HEAD에 대한 모든 커밋에 대한 통계를 제공합니다. 다른 지점에 통계를 추가하려면에 통계를 제공해야합니다 git log
.
스크립트에 전달하기 위해 빈 로그 형식으로 "oneline"형식을 제거 할 수도 있으며 Jakub Narębski의 의견에 따르면 --numstat
다른 대안입니다. 행당 통계보다는 파일 단위로 생성되지만 구문 분석이 더 쉽습니다.
git log --author="<authorname>" --pretty=tformat: --numstat
--numstat
대신 사용할 수 있습니다 --shortstat
.
git help log
는 첫 번째 줄이 추가되고 두 번째 줄이 삭제되었음을 알려줍니다.
이것은 저자에 대한 통계를 제공하고 필요에 따라 수정합니다.
Gawk 사용하기 :
git log --author="_Your_Name_Here_" --pretty=tformat: --numstat \
| gawk '{ add += $1; subs += $2; loc += $1 - $2 } END { printf "added lines: %s removed lines: %s total lines: %s\n", add, subs, loc }' -
Mac OSX에서 Awk 사용 :
git log --author="_Your_Name_Here_" --pretty=tformat: --numstat | awk '{ add += $1; subs += $2; loc += $1 - $2 } END { printf "added lines: %s, removed lines: %s, total lines: %s\n", add, subs, loc }' -
github에는 매끄러운 것처럼 보이고 bash를 종속성으로 사용하는 새로운 패키지가 있습니다 (Linux에서 테스트 됨). 스크립트보다는 직접 사용에 더 적합합니다.
그것은의 자식-빠른 통계 (GitHub의 링크) .
git-quick-stats
폴더에 복사 하고 경로에 폴더를 추가하십시오.
mkdir ~/source
cd ~/source
git clone git@github.com:arzzen/git-quick-stats.git
mkdir ~/bin
ln -s ~/source/git-quick-stats/git-quick-stats ~/bin/git-quick-stats
chmod +x ~/bin/git-quick-stats
export PATH=${PATH}:~/bin
용법:
git-quick-stats
gawk
할 수 awk
는 OSX 터미널에서 작동하도록
git clone https://github.com/arzzen/git-quick-stats.git
누구나 자신의 코드베이스에서 모든 사용자 의 통계를보고 싶을 때 최근 두 명의 동료 가이 끔찍한 원 라이너를 생각해 냈습니다.
git log --shortstat --pretty="%cE" | sed 's/\(.*\)@.*/\1/' | grep -v "^$" | awk 'BEGIN { line=""; } !/^ / { if (line=="" || !match(line, $0)) {line = $0 "," line }} /^ / { print line " # " $0; line=""}' | sort | sed -E 's/# //;s/ files? changed,//;s/([0-9]+) ([0-9]+ deletion)/\1 0 insertions\(+\), \2/;s/\(\+\)$/\(\+\), 0 deletions\(-\)/;s/insertions?\(\+\), //;s/ deletions?\(-\)//' | awk 'BEGIN {name=""; files=0; insertions=0; deletions=0;} {if ($1 != name && name != "") { print name ": " files " files changed, " insertions " insertions(+), " deletions " deletions(-), " insertions-deletions " net"; files=0; insertions=0; deletions=0; name=$1; } name=$1; files+=$2; insertions+=$3; deletions+=$4} END {print name ": " files " files changed, " insertions " insertions(+), " deletions " deletions(-), " insertions-deletions " net";}'
(약 10-15k 커밋이있는 리포지토리를 통해 몇 분이 소요됩니다.)
michael,: 6057 files changed, 854902 insertions(+), 26973 deletions(-), 827929 net
힘내 명성 https://github.com/oleander/git-fame-rb
커밋 및 수정 된 파일 수를 포함하여 모든 작성자의 수를 한 번에 계산할 수있는 유용한 도구입니다.
sudo apt-get install ruby-dev
sudo gem install git_fame
cd /path/to/gitdir && git fame
https://github.com/casperdcl/git-fame(@fracz 에서 언급 )에도 Python 버전이 있습니다 .
sudo apt-get install python-pip python-dev build-essential
pip install --user git-fame
cd /path/to/gitdir && git fame
샘플 출력 :
Total number of files: 2,053
Total number of lines: 63,132
Total number of commits: 4,330
+------------------------+--------+---------+-------+--------------------+
| name | loc | commits | files | percent |
+------------------------+--------+---------+-------+--------------------+
| Johan Sørensen | 22,272 | 1,814 | 414 | 35.3 / 41.9 / 20.2 |
| Marius Mathiesen | 10,387 | 502 | 229 | 16.5 / 11.6 / 11.2 |
| Jesper Josefsson | 9,689 | 519 | 191 | 15.3 / 12.0 / 9.3 |
| Ole Martin Kristiansen | 6,632 | 24 | 60 | 10.5 / 0.6 / 2.9 |
| Linus Oleander | 5,769 | 705 | 277 | 9.1 / 16.3 / 13.5 |
| Fabio Akita | 2,122 | 24 | 60 | 3.4 / 0.6 / 2.9 |
| August Lilleaas | 1,572 | 123 | 63 | 2.5 / 2.8 / 3.1 |
| David A. Cuadrado | 731 | 111 | 35 | 1.2 / 2.6 / 1.7 |
| Jonas Ängeslevä | 705 | 148 | 51 | 1.1 / 3.4 / 2.5 |
| Diego Algorta | 650 | 6 | 5 | 1.0 / 0.1 / 0.2 |
| Arash Rouhani | 629 | 95 | 31 | 1.0 / 2.2 / 1.5 |
| Sofia Larsson | 595 | 70 | 77 | 0.9 / 1.6 / 3.8 |
| Tor Arne Vestbø | 527 | 51 | 97 | 0.8 / 1.2 / 4.7 |
| spontus | 339 | 18 | 42 | 0.5 / 0.4 / 2.0 |
| Pontus | 225 | 49 | 34 | 0.4 / 1.1 / 1.7 |
+------------------------+--------+---------+-------+--------------------+
그러나 Jared의 의견에서 언급했듯이 매우 큰 저장소에서 처리하는 데 몇 시간이 걸립니다. 그것이 너무 많은 Git 데이터를 처리해야한다는 것을 고려할 때 그것이 향상 될 수 있는지 확실하지 않습니다.
git fame --branch=dev --timeout=-1 --exclude=Pods/*
다음은 현재 코드베이스에 가장 많은 행을 가진 사람을 보는 데 유용한 것으로 나타났습니다.
git ls-files -z | xargs -0n1 git blame -w | ruby -n -e '$_ =~ /^.*\((.*?)\s[\d]{4}/; puts $1.strip' | sort -f | uniq -c | sort -n
다른 답변은 커밋에서 변경된 행에 주로 초점을 맞추었지만 커밋이 살아남지 않고 덮어 쓰면 이탈했을 수 있습니다. 위의 주문은 또한 모든 커미터를 한 번에 하나씩이 아니라 한 줄씩 정렬하도록합니다. git blame (-C -M)에 몇 가지 옵션을 추가하여 파일 간 파일 이동 및 줄 이동을 고려한 더 나은 숫자를 얻을 수 있지만 명령을 실행하면 명령이 훨씬 오래 실행될 수 있습니다.
또한 모든 커미터에 대한 모든 커밋에서 변경된 행을 찾으려면 다음 작은 스크립트가 도움이됩니다.
/^.*\((.*?)\s[\d]{4}/
/^.*?\((.*?)\s[\d]{4}/
저자로서 소스에서 일치하는 괄호를 방지 해야합니다 .
주어진 브랜치에서 주어진 저자 (또는 모든 저자) 의 커밋 수를 세려면 git-shortlog를 사용할 수 있습니다 . git 저장소에서 실행될 때 특히 해당 옵션 --numbered
과 --summary
옵션을 참조하십시오 .
$ git shortlog v1.6.4 --numbered --summary
6904 Junio C Hamano
1320 Shawn O. Pearce
1065 Linus Torvalds
692 Johannes Schindelin
443 Eric Wong
v1.6.4
당신이 및 복제 / 또는 자식 저장소에서 가져 오지 않은 때에 상관없이 같은 수 없습니다 : 메이크업 출력 결정이 예에서는 여기에있다.
v1.6.4
:fatal: ambiguous argument 'v1.6.4': unknown revision or path not in the working tree.
git shortlog -sne
또는 합병을 포함시키지 않으 git shortlog -sne --no-merges
-s
is --summary
, -n
is --numbered
, [new] -e
는 --email
저자의 이메일을 보여주는 것입니다 (그리고 .mailmap
수정 사항 을 고려하여 다른 이메일 주소를 가진 동일한 저자를 별도로 계산합니다 ). 에 대한 좋은 전화 --no-merges
.
보고 후 알렉스 와 Gerty3000 의 대답, 나는 한 줄을 단축하는 것을 시도했다 :
기본적으로 git log numstat를 사용하고 변경된 파일 수를 추적 하지 않습니다 .
Mac OSX에서 Git 버전 2.1.0 :
git log --format='%aN' | sort -u | while read name; do echo -en "$name\t"; git log --author="$name" --pretty=tformat: --numstat | awk '{ add += $1; subs += $2; loc += $1 - $2 } END { printf "added lines: %s, removed lines: %s, total lines: %s\n", add, subs, loc }' -; done
예:
Jared Burrows added lines: 6826, removed lines: 2825, total lines: 4001
쉘 one-liner를 사용하는 AaronM 의 대답 은 좋지만 실제로는 사용자 이름과 날짜 사이에 공백이 다른 경우 공백이 사용자 이름을 손상시키는 또 다른 버그가 있습니다. 손상된 사용자 이름은 사용자 수에 대해 여러 행을 제공하므로 직접 요약해야합니다.
이 작은 변경으로 인해 문제가 해결되었습니다.
git ls-files -z | xargs -0n1 git blame -w --show-email | perl -n -e '/^.*?\((.*?)\s+[\d]{4}/; print $1,"\n"' | sort -f | uniq -c | sort -n
이름에서 날짜까지 모든 공백을 사용하는 + after \ s에 주목하십시오.
사실 나는이 주제를 google에 두 번째로 기록하기 때문에 다른 사람을 돕는 것만 큼 내 자신의 기억을 위해이 답변을 많이 추가합니다. :)
--show-email
하는 git blame -w
어떤 사람들은 다른 사용하기 때문에, 대신 이메일에 통합 할 Name
다른 컴퓨터에 포맷을하고, 같은 이름을 가진 때로는 두 사람이 같은 자식에서 일하고있다.unsupported file type
하지만 그렇지 않은 경우에도 제대로 작동하는 것 같습니다 (건너 뜁니다).
다음은 모든 저자에 대한 통계를 생성하는 짧은 하나의 라이너입니다. 위의 Dan 솔루션보다 https://stackoverflow.com/a/20414465/1102119 보다 훨씬 빠릅니다 (N은 커밋 수이고 M은 저자 수입니다). ).
git log --no-merges --pretty=format:%an --numstat | awk '/./ && !author { author = $0; next } author { ins[author] += $1; del[author] += $2 } /^$/ { author = ""; next } END { for (a in ins) { printf "%10d %10d %10d %s\n", ins[a] - del[a], ins[a], del[a], a } }' | sort -rn
--no-show-signature
그렇지 않으면 자신의 커밋 PGP 서명 할 사람이 계산 얻을하지 않을 수 있습니다.
count-lines = "!f() { git log --no-merges --pretty=format:%an --numstat | awk '/./ && !author { author = $0; next } author { ins[author] += $1; del[author] += $2 } /^$/ { author = \"\"; next } END { for (a in ins) { printf \"%10d %10d %10d %s\\n\", ins[a] - del[a], ins[a], del[a], a } }' | sort -rn; }; f"
. (나는 Windows에 있습니다; 당신은 다른 종류의 따옴표를 사용해야 할 수도 있습니다)
@mmrobins @AaronM @ErikZ @JamesMishra는 모두 공통적으로 문제가있는 변형을 제공했습니다. git은 동일한 줄에있는 저장소의 줄 내용을 포함하여 스크립트 소비 용이 아닌 정보의 혼합을 생성하도록 요청한 다음 정규 표현식과 엉망을 일치시킵니다. .
이것은 일부 행이 유효한 UTF-8 텍스트가 아니고 일부 행이 정규 표현식과 일치 할 때 문제가됩니다 (여기에서 발생했습니다).
다음은 이러한 문제가없는 수정 된 줄입니다. git이 데이터를 별도의 라인으로 깨끗하게 출력하도록 요청하므로 원하는 것을 쉽게 필터링 할 수 있습니다.
git ls-files -z | xargs -0n1 git blame -w --line-porcelain | grep -a "^author " | sort -f | uniq -c | sort -n
저자 메일, 커미터 등과 같은 다른 문자열을 grep 할 수 있습니다.
아마도 바이트 수준 처리를 강제하기 위해 먼저 export LC_ALL=C
(가정이라고 가정 bash
) (UTF-8 기반 로케일에서 grep을 엄청나게 가속화합니다).
해결책은 중간에 루비가 주어졌으며, perl은 기본적으로 조금 더 사용 가능합니다. 여기서는 현재 줄에 perl을 사용하는 대안이 있습니다.
git ls-files -z | xargs -0n1 git blame -w | perl -n -e '/^.*\((.*?)\s*[\d]{4}/; print $1,"\n"' | sort -f | uniq -c | sort -n
Charles Bailey의 답변 외에도 -C
매개 변수를 명령 에 추가 할 수 있습니다 . 그렇지 않으면 파일 내용이 수정되지 않은 경우에도 파일 이름 바꾸기에 추가 및 제거 횟수 (파일에 줄이있는 개수)가 포함됩니다.
예를 들어, 다음은 명령을 사용할 때 내 프로젝트 중 하나에서 많은 파일이 이동되는 커밋 입니다 git log --oneline --shortstat
.
9052459 Reorganized project structure
43 files changed, 1049 insertions(+), 1000 deletions(-)
다음 git log --oneline --shortstat -C
은 파일 사본을 감지하고 이름을 바꾸는 명령을 사용하는 동일한 커밋입니다 .
9052459 Reorganized project structure
27 files changed, 134 insertions(+), 85 deletions(-)
내 생각에 후자는 파일 이름을 바꾸는 것이 처음부터 파일을 작성하는 것보다 훨씬 작은 작업이기 때문에 개인이 프로젝트에 얼마나 많은 영향을 미쳤는 지에 대한보다 현실적인 견해를 제공합니다.
whodid를 사용할 수 있습니다 ( https://www.npmjs.com/package/whodid )
$ npm install whodid -g
$ cd your-project-dir
과
$ whodid author --include-merge=false --path=./ --valid-threshold=1000 --since=1.week
아니면 그냥 입력
$ whodid
다음과 같은 결과를 볼 수 있습니다
Contribution state
=====================================================
score | author
-----------------------------------------------------
3059 | someguy <someguy@tensorflow.org>
585 | somelady <somelady@tensorflow.org>
212 | niceguy <nice@google.com>
173 | coolguy <coolgay@google.com>
=====================================================
-g
에, 패키지 이름 앞에 와야했다 macOS
. 단순히 도와 주려고합니다.
다음은 주어진 로그 쿼리에 대한 사용자 별 영향을 비교하는 빠른 루비 스크립트입니다.
예를 들어, rubinius의 경우 :
Brian Ford: 4410668
Evan Phoenix: 1906343
Ryan Davis: 855674
Shane Becker: 242904
Alexander Kellett: 167600
Eric Hodel: 132986
Dirkjan Bussink: 113756
...
스크립트 :
#!/usr/bin/env ruby
impact = Hash.new(0)
IO.popen("git log --pretty=format:\"%an\" --shortstat #{ARGV.join(' ')}") do |f|
prev_line = ''
while line = f.gets
changes = /(\d+) insertions.*(\d+) deletions/.match(line)
if changes
impact[prev_line] += changes[1].to_i + changes[2].to_i
end
prev_line = line # Names are on a line of their own, just before the stats
end
end
impact.sort_by { |a,i| -i }.each do |author, impact|
puts "#{author.strip}: #{impact}"
end
위의 짧은 답변을 수정했지만 내 요구에 충분하지 않았습니다. 최종 코드에서 커밋 된 라인과 라인을 모두 분류 할 수 있어야했습니다. 또한 파일별로 분류하고 싶었습니다. 이 코드는 되풀이되지 않고 단일 디렉토리에 대한 결과 만 반환하지만 누군가가 더 나아가고 싶다면 좋은 시작입니다. 파일에 복사하여 붙여 넣어 실행 가능하게 만들거나 Perl로 실행하십시오.
#!/usr/bin/perl
use strict;
use warnings;
use Data::Dumper;
my $dir = shift;
die "Please provide a directory name to check\n"
unless $dir;
chdir $dir
or die "Failed to enter the specified directory '$dir': $!\n";
if ( ! open(GIT_LS,'-|','git ls-files') ) {
die "Failed to process 'git ls-files': $!\n";
}
my %stats;
while (my $file = <GIT_LS>) {
chomp $file;
if ( ! open(GIT_LOG,'-|',"git log --numstat $file") ) {
die "Failed to process 'git log --numstat $file': $!\n";
}
my $author;
while (my $log_line = <GIT_LOG>) {
if ( $log_line =~ m{^Author:\s*([^<]*?)\s*<([^>]*)>} ) {
$author = lc($1);
}
elsif ( $log_line =~ m{^(\d+)\s+(\d+)\s+(.*)} ) {
my $added = $1;
my $removed = $2;
my $file = $3;
$stats{total}{by_author}{$author}{added} += $added;
$stats{total}{by_author}{$author}{removed} += $removed;
$stats{total}{by_author}{total}{added} += $added;
$stats{total}{by_author}{total}{removed} += $removed;
$stats{total}{by_file}{$file}{$author}{added} += $added;
$stats{total}{by_file}{$file}{$author}{removed} += $removed;
$stats{total}{by_file}{$file}{total}{added} += $added;
$stats{total}{by_file}{$file}{total}{removed} += $removed;
}
}
close GIT_LOG;
if ( ! open(GIT_BLAME,'-|',"git blame -w $file") ) {
die "Failed to process 'git blame -w $file': $!\n";
}
while (my $log_line = <GIT_BLAME>) {
if ( $log_line =~ m{\((.*?)\s+\d{4}} ) {
my $author = $1;
$stats{final}{by_author}{$author} ++;
$stats{final}{by_file}{$file}{$author}++;
$stats{final}{by_author}{total} ++;
$stats{final}{by_file}{$file}{total} ++;
$stats{final}{by_file}{$file}{total} ++;
}
}
close GIT_BLAME;
}
close GIT_LS;
print "Total lines committed by author by file\n";
printf "%25s %25s %8s %8s %9s\n",'file','author','added','removed','pct add';
foreach my $file (sort keys %{$stats{total}{by_file}}) {
printf "%25s %4.0f%%\n",$file
,100*$stats{total}{by_file}{$file}{total}{added}/$stats{total}{by_author}{total}{added};
foreach my $author (sort keys %{$stats{total}{by_file}{$file}}) {
next if $author eq 'total';
if ( $stats{total}{by_file}{$file}{total}{added} ) {
printf "%25s %25s %8d %8d %8.0f%%\n",'', $author,@{$stats{total}{by_file}{$file}{$author}}{qw{added removed}}
,100*$stats{total}{by_file}{$file}{$author}{added}/$stats{total}{by_file}{$file}{total}{added};
} else {
printf "%25s %25s %8d %8d\n",'', $author,@{$stats{total}{by_file}{$file}{$author}}{qw{added removed}} ;
}
}
}
print "\n";
print "Total lines in the final project by author by file\n";
printf "%25s %25s %8s %9s %9s\n",'file','author','final','percent', '% of all';
foreach my $file (sort keys %{$stats{final}{by_file}}) {
printf "%25s %4.0f%%\n",$file
,100*$stats{final}{by_file}{$file}{total}/$stats{final}{by_author}{total};
foreach my $author (sort keys %{$stats{final}{by_file}{$file}}) {
next if $author eq 'total';
printf "%25s %25s %8d %8.0f%% %8.0f%%\n",'', $author,$stats{final}{by_file}{$file}{$author}
,100*$stats{final}{by_file}{$file}{$author}/$stats{final}{by_file}{$file}{total}
,100*$stats{final}{by_file}{$file}{$author}/$stats{final}{by_author}{total}
;
}
}
print "\n";
print "Total lines committed by author\n";
printf "%25s %8s %8s %9s\n",'author','added','removed','pct add';
foreach my $author (sort keys %{$stats{total}{by_author}}) {
next if $author eq 'total';
printf "%25s %8d %8d %8.0f%%\n",$author,@{$stats{total}{by_author}{$author}}{qw{added removed}}
,100*$stats{total}{by_author}{$author}{added}/$stats{total}{by_author}{total}{added};
};
print "\n";
print "Total lines in the final project by author\n";
printf "%25s %8s %9s\n",'author','final','percent';
foreach my $author (sort keys %{$stats{final}{by_author}}) {
printf "%25s %8d %8.0f%%\n",$author,$stats{final}{by_author}{$author}
,100*$stats{final}{by_author}{$author}/$stats{final}{by_author}{total};
}
Windows 사용자의 경우 지정된 작성자의 추가 / 제거 된 행을 계산하는 다음 배치 스크립트를 사용할 수 있습니다.
@echo off
set added=0
set removed=0
for /f "tokens=1-3 delims= " %%A in ('git log --pretty^=tformat: --numstat --author^=%1') do call :Count %%A %%B %%C
@echo added=%added%
@echo removed=%removed%
goto :eof
:Count
if NOT "%1" == "-" set /a added=%added% + %1
if NOT "%2" == "-" set /a removed=%removed% + %2
goto :eof
https://gist.github.com/zVolodymyr/62e78a744d99d414d56646a5e8a1ff4f
git-quick-stats
brew install git-quick-stats
git-quick-stats
나열된 번호를 입력하고 Enter 키를 눌러이 목록에서 원하는 옵션을 선택하십시오.
Generate:
1) Contribution stats (by author)
2) Contribution stats (by author) on a specific branch
3) Git changelogs (last 10 days)
4) Git changelogs by author
5) My daily status
6) Save git log output in JSON format
List:
7) Branch tree view (last 10)
8) All branches (sorted by most recent commit)
9) All contributors (sorted by name)
10) Git commits per author
11) Git commits per date
12) Git commits per month
13) Git commits per weekday
14) Git commits per hour
15) Git commits by author per hour
Suggest:
16) Code reviewers (based on git history)
이 스크립트는 여기에 있습니다. authorship.sh, chmod + x에 넣으면 모든 준비가 완료된 것입니다.
#!/bin/sh
declare -A map
while read line; do
if grep "^[a-zA-Z]" <<< "$line" > /dev/null; then
current="$line"
if [ -z "${map[$current]}" ]; then
map[$current]=0
fi
elif grep "^[0-9]" <<<"$line" >/dev/null; then
for i in $(cut -f 1,2 <<< "$line"); do
map[$current]=$((map[$current] + $i))
done
fi
done <<< "$(git log --numstat --pretty="%aN")"
for i in "${!map[@]}"; do
echo -e "$i:${map[$i]}"
done | sort -nr -t ":" -k 2 | column -t -s ":"
다음을 사용하여 로그를 파일로 저장하십시오.
git log --author="<authorname>" --oneline --shortstat > logs.txt
파이썬 애호가들에게 :
with open(r".\logs.txt", "r", encoding="utf8") as f:
files = insertions = deletions = 0
for line in f:
if ' changed' in line:
line = line.strip()
spl = line.split(', ')
if len(spl) > 0:
files += int(spl[0].split(' ')[0])
if len(spl) > 1:
insertions += int(spl[1].split(' ')[0])
if len(spl) > 2:
deletions += int(spl[2].split(' ')[0])
print(str(files).ljust(10) + ' files changed')
print(str(insertions).ljust(10) + ' insertions')
print(str(deletions).ljust(10) + ' deletions')
출력은 다음과 같습니다.
225 files changed
6751 insertions
1379 deletions
이 질문은 특정 저자 에 대한 정보를 요구 했지만 많은 답변은 변경된 코드 라인을 기준으로 순위가 높은 저자 목록을 반환하는 솔루션이었습니다.
이것이 내가 찾던 것이었지만 기존 솔루션은 완벽하지 않았습니다. Google을 통해이 질문을 찾을 수있는 사람들을 위해 몇 가지를 개선하고 쉘 스크립트로 만들었습니다. 아래에 표시됩니다. 주석이 달린 항목 (계속 유지)은 Github에서 찾을 수 있습니다 .
Perl 또는 Ruby에 대한 종속성 이 없습니다 . 또한 공백, 개수 변경 및 줄 이동이 줄 변경 횟수에 고려됩니다. 이것을 파일에 넣고 Git 저장소를 첫 번째 매개 변수로 전달하십시오.
#!/bin/bash
git --git-dir="$1/.git" log > /dev/null 2> /dev/null
if [ $? -eq 128 ]
then
echo "Not a git repository!"
exit 128
else
echo -e "Lines | Name\nChanged|"
git --work-tree="$1" --git-dir="$1/.git" ls-files -z |\
xargs -0n1 git --work-tree="$1" --git-dir="$1/.git" blame -C -M -w |\
cut -d'(' -f2 |\
cut -d2 -f1 |\
sed -e "s/ \{1,\}$//" |\
sort |\
uniq -c |\
sort -nr
fi
지금까지 내가 확인한 최고의 도구는 gitinspector입니다. 그것은 사용자 당, 주별 등의 세트 보고서를 제공합니다.
npm install -g gitinspector
더 자세한 정보를 얻을 수있는 링크
https://www.npmjs.com/package/gitinspector
https://github.com/ejwa/gitinspector/wiki/Documentation
https://github.com/ejwa/gitinspector
예제 명령은
gitinspector -lmrTw
gitinspector --since=1-1-2017 etc
이 작업을 수행하기 위해이 Perl 스크립트를 작성했습니다.
#!/usr/bin/env perl
use strict;
use warnings;
# save the args to pass to the git log command
my $ARGS = join(' ', @ARGV);
#get the repo slug
my $NAME = _get_repo_slug();
#get list of authors
my @authors = _get_authors();
my ($projectFiles, $projectInsertions, $projectDeletions) = (0,0,0);
#for each author
foreach my $author (@authors) {
my $command = qq{git log $ARGS --author="$author" --oneline --shortstat --no-merges};
my ($files, $insertions, $deletions) = (0,0,0);
my @lines = `$command`;
foreach my $line (@lines) {
if ($line =~ m/^\s(\d+)\s\w+\s\w+,\s(\d+)\s\w+\([\+|\-]\),\s(\d+)\s\w+\([\+|\-]\)$|^\s(\d+)\s\w+\s\w+,\s(\d+)\s\w+\(([\+|\-])\)$/) {
my $lineFiles = $1 ? $1 : $4;
my $lineInsertions = (defined $6 && $6 eq '+') ? $5 : (defined $2) ? $2 : 0;
my $lineDeletions = (defined $6 && $6 eq '-') ? $5 : (defined $3) ? $3 : 0;
$files += $lineFiles;
$insertions += $lineInsertions;
$deletions += $lineDeletions;
$projectFiles += $lineFiles;
$projectInsertions += $lineInsertions;
$projectDeletions += $lineDeletions;
}
}
if ($files || $insertions || $deletions) {
printf(
"%s,%s,%s,+%s,-%s,%s\n",
$NAME,
$author,
$files,
$insertions,
$deletions,
$insertions - $deletions
);
}
}
printf(
"%s,%s,%s,+%s,-%s,%s\n",
$NAME,
'PROJECT_TOTAL',
$projectFiles,
$projectInsertions,
$projectDeletions,
$projectInsertions - $projectDeletions
);
exit 0;
#get the remote.origin.url joins that last two pieces (project and repo folder)
#and removes any .git from the results.
sub _get_repo_slug {
my $get_remote_url = "git config --get remote.origin.url";
my $remote_url = `$get_remote_url`;
chomp $remote_url;
my @parts = split('/', $remote_url);
my $slug = join('-', @parts[-2..-1]);
$slug =~ s/\.git//;
return $slug;
}
sub _get_authors {
my $git_authors = 'git shortlog -s | cut -c8-';
my @authors = `$git_authors`;
chomp @authors;
return @authors;
}
나는 그것을 명명 git-line-changes-by-author
하고에 넣었다 /usr/local/bin
. 내 경로에 저장되었으므로 git line-changes-by-author --before 2018-12-31 --after 2020-01-01
2019 년 동안 보고서를 가져 오도록 명령 을 실행할 수 있습니다 . 예로서. 그리고 철자가 틀리면 git이라는 이름이 올바른 철자를 제안합니다.
내 repos가 저장되고 그렇지 않을 수도 있으므로 _get_repo_slug
마지막 부분 만 포함 하도록 하위 를 조정할 수 있습니다.remote.origin.url
project/repo
git://git.lwn.net/gitdm.git
.