2006-12-23 00:15:59 +03:00
#!/bin/sh
#
# Copyright (c) 2006 Johannes E. Schindelin
#
2007-07-03 09:52:14 +04:00
test_description = ' git shortlog
2006-12-23 00:15:59 +03:00
'
2020-11-19 02:44:27 +03:00
GIT_TEST_DEFAULT_INITIAL_BRANCH_NAME = main
tests: mark tests relying on the current default for `init.defaultBranch`
In addition to the manual adjustment to let the `linux-gcc` CI job run
the test suite with `master` and then with `main`, this patch makes sure
that GIT_TEST_DEFAULT_INITIAL_BRANCH_NAME is set in all test scripts
that currently rely on the initial branch name being `master by default.
To determine which test scripts to mark up, the first step was to
force-set the default branch name to `master` in
- all test scripts that contain the keyword `master`,
- t4211, which expects `t/t4211/history.export` with a hard-coded ref to
initialize the default branch,
- t5560 because it sources `t/t556x_common` which uses `master`,
- t8002 and t8012 because both source `t/annotate-tests.sh` which also
uses `master`)
This trick was performed by this command:
$ sed -i '/^ *\. \.\/\(test-lib\|lib-\(bash\|cvs\|git-svn\)\|gitweb-lib\)\.sh$/i\
GIT_TEST_DEFAULT_INITIAL_BRANCH_NAME=master\
export GIT_TEST_DEFAULT_INITIAL_BRANCH_NAME\
' $(git grep -l master t/t[0-9]*.sh) \
t/t4211*.sh t/t5560*.sh t/t8002*.sh t/t8012*.sh
After that, careful, manual inspection revealed that some of the test
scripts containing the needle `master` do not actually rely on a
specific default branch name: either they mention `master` only in a
comment, or they initialize that branch specificially, or they do not
actually refer to the current default branch. Therefore, the
aforementioned modification was undone in those test scripts thusly:
$ git checkout HEAD -- \
t/t0027-auto-crlf.sh t/t0060-path-utils.sh \
t/t1011-read-tree-sparse-checkout.sh \
t/t1305-config-include.sh t/t1309-early-config.sh \
t/t1402-check-ref-format.sh t/t1450-fsck.sh \
t/t2024-checkout-dwim.sh \
t/t2106-update-index-assume-unchanged.sh \
t/t3040-subprojects-basic.sh t/t3301-notes.sh \
t/t3308-notes-merge.sh t/t3423-rebase-reword.sh \
t/t3436-rebase-more-options.sh \
t/t4015-diff-whitespace.sh t/t4257-am-interactive.sh \
t/t5323-pack-redundant.sh t/t5401-update-hooks.sh \
t/t5511-refspec.sh t/t5526-fetch-submodules.sh \
t/t5529-push-errors.sh t/t5530-upload-pack-error.sh \
t/t5548-push-porcelain.sh \
t/t5552-skipping-fetch-negotiator.sh \
t/t5572-pull-submodule.sh t/t5608-clone-2gb.sh \
t/t5614-clone-submodules-shallow.sh \
t/t7508-status.sh t/t7606-merge-custom.sh \
t/t9302-fast-import-unpack-limit.sh
We excluded one set of test scripts in these commands, though: the range
of `git p4` tests. The reason? `git p4` stores the (foreign) remote
branch in the branch called `p4/master`, which is obviously not the
default branch. Manual analysis revealed that only five of these tests
actually require a specific default branch name to pass; They were
modified thusly:
$ sed -i '/^ *\. \.\/lib-git-p4\.sh$/i\
GIT_TEST_DEFAULT_INITIAL_BRANCH_NAME=master\
export GIT_TEST_DEFAULT_INITIAL_BRANCH_NAME\
' t/t980[0167]*.sh t/t9811*.sh
Signed-off-by: Johannes Schindelin <johannes.schindelin@gmx.de>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
2020-11-19 02:44:19 +03:00
export GIT_TEST_DEFAULT_INITIAL_BRANCH_NAME
2006-12-23 00:15:59 +03:00
. ./test-lib.sh
2010-05-04 06:57:36 +04:00
test_expect_success 'setup' '
2017-11-12 18:25:23 +03:00
test_tick &&
2010-05-04 06:57:36 +04:00
echo 1 >a1 &&
git add a1 &&
tree = $( git write-tree) &&
commit = $( printf "%s\n" "Test" "" | git commit-tree " $tree " ) &&
git update-ref HEAD " $commit " &&
echo 2 >a1 &&
git commit --quiet -m "This is a very, very long first line for the commit message to see if it is wrapped correctly" a1 &&
# test if the wrapping is still valid
# when replacing all is by treble clefs.
echo 3 >a1 &&
git commit --quiet -m " $(
echo "This is a very, very long first line for the commit message to see if it is wrapped correctly" |
sed "s/i/1234/g" |
tr 1234 "\360\235\204\236" ) " a1 &&
# now fsck up the utf8
git config i18n.commitencoding non-utf-8 &&
echo 4 >a1 &&
git commit --quiet -m " $(
echo "This is a very, very long first line for the commit message to see if it is wrapped correctly" |
sed "s/i/1234/g" |
tr 1234 "\370\235\204\236" ) " a1 &&
echo 5 >a1 &&
2010-10-31 04:46:54 +03:00
git commit --quiet -m "a 12 34 56 78" a1 &&
2010-05-04 06:58:04 +04:00
echo 6 >a1 &&
git commit --quiet -m "Commit by someone else" \
2010-05-04 06:59:55 +04:00
--author= "Someone else <not!me>" a1 &&
cat >expect.template <<-\E OF
A U Thor ( 5) :
SUBJECT
SUBJECT
SUBJECT
SUBJECT
SUBJECT
Someone else ( 1) :
SUBJECT
EOF
'
fuzz( ) {
file = $1 &&
sed "
2018-05-13 05:24:15 +03:00
s/$OID_REGEX /OBJECT_NAME/g
2017-11-12 18:25:23 +03:00
s/$_x35 /OBJID/g
2010-05-04 06:59:55 +04:00
s/^ \{ 6\} [ CTa] .*/ SUBJECT/g
s/^ \{ 8\} [ ^ ] .*/ CONTINUATION/g
" <" $file " >" $file .fuzzy" &&
sed "/CONTINUATION/ d" <" $file .fuzzy "
}
test_expect_success 'default output format' '
git shortlog HEAD >log &&
fuzz log >log.predictable &&
test_cmp expect.template log.predictable
'
test_expect_success 'pretty format' '
sed s/SUBJECT/OBJECT_NAME/ expect.template >expect &&
git shortlog --format= "%H" HEAD >log &&
fuzz log >log.predictable &&
test_cmp expect log.predictable
'
2010-05-04 07:18:57 +04:00
test_expect_success '--abbrev' '
2010-05-04 06:59:55 +04:00
sed s/SUBJECT/OBJID/ expect.template >expect &&
2017-11-12 18:25:23 +03:00
git shortlog --format= "%h" --abbrev= 35 HEAD >log &&
2010-05-04 06:59:55 +04:00
fuzz log >log.predictable &&
test_cmp expect log.predictable
'
test_expect_success 'output from user-defined format is re-wrapped' '
sed "s/SUBJECT/two lines/" expect.template >expect &&
git shortlog --format= "two%nlines" HEAD >log &&
fuzz log >log.predictable &&
test_cmp expect log.predictable
2010-05-04 06:57:36 +04:00
'
2006-12-23 00:15:59 +03:00
2014-07-22 02:09:27 +04:00
test_expect_success !MINGW 'shortlog wrapping' '
2010-05-04 06:57:36 +04:00
cat >expect <<\E OF &&
2006-12-23 00:15:59 +03:00
A U Thor ( 5) :
Test
This is a very, very long first line for the commit message to see if
it is wrapped correctly
Th𝄞s 𝄞s a very, very long f𝄞rst l𝄞ne for the comm𝄞t message to see 𝄞f
𝄞t 𝄞s wrapped correctly
Th<54> <68> <EFBFBD> <EFBFBD> s <20> <> <EFBFBD> <EFBFBD> s a very, very long f<> <66> <EFBFBD> <EFBFBD> rst l<> <6C> <EFBFBD> <EFBFBD> ne for the comm<6D> <6D> <EFBFBD> <EFBFBD> t
message to see <20> <> <EFBFBD> <EFBFBD> f <20> <> <EFBFBD> <EFBFBD> t <20> <> <EFBFBD> <EFBFBD> s wrapped correctly
a 12 34
56 78
2010-05-04 06:58:04 +04:00
Someone else ( 1) :
Commit by someone else
2006-12-23 00:15:59 +03:00
EOF
2010-05-04 06:57:36 +04:00
git shortlog -w HEAD >out &&
test_cmp expect out
'
2006-12-23 00:15:59 +03:00
2014-07-22 02:09:27 +04:00
test_expect_success !MINGW 'shortlog from non-git directory' '
2016-03-30 01:49:24 +03:00
git log --no-expand-tabs HEAD >log &&
2010-05-04 06:57:36 +04:00
GIT_DIR = non-existing git shortlog -w <log >out &&
test_cmp expect out
'
2008-03-15 00:35:24 +03:00
2016-01-18 23:02:40 +03:00
test_expect_success !MINGW 'shortlog can read --format=raw output' '
git log --format= raw HEAD >log &&
GIT_DIR = non-existing git shortlog -w <log >out &&
test_cmp expect out
'
2018-03-15 00:34:19 +03:00
test_expect_success 'shortlog from non-git directory refuses extra arguments' '
test_must_fail env GIT_DIR = non-existing git shortlog foo 2>out &&
test_i18ngrep "too many arguments" out
'
2012-12-11 09:59:21 +04:00
test_expect_success 'shortlog should add newline when input line matches wraplen' '
cat >expect <<\E OF &&
A U Thor ( 2) :
bbbbbbbbbbbbbbbbbb: bbbbbbbb bbb bbbb bbbbbbb bb bbbb bbb bbbbb bbbbbb
aaaaaaaaaaaaaaaaaaaaaa: aaaaaa aaaaaaaaaa aaaa aaaaaaaa aa aaaa aa aaa
EOF
git shortlog -w >out <<\E OF &&
commit 0000000000000000000000000000000000000001
Author: A U Thor <author@example.com>
Date: Thu Apr 7 15:14:13 2005 -0700
aaaaaaaaaaaaaaaaaaaaaa: aaaaaa aaaaaaaaaa aaaa aaaaaaaa aa aaaa aa aaa
commit 0000000000000000000000000000000000000002
Author: A U Thor <author@example.com>
Date: Thu Apr 7 15:14:13 2005 -0700
bbbbbbbbbbbbbbbbbb: bbbbbbbb bbb bbbb bbbbbbb bb bbbb bbb bbbbb bbbbbb
EOF
test_cmp expect out
'
2009-11-25 22:33:28 +03:00
iconvfromutf8toiso88591( ) {
2009-12-03 20:52:45 +03:00
printf "%s" " $* " | iconv -f UTF-8 -t ISO8859-1
2009-11-25 22:33:28 +03:00
}
DSCHO = "Jöhännës \"Dschö\" Schindëlin"
DSCHOE = " $DSCHO <Johannes.Schindelin@gmx.de> "
MSG1 = "set a1 to 2 and some non-ASCII chars: Äßø"
MSG2 = "set a1 to 3 and some non-ASCII chars: áæï"
cat > expect << EOF
$DSCHO ( 2) :
$MSG1
$MSG2
EOF
2014-07-22 02:09:27 +04:00
test_expect_success !MINGW 'shortlog encoding' '
2009-11-25 22:33:28 +03:00
git reset --hard " $commit " &&
git config --unset i18n.commitencoding &&
echo 2 > a1 &&
git commit --quiet -m " $MSG1 " --author= " $DSCHOE " a1 &&
2009-12-03 20:52:45 +03:00
git config i18n.commitencoding "ISO8859-1" &&
2009-11-25 22:33:28 +03:00
echo 3 > a1 &&
git commit --quiet -m " $( iconvfromutf8toiso88591 " $MSG2 " ) " \
--author= " $( iconvfromutf8toiso88591 " $DSCHOE " ) " a1 &&
git config --unset i18n.commitencoding &&
git shortlog HEAD~2.. > out &&
test_cmp expect out'
2014-05-30 23:57:25 +04:00
test_expect_success 'shortlog with revision pseudo options' '
git shortlog --all &&
git shortlog --branches &&
git shortlog --exclude= refs/heads/m* --all
'
2016-06-22 18:02:07 +03:00
test_expect_success 'shortlog with --output=<file>' '
2020-11-19 02:44:27 +03:00
git shortlog --output= shortlog -1 main >output &&
2018-08-20 00:57:23 +03:00
test_must_be_empty output &&
2016-07-11 16:11:37 +03:00
test_line_count = 3 shortlog
2016-06-22 18:02:07 +03:00
'
2016-12-16 16:51:41 +03:00
test_expect_success 'shortlog --committer (internal)' '
2016-12-20 21:35:54 +03:00
git checkout --orphan side &&
git commit --allow-empty -m one &&
git commit --allow-empty -m two &&
GIT_COMMITTER_NAME = "Sin Nombre" git commit --allow-empty -m three &&
2016-12-16 16:51:41 +03:00
cat >expect <<-\E OF &&
2016-12-20 21:35:54 +03:00
2 C O Mitter
1 Sin Nombre
2016-12-16 16:51:41 +03:00
EOF
git shortlog -nsc HEAD >actual &&
test_cmp expect actual
'
test_expect_success 'shortlog --committer (external)' '
git log --format= full | git shortlog -nsc >actual &&
test_cmp expect actual
'
2020-09-27 11:39:59 +03:00
test_expect_success '--group=committer is the same as --committer' '
git shortlog -ns --group= committer HEAD >actual &&
test_cmp expect actual
'
2020-09-27 11:40:04 +03:00
test_expect_success 'shortlog --group=trailer:signed-off-by' '
git commit --allow-empty -m foo -s &&
GIT_COMMITTER_NAME = "SOB One" \
GIT_COMMITTER_EMAIL = sob@example.com \
git commit --allow-empty -m foo -s &&
git commit --allow-empty --amend --no-edit -s &&
cat >expect <<-\E OF &&
2 C O Mitter <committer@example.com>
1 SOB One <sob@example.com>
EOF
2020-09-27 11:40:11 +03:00
git shortlog -nse --group= trailer:signed-off-by HEAD >actual &&
test_cmp expect actual
'
test_expect_success 'trailer idents are split' '
cat >expect <<-\E OF &&
2 C O Mitter
1 SOB One
EOF
2020-09-27 11:40:04 +03:00
git shortlog -ns --group= trailer:signed-off-by HEAD >actual &&
test_cmp expect actual
'
2020-09-27 11:40:11 +03:00
test_expect_success 'trailer idents are mailmapped' '
cat >expect <<-\E OF &&
2 C O Mitter
1 Another Name
EOF
echo "Another Name <sob@example.com>" >mail.map &&
git -c mailmap.file= mail.map shortlog -ns \
--group= trailer:signed-off-by HEAD >actual &&
test_cmp expect actual
'
2020-09-27 11:40:07 +03:00
test_expect_success 'shortlog de-duplicates trailers in a single commit' '
git commit --allow-empty -F - <<-\E OF &&
subject one
this message has two distinct values, plus a repeat
Repeated-trailer: Foo
Repeated-trailer: Bar
Repeated-trailer: Foo
EOF
git commit --allow-empty -F - <<-\E OF &&
subject two
similar to the previous, but without the second distinct value
Repeated-trailer: Foo
Repeated-trailer: Foo
EOF
cat >expect <<-\E OF &&
2 Foo
1 Bar
EOF
git shortlog -ns --group= trailer:repeated-trailer -2 HEAD >actual &&
test_cmp expect actual
'
shortlog: allow multiple groups to be specified
Now that shortlog supports reading from trailers, it can be useful to
combine counts from multiple trailers, or between trailers and authors.
This can be done manually by post-processing the output from multiple
runs, but it's non-trivial to make sure that each name/commit pair is
counted only once.
This patch teaches shortlog to accept multiple --group options on the
command line, and pull data from all of them. That makes it possible to
run:
git shortlog -ns --group=author --group=trailer:co-authored-by
to get a shortlog that counts authors and co-authors equally.
The implementation is mostly straightforward. The "group" enum becomes a
bitfield, and the trailer key becomes a list. I didn't bother
implementing the multi-group semantics for reading from stdin. It would
be possible to do, but the existing matching code makes it awkward, and
I doubt anybody cares.
The duplicate suppression we used for trailers now covers authors and
committers as well (though in non-trailer single-group mode we can skip
the hash insertion and lookup, since we only see one value per commit).
There is one subtlety: we now care about the case when no group bit is
set (in which case we default to showing the author). The caller in
builtin/log.c needs to be adapted to ask explicitly for authors, rather
than relying on shortlog_init(). It would be possible with some
gymnastics to make this keep working as-is, but it's not worth it for a
single caller.
Signed-off-by: Jeff King <peff@peff.net>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
2020-09-27 11:40:15 +03:00
test_expect_success 'shortlog can match multiple groups' '
git commit --allow-empty -F - <<-\E OF &&
subject one
this has two trailers that are distinct from the author; it will count
3 times in the output
Some-trailer: User A <a@example.com>
Another-trailer: User B <b@example.com>
EOF
git commit --allow-empty -F - <<-\E OF &&
subject two
this one has two trailers, one of which is a duplicate with the author;
it will only be counted once for them
Another-trailer: A U Thor <author@example.com>
Some-trailer: User B <b@example.com>
EOF
cat >expect <<-\E OF &&
2 A U Thor
2 User B
1 User A
EOF
git shortlog -ns \
--group= author \
--group= trailer:some-trailer \
--group= trailer:another-trailer \
-2 HEAD >actual &&
test_cmp expect actual
'
test_expect_success 'set up option selection tests' '
git commit --allow-empty -F - <<-\E OF
subject
body
Trailer-one: value-one
Trailer-two: value-two
EOF
'
test_expect_success '--no-group resets group list to author' '
cat >expect <<-\E OF &&
1 A U Thor
EOF
git shortlog -ns \
--group= committer \
--group= trailer:trailer-one \
--no-group \
-1 HEAD >actual &&
test_cmp expect actual
'
test_expect_success '--no-group resets trailer list' '
cat >expect <<-\E OF &&
1 value-two
EOF
git shortlog -ns \
--group= trailer:trailer-one \
--no-group \
--group= trailer:trailer-two \
-1 HEAD >actual &&
test_cmp expect actual
'
test_expect_success 'stdin with multiple groups reports error' '
git log >log &&
test_must_fail git shortlog --group= author --group= committer <log
'
2006-12-23 00:15:59 +03:00
test_done