| #!/bin/sh |
| |
| test_description='Merge-recursive merging renames' |
| . ./test-lib.sh |
| |
| test_expect_success setup \ |
| ' |
| cat >A <<\EOF && |
| a aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa |
| b bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb |
| c cccccccccccccccccccccccccccccccccccccccccccccccc |
| d dddddddddddddddddddddddddddddddddddddddddddddddd |
| e eeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeee |
| f ffffffffffffffffffffffffffffffffffffffffffffffff |
| g gggggggggggggggggggggggggggggggggggggggggggggggg |
| h hhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhh |
| i iiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiii |
| j jjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjj |
| k kkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkk |
| l llllllllllllllllllllllllllllllllllllllllllllllll |
| m mmmmmmmmmmmmmmmmmmmmmmmmmmmmmmmmmmmmmmmmmmmmmmmm |
| n nnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnn |
| o oooooooooooooooooooooooooooooooooooooooooooooooo |
| EOF |
| |
| cat >M <<\EOF && |
| A AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA |
| B BBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBB |
| C CCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCC |
| D DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD |
| E EEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEE |
| F FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF |
| G GGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGG |
| H HHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHHH |
| I IIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIII |
| J JJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJJ |
| K KKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKKK |
| L LLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLLL |
| M MMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMM |
| N NNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNN |
| O OOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOO |
| EOF |
| |
| git add A M && |
| git commit -m "initial has A and M" && |
| git branch white && |
| git branch red && |
| git branch blue && |
| git branch yellow && |
| git branch change && |
| git branch change+rename && |
| |
| sed -e "/^g /s/.*/g : master changes a line/" <A >A+ && |
| mv A+ A && |
| git commit -a -m "master updates A" && |
| |
| git checkout yellow && |
| rm -f M && |
| git commit -a -m "yellow removes M" && |
| |
| git checkout white && |
| sed -e "/^g /s/.*/g : white changes a line/" <A >B && |
| sed -e "/^G /s/.*/G : colored branch changes a line/" <M >N && |
| rm -f A M && |
| git update-index --add --remove A B M N && |
| git commit -m "white renames A->B, M->N" && |
| |
| git checkout red && |
| sed -e "/^g /s/.*/g : red changes a line/" <A >B && |
| sed -e "/^G /s/.*/G : colored branch changes a line/" <M >N && |
| rm -f A M && |
| git update-index --add --remove A B M N && |
| git commit -m "red renames A->B, M->N" && |
| |
| git checkout blue && |
| sed -e "/^g /s/.*/g : blue changes a line/" <A >C && |
| sed -e "/^G /s/.*/G : colored branch changes a line/" <M >N && |
| rm -f A M && |
| git update-index --add --remove A C M N && |
| git commit -m "blue renames A->C, M->N" && |
| |
| git checkout change && |
| sed -e "/^g /s/.*/g : changed line/" <A >A+ && |
| mv A+ A && |
| git commit -q -a -m "changed" && |
| |
| git checkout change+rename && |
| sed -e "/^g /s/.*/g : changed line/" <A >B && |
| rm A && |
| git update-index --add B && |
| git commit -q -a -m "changed and renamed" && |
| |
| git checkout master' |
| |
| test_expect_success 'pull renaming branch into unrenaming one' \ |
| ' |
| git show-branch |
| git pull . white && { |
| echo "BAD: should have conflicted" |
| return 1 |
| } |
| git ls-files -s |
| test "$(git ls-files -u B | wc -l)" -eq 3 || { |
| echo "BAD: should have left stages for B" |
| return 1 |
| } |
| test "$(git ls-files -s N | wc -l)" -eq 1 || { |
| echo "BAD: should have merged N" |
| return 1 |
| } |
| sed -ne "/^g/{ |
| p |
| q |
| }" B | grep master || { |
| echo "BAD: should have listed our change first" |
| return 1 |
| } |
| test "$(git diff white N | wc -l)" -eq 0 || { |
| echo "BAD: should have taken colored branch" |
| return 1 |
| } |
| ' |
| |
| test_expect_success 'pull renaming branch into another renaming one' \ |
| ' |
| rm -f B |
| git reset --hard |
| git checkout red |
| git pull . white && { |
| echo "BAD: should have conflicted" |
| return 1 |
| } |
| test "$(git ls-files -u B | wc -l)" -eq 3 || { |
| echo "BAD: should have left stages" |
| return 1 |
| } |
| test "$(git ls-files -s N | wc -l)" -eq 1 || { |
| echo "BAD: should have merged N" |
| return 1 |
| } |
| sed -ne "/^g/{ |
| p |
| q |
| }" B | grep red || { |
| echo "BAD: should have listed our change first" |
| return 1 |
| } |
| test "$(git diff white N | wc -l)" -eq 0 || { |
| echo "BAD: should have taken colored branch" |
| return 1 |
| } |
| ' |
| |
| test_expect_success 'pull unrenaming branch into renaming one' \ |
| ' |
| git reset --hard |
| git show-branch |
| git pull . master && { |
| echo "BAD: should have conflicted" |
| return 1 |
| } |
| test "$(git ls-files -u B | wc -l)" -eq 3 || { |
| echo "BAD: should have left stages" |
| return 1 |
| } |
| test "$(git ls-files -s N | wc -l)" -eq 1 || { |
| echo "BAD: should have merged N" |
| return 1 |
| } |
| sed -ne "/^g/{ |
| p |
| q |
| }" B | grep red || { |
| echo "BAD: should have listed our change first" |
| return 1 |
| } |
| test "$(git diff white N | wc -l)" -eq 0 || { |
| echo "BAD: should have taken colored branch" |
| return 1 |
| } |
| ' |
| |
| test_expect_success 'pull conflicting renames' \ |
| ' |
| git reset --hard |
| git show-branch |
| git pull . blue && { |
| echo "BAD: should have conflicted" |
| return 1 |
| } |
| test "$(git ls-files -u A | wc -l)" -eq 1 || { |
| echo "BAD: should have left a stage" |
| return 1 |
| } |
| test "$(git ls-files -u B | wc -l)" -eq 1 || { |
| echo "BAD: should have left a stage" |
| return 1 |
| } |
| test "$(git ls-files -u C | wc -l)" -eq 1 || { |
| echo "BAD: should have left a stage" |
| return 1 |
| } |
| test "$(git ls-files -s N | wc -l)" -eq 1 || { |
| echo "BAD: should have merged N" |
| return 1 |
| } |
| sed -ne "/^g/{ |
| p |
| q |
| }" B | grep red || { |
| echo "BAD: should have listed our change first" |
| return 1 |
| } |
| test "$(git diff white N | wc -l)" -eq 0 || { |
| echo "BAD: should have taken colored branch" |
| return 1 |
| } |
| ' |
| |
| test_expect_success 'interference with untracked working tree file' ' |
| |
| git reset --hard |
| git show-branch |
| echo >A this file should not matter |
| git pull . white && { |
| echo "BAD: should have conflicted" |
| return 1 |
| } |
| test -f A || { |
| echo "BAD: should have left A intact" |
| return 1 |
| } |
| ' |
| |
| test_expect_success 'interference with untracked working tree file' ' |
| |
| git reset --hard |
| git checkout white |
| git show-branch |
| rm -f A |
| echo >A this file should not matter |
| git pull . red && { |
| echo "BAD: should have conflicted" |
| return 1 |
| } |
| test -f A || { |
| echo "BAD: should have left A intact" |
| return 1 |
| } |
| ' |
| |
| test_expect_success 'interference with untracked working tree file' ' |
| |
| git reset --hard |
| rm -f A M |
| git checkout -f master |
| git tag -f anchor |
| git show-branch |
| git pull . yellow || { |
| echo "BAD: should have cleanly merged" |
| return 1 |
| } |
| test -f M && { |
| echo "BAD: should have removed M" |
| return 1 |
| } |
| git reset --hard anchor |
| ' |
| |
| test_expect_success 'updated working tree file should prevent the merge' ' |
| |
| git reset --hard |
| rm -f A M |
| git checkout -f master |
| git tag -f anchor |
| git show-branch |
| echo >>M one line addition |
| cat M >M.saved |
| git pull . yellow && { |
| echo "BAD: should have complained" |
| return 1 |
| } |
| test_cmp M M.saved || { |
| echo "BAD: should have left M intact" |
| return 1 |
| } |
| rm -f M.saved |
| ' |
| |
| test_expect_success 'updated working tree file should prevent the merge' ' |
| |
| git reset --hard |
| rm -f A M |
| git checkout -f master |
| git tag -f anchor |
| git show-branch |
| echo >>M one line addition |
| cat M >M.saved |
| git update-index M |
| git pull . yellow && { |
| echo "BAD: should have complained" |
| return 1 |
| } |
| test_cmp M M.saved || { |
| echo "BAD: should have left M intact" |
| return 1 |
| } |
| rm -f M.saved |
| ' |
| |
| test_expect_success 'interference with untracked working tree file' ' |
| |
| git reset --hard |
| rm -f A M |
| git checkout -f yellow |
| git tag -f anchor |
| git show-branch |
| echo >M this file should not matter |
| git pull . master || { |
| echo "BAD: should have cleanly merged" |
| return 1 |
| } |
| test -f M || { |
| echo "BAD: should have left M intact" |
| return 1 |
| } |
| git ls-files -s | grep M && { |
| echo "BAD: M must be untracked in the result" |
| return 1 |
| } |
| git reset --hard anchor |
| ' |
| |
| test_expect_success 'merge of identical changes in a renamed file' ' |
| rm -f A M N |
| git reset --hard && |
| git checkout change+rename && |
| GIT_MERGE_VERBOSITY=3 git merge change | grep "^Skipped B" && |
| git reset --hard HEAD^ && |
| git checkout change && |
| GIT_MERGE_VERBOSITY=3 git merge change+rename | grep "^Skipped B" |
| ' |
| |
| test_done |