From: Elijah Newren <newren@gmail.com>
To: git@vger.kernel.org
Cc: Elijah Newren <newren@gmail.com>
Subject: [RFC PATCH v2 4/9] Add testcases for improved file collision conflict handling
Date: Mon, 20 Nov 2017 14:19:39 -0800 [thread overview]
Message-ID: <20171120221944.15431-5-newren@gmail.com> (raw)
In-Reply-To: <20171120221944.15431-1-newren@gmail.com>
Adds testcases dealing with file collisions for the following types of
conflicts:
* add/add
* rename/add
* rename/rename(2to1)
These tests include expectations for new, smarter behavior provided by
handle_file_collision(). Since that function is not in use yet, the
tests are currently expected to fail.
Signed-off-by: Elijah Newren <newren@gmail.com>
---
t/t6042-merge-rename-corner-cases.sh | 210 +++++++++++++++++++++++++++++++++++
1 file changed, 210 insertions(+)
diff --git a/t/t6042-merge-rename-corner-cases.sh b/t/t6042-merge-rename-corner-cases.sh
index 411550d2b6..d8fe797f0d 100755
--- a/t/t6042-merge-rename-corner-cases.sh
+++ b/t/t6042-merge-rename-corner-cases.sh
@@ -575,4 +575,214 @@ test_expect_success 'rename/rename/add-dest merge still knows about conflicting
test ! -f c
'
+test_conflicts_with_adds_and_renames() {
+ test $1 != 0 && side1=rename || side1=add
+ test $2 != 0 && side2=rename || side2=add
+
+ # Setup:
+ # L
+ # / \
+ # master ?
+ # \ /
+ # R
+ #
+ # Where:
+ # Both L and R have files named 'three-unrelated' and
+ # 'three-related' which collide. Each of the colliding files
+ # could have been involved in a rename, in which case there was a
+ # file named 'one-[un]related' or 'two-[un]related' that was
+ # modified on the opposite side of history and renamed into the
+ # collision on this side of history.
+ #
+ # Questions for both three-unrelated and three-related:
+ # 1) The index should contain both a stage 2 and stage 3 entry
+ # for the colliding file. Does it?
+ # 2) When renames are involved, the content merges are clean, so
+ # the index should reflect the content merges, not merely the
+ # version of the colliding file from the prior commit. Does
+ # it?
+ #
+ # Questions for three-unrelated:
+ # 3) There should be files in the worktree named
+ # 'three-unrelated~HEAD' and 'three-unrelated~R^0' with the
+ # (content-merged) version of 'three-unrelated' from the
+ # appropriate side of the merge. Are they present?
+ # 4) There should be no file named 'three-unrelated' in the
+ # working tree. That'd make it too likely that users would
+ # use it instead of carefully looking at both
+ # three-unrelated~HEAD and three-unrelated~R^0. Is it
+ # correctly missing?
+ #
+ # Questions for three-related:
+ # 3) There should be a file in the worktree named three-related
+ # containing the two-way merged contents of the content-merged
+ # versions of three-related from each of the two colliding
+ # files. Is it present?
+ # 4) There should not be any three-related~* files in the working
+ # tree.
+ test_expect_success "setup simple $side1/$side2 conflict" '
+ git rm -rf . &&
+ git clean -fdqx &&
+ rm -rf .git &&
+ git init &&
+
+ # Create a simple file with 10 lines
+ ten="0 1 2 3 4 5 6 7 8 9" &&
+ for i in $ten
+ do
+ echo line $i in a sample file
+ done >unrelated1_v1 &&
+ # Create a second version of same file with one more line
+ cat unrelated1_v1 >unrelated1_v2 &&
+ echo another line >>unrelated1_v2 &&
+
+ # Create an unrelated simple file with 10 lines
+ for i in $ten
+ do
+ echo line $i in another sample file
+ done >unrelated2_v1 &&
+ # Create a second version of same file with one more line
+ cat unrelated2_v1 >unrelated2_v2 &&
+ echo another line >>unrelated2_v2 &&
+
+ # Create some related files now
+ for i in $ten
+ do
+ echo Random base content line $i
+ done >related1_v1 &&
+ cp -a related1_v1 related1_v2 &&
+ echo modification >>related1_v2 &&
+
+ cp -a related1_v1 related2_v1 &&
+ echo more stuff >>related2_v1 &&
+ cp -a related2_v1 related2_v2 &&
+ echo yet more stuff >>related2_v2 &&
+
+ # Use a tag to record both these files for simple access,
+ # and clean out these untracked files
+ git tag unrelated1_v1 `git hash-object -w unrelated1_v1` &&
+ git tag unrelated1_v2 `git hash-object -w unrelated1_v2` &&
+ git tag unrelated2_v1 `git hash-object -w unrelated2_v1` &&
+ git tag unrelated2_v2 `git hash-object -w unrelated2_v2` &&
+ git tag related1_v1 `git hash-object -w related1_v1` &&
+ git tag related1_v2 `git hash-object -w related1_v2` &&
+ git tag related2_v1 `git hash-object -w related2_v1` &&
+ git tag related2_v2 `git hash-object -w related2_v2` &&
+ git clean -f &&
+
+ # Setup merge-base, consisting of files named "one-*"
+ # and "two-*" if renames were involved.
+ touch irrelevant_file &&
+ git add irrelevant_file &&
+ if [ $side1 == "rename" ]; then
+ git show unrelated1_v1 >one-unrelated &&
+ git add one-unrelated
+ git show related1_v1 >one-related &&
+ git add one-related
+ fi &&
+ if [ $side2 == "rename" ]; then
+ git show unrelated2_v1 >two-unrelated &&
+ git add two-unrelated
+ git show related2_v1 >two-related &&
+ git add two-related
+ fi &&
+ test_tick && git commit -m initial &&
+
+ git branch L &&
+ git branch R &&
+
+ # Handle the left side
+ git checkout L &&
+ if [ $side1 == "rename" ]; then
+ git mv one-unrelated three-unrelated
+ git mv one-related three-related
+ else
+ git show unrelated1_v2 >three-unrelated &&
+ git add three-unrelated
+ git show related1_v2 >three-related &&
+ git add three-related
+ fi &&
+ if [ $side2 == "rename" ]; then
+ git show unrelated2_v2 >two-unrelated &&
+ git add two-unrelated
+ git show related2_v2 >two-related &&
+ git add two-related
+ fi &&
+ test_tick && git commit -m L &&
+
+ # Handle the right side
+ git checkout R &&
+ if [ $side1 == "rename" ]; then
+ git show unrelated1_v2 >one-unrelated &&
+ git add one-unrelated
+ git show related1_v2 >one-related &&
+ git add one-related
+ fi &&
+ if [ $side2 == "rename" ]; then
+ git mv two-unrelated three-unrelated
+ git mv two-related three-related
+ else
+ git show unrelated2_v2 >three-unrelated &&
+ git add three-unrelated
+ git show related2_v2 >three-related &&
+ git add three-related
+ fi &&
+ test_tick && git commit -m R
+ '
+
+ test_expect_failure "check simple $side1/$side2 conflict" '
+ git reset --hard &&
+ git checkout L^0 &&
+
+ # Merge must fail; there is a conflict
+ test_must_fail git merge -s recursive R^0 &&
+
+ # Make sure the index has the right number of entries
+ test 5 = $(git ls-files -s | wc -l) &&
+ test 4 = $(git ls-files -u | wc -l) &&
+
+ # Nothing should have touched irrelevant_file
+ test $(git rev-parse :0:irrelevant_file) = $(git rev-parse master:irrelevant_file) &&
+
+ # Even for renames, make sure the index contains the MERGED
+ # version of the file, not the version of the file that existed
+ # on the given side.
+ test $(git rev-parse :2:three-unrelated) = $(git rev-parse unrelated1_v2) &&
+ test $(git rev-parse :3:three-unrelated) = $(git rev-parse unrelated2_v2) &&
+ test $(git rev-parse :2:three-related) = $(git rev-parse related1_v2) &&
+ test $(git rev-parse :3:three-related) = $(git rev-parse related2_v2) &&
+
+ # Make sure we have the correct number of untracked files
+ test 2 = $(git ls-files -o | wc -l) &&
+
+ # Make sure each file (with merging if rename involved) is
+ # present in the working tree for the user to work with.
+ test $(git hash-object three-unrelated~HEAD) = $(git rev-parse unrelated1_v2) &&
+ test $(git hash-object three-unrelated~R^0) = $(git rev-parse unrelated2_v2) &&
+
+ # "three-unrelated" should not exist because there is no
+ # reason to give preference to either three-unrelated~HEAD
+ # or three-unrelated~R^0
+ test ! -f three-unrelated &&
+
+ # Make sure we have the correct merged contents for three-related
+ git show related1_v1 >expected &&
+ cat <<EOF >>expected &&
+<<<<<<< HEAD
+modification
+=======
+more stuff
+yet more stuff
+>>>>>>> R^0
+EOF
+
+ test_cmp expected three-related
+ '
+}
+
+test_conflicts_with_adds_and_renames 1 1
+test_conflicts_with_adds_and_renames 1 0
+test_conflicts_with_adds_and_renames 0 1
+test_conflicts_with_adds_and_renames 0 0
+
test_done
--
2.15.0.323.g31fe956618
next prev parent reply other threads:[~2017-11-20 22:20 UTC|newest]
Thread overview: 10+ messages / expand[flat|nested] mbox.gz Atom feed top
2017-11-20 22:19 [RFC PATCH v2 0/9] Improve merge recursive performance Elijah Newren
2017-11-20 22:19 ` [RFC PATCH v2 1/9] diffcore-rename: no point trying to find a match better than exact Elijah Newren
2017-11-20 22:19 ` [RFC PATCH v2 2/9] merge-recursive: avoid unnecessary string list lookups Elijah Newren
2017-11-20 22:19 ` [RFC PATCH v2 3/9] merge-recursive: new function for better colliding conflict resolutions Elijah Newren
2017-11-20 22:19 ` Elijah Newren [this message]
2017-11-20 22:19 ` [RFC PATCH v2 5/9] merge-recursive: fix rename/add conflict handling Elijah Newren
2017-11-20 22:19 ` [RFC PATCH v2 6/9] merge-recursive: improve handling for rename/rename(2to1) conflicts Elijah Newren
2017-11-20 22:19 ` [RFC PATCH v2 7/9] merge-recursive: improve handling for add/add conflicts Elijah Newren
2017-11-20 22:19 ` [RFC PATCH v2 8/9] merge-recursive: accelerate rename detection Elijah Newren
2017-11-20 22:19 ` [RFC PATCH v2 9/9] diffcore-rename: filter rename_src list when possible Elijah Newren
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
List information: http://vger.kernel.org/majordomo-info.html
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20171120221944.15431-5-newren@gmail.com \
--to=newren@gmail.com \
--cc=git@vger.kernel.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
Code repositories for project(s) associated with this public inbox
https://80x24.org/mirrors/git.git
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).