git/t/t8003-blame-corner-cases.sh
Jeff King 6dbf0c7beb t8003: check output of coalesced blame
Commit f0cbe742f4 (blame: add a test to cover blame_coalesce(),
2019-06-20) added a test case where blame can usefully coalesce two
groups of lines. But since it relies on the normal blame output, it only
exercises the code and can't tell whether the lines were actually
joined into a single group.

However, by using --porcelain output, we can see how git-blame considers
the groupings (and likewise how the coalescing might have a real
user-visible impact for a tool that uses the porcelain-output
groupings). This lets us confirm that we are indeed coalescing correctly
(and the fact that this test case requires coalescing can be verified by
dropping the call to blame_coalesce(), causing the test to fail).

Signed-off-by: Jeff King <peff@peff.net>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
2020-08-13 10:08:10 -07:00

310 lines
6 KiB
Bash
Executable file

#!/bin/sh
test_description='git blame corner cases'
. ./test-lib.sh
pick_fc='s/^[0-9a-f^]* *\([^ ]*\) *(\([^ ]*\) .*/\1-\2/'
test_expect_success setup '
echo A A A A A >one &&
echo B B B B B >two &&
echo C C C C C >tres &&
echo ABC >mouse &&
for i in 1 2 3 4 5 6 7 8 9
do
echo $i
done >nine_lines &&
for i in 1 2 3 4 5 6 7 8 9 a
do
echo $i
done >ten_lines &&
git add one two tres mouse nine_lines ten_lines &&
test_tick &&
GIT_AUTHOR_NAME=Initial git commit -m Initial &&
cat one >uno &&
mv two dos &&
cat one >>tres &&
echo DEF >>mouse &&
git add uno dos tres mouse &&
test_tick &&
GIT_AUTHOR_NAME=Second git commit -a -m Second &&
echo GHIJK >>mouse &&
git add mouse &&
test_tick &&
GIT_AUTHOR_NAME=Third git commit -m Third &&
cat mouse >cow &&
git add cow &&
test_tick &&
GIT_AUTHOR_NAME=Fourth git commit -m Fourth &&
cat >cow <<-\EOF &&
ABC
DEF
XXXX
GHIJK
EOF
git add cow &&
test_tick &&
GIT_AUTHOR_NAME=Fifth git commit -m Fifth
'
test_expect_success 'straight copy without -C' '
git blame uno | grep Second
'
test_expect_success 'straight move without -C' '
git blame dos | grep Initial
'
test_expect_success 'straight copy with -C' '
git blame -C1 uno | grep Second
'
test_expect_success 'straight move with -C' '
git blame -C1 dos | grep Initial
'
test_expect_success 'straight copy with -C -C' '
git blame -C -C1 uno | grep Initial
'
test_expect_success 'straight move with -C -C' '
git blame -C -C1 dos | grep Initial
'
test_expect_success 'append without -C' '
git blame -L2 tres | grep Second
'
test_expect_success 'append with -C' '
git blame -L2 -C1 tres | grep Second
'
test_expect_success 'append with -C -C' '
git blame -L2 -C -C1 tres | grep Second
'
test_expect_success 'append with -C -C -C' '
git blame -L2 -C -C -C1 tres | grep Initial
'
test_expect_success 'blame wholesale copy' '
git blame -f -C -C1 HEAD^ -- cow | sed -e "$pick_fc" >current &&
cat >expected <<-\EOF &&
mouse-Initial
mouse-Second
mouse-Third
EOF
test_cmp expected current
'
test_expect_success 'blame wholesale copy and more' '
git blame -f -C -C1 HEAD -- cow | sed -e "$pick_fc" >current &&
cat >expected <<-\EOF &&
mouse-Initial
mouse-Second
cow-Fifth
mouse-Third
EOF
test_cmp expected current
'
test_expect_success 'blame wholesale copy and more in the index' '
cat >horse <<-\EOF &&
ABC
DEF
XXXX
YYYY
GHIJK
EOF
git add horse &&
test_when_finished "git rm -f horse" &&
git blame -f -C -C1 -- horse | sed -e "$pick_fc" >current &&
cat >expected <<-\EOF &&
mouse-Initial
mouse-Second
cow-Fifth
horse-Not
mouse-Third
EOF
test_cmp expected current
'
test_expect_success 'blame during cherry-pick with file rename conflict' '
test_when_finished "git reset --hard && git checkout master" &&
git checkout HEAD~3 &&
echo MOUSE >> mouse &&
git mv mouse rodent &&
git add rodent &&
GIT_AUTHOR_NAME=Rodent git commit -m "rodent" &&
git checkout --detach master &&
(git cherry-pick HEAD@{1} || test $? -eq 1) &&
git show HEAD@{1}:rodent > rodent &&
git add rodent &&
git blame -f -C -C1 rodent | sed -e "$pick_fc" >current &&
cat >expected <<-\EOF &&
mouse-Initial
mouse-Second
rodent-Not
EOF
test_cmp expected current
'
test_expect_success 'blame path that used to be a directory' '
mkdir path &&
echo A A A A A >path/file &&
echo B B B B B >path/elif &&
git add path &&
test_tick &&
git commit -m "path was a directory" &&
rm -fr path &&
echo A A A A A >path &&
git add path &&
test_tick &&
git commit -m "path is a regular file" &&
git blame HEAD^.. -- path
'
test_expect_success 'blame to a commit with no author name' '
TREE=$(git rev-parse HEAD:) &&
cat >badcommit <<EOF &&
tree $TREE
author <noname> 1234567890 +0000
committer David Reiss <dreiss@facebook.com> 1234567890 +0000
some message
EOF
COMMIT=$(git hash-object -t commit -w badcommit) &&
git --no-pager blame $COMMIT -- uno >/dev/null
'
test_expect_success 'blame -L with invalid start' '
test_must_fail git blame -L5 tres 2>errors &&
test_i18ngrep "has only 2 lines" errors
'
test_expect_success 'blame -L with invalid end' '
git blame -L1,5 tres >out &&
test_line_count = 2 out
'
test_expect_success 'blame parses <end> part of -L' '
git blame -L1,1 tres >out &&
test_line_count = 1 out
'
test_expect_success 'blame -Ln,-(n+1)' '
git blame -L3,-4 nine_lines >out &&
test_line_count = 3 out
'
test_expect_success 'indent of line numbers, nine lines' '
git blame nine_lines >actual &&
test $(grep -c " " actual) = 0
'
test_expect_success 'indent of line numbers, ten lines' '
git blame ten_lines >actual &&
test $(grep -c " " actual) = 9
'
test_expect_success 'setup file with CRLF newlines' '
git config core.autocrlf false &&
printf "testcase\n" >crlffile &&
git add crlffile &&
git commit -m testcase &&
printf "testcase\r\n" >crlffile
'
test_expect_success 'blame file with CRLF core.autocrlf true' '
git config core.autocrlf true &&
git blame crlffile >actual &&
grep "A U Thor" actual
'
test_expect_success 'blame file with CRLF attributes text' '
git config core.autocrlf false &&
echo "crlffile text" >.gitattributes &&
git blame crlffile >actual &&
grep "A U Thor" actual
'
test_expect_success 'blame file with CRLF core.autocrlf=true' '
git config core.autocrlf false &&
printf "testcase\r\n" >crlfinrepo &&
>.gitattributes &&
git add crlfinrepo &&
git commit -m "add crlfinrepo" &&
git config core.autocrlf true &&
mv crlfinrepo tmp &&
git checkout crlfinrepo &&
rm tmp &&
git blame crlfinrepo >actual &&
grep "A U Thor" actual
'
test_expect_success 'blame coalesce' '
cat >giraffe <<-\EOF &&
ABC
DEF
EOF
git add giraffe &&
git commit -m "original file" &&
oid=$(git rev-parse HEAD) &&
cat >giraffe <<-\EOF &&
ABC
SPLIT
DEF
EOF
git add giraffe &&
git commit -m "interior SPLIT line" &&
cat >giraffe <<-\EOF &&
ABC
DEF
EOF
git add giraffe &&
git commit -m "same contents as original" &&
cat >expect <<-EOF &&
$oid 1 1 2
$oid 2 2
EOF
git blame --porcelain giraffe >actual.raw &&
grep "^$oid" actual.raw >actual &&
test_cmp expect actual
'
test_done