t1400: prepare for `main` being default branch name
[git] / t / t4108-apply-threeway.sh
1 #!/bin/sh
2
3 test_description='git apply --3way'
4
5 . ./test-lib.sh
6
7 print_sanitized_conflicted_diff () {
8         git diff HEAD >diff.raw &&
9         sed -e '
10                 /^index /d
11                 s/^\(+[<>|][<>|][<>|][<>|]*\) .*/\1/
12         ' diff.raw
13 }
14
15 test_expect_success setup '
16         test_tick &&
17         test_write_lines 1 2 3 4 5 6 7 >one &&
18         cat one >two &&
19         git add one two &&
20         git commit -m initial &&
21
22         git branch side &&
23
24         test_tick &&
25         test_write_lines 1 two 3 4 5 six 7 >one &&
26         test_write_lines 1 two 3 4 5 6 7 >two &&
27         git commit -a -m master &&
28
29         git checkout side &&
30         test_write_lines 1 2 3 4 five 6 7 >one &&
31         test_write_lines 1 2 3 4 five 6 7 >two &&
32         git commit -a -m side &&
33
34         git checkout master
35 '
36
37 test_expect_success 'apply without --3way' '
38         git diff side^ side >P.diff &&
39
40         # should fail to apply
41         git reset --hard &&
42         git checkout master^0 &&
43         test_must_fail git apply --index P.diff &&
44         # should leave things intact
45         git diff-files --exit-code &&
46         git diff-index --exit-code --cached HEAD
47 '
48
49 test_apply_with_3way () {
50         # Merging side should be similar to applying this patch
51         git diff ...side >P.diff &&
52
53         # The corresponding conflicted merge
54         git reset --hard &&
55         git checkout master^0 &&
56         test_must_fail git merge --no-commit side &&
57         git ls-files -s >expect.ls &&
58         print_sanitized_conflicted_diff >expect.diff &&
59
60         # should fail to apply
61         git reset --hard &&
62         git checkout master^0 &&
63         test_must_fail git apply --index --3way P.diff &&
64         git ls-files -s >actual.ls &&
65         print_sanitized_conflicted_diff >actual.diff &&
66
67         # The result should resemble the corresponding merge
68         test_cmp expect.ls actual.ls &&
69         test_cmp expect.diff actual.diff
70 }
71
72 test_expect_success 'apply with --3way' '
73         test_apply_with_3way
74 '
75
76 test_expect_success 'apply with --3way with merge.conflictStyle = diff3' '
77         test_config merge.conflictStyle diff3 &&
78         test_apply_with_3way
79 '
80
81 test_expect_success 'apply with --3way with rerere enabled' '
82         test_config rerere.enabled true &&
83
84         # Merging side should be similar to applying this patch
85         git diff ...side >P.diff &&
86
87         # The corresponding conflicted merge
88         git reset --hard &&
89         git checkout master^0 &&
90         test_must_fail git merge --no-commit side &&
91
92         # Manually resolve and record the resolution
93         test_write_lines 1 two 3 4 five six 7 >one &&
94         git rerere &&
95         cat one >expect &&
96
97         # should fail to apply
98         git reset --hard &&
99         git checkout master^0 &&
100         test_must_fail git apply --index --3way P.diff &&
101
102         # but rerere should have replayed the recorded resolution
103         test_cmp expect one
104 '
105
106 test_expect_success 'apply -3 with add/add conflict setup' '
107         git reset --hard &&
108
109         git checkout -b adder &&
110         test_write_lines 1 2 3 4 5 6 7 >three &&
111         test_write_lines 1 2 3 4 5 6 7 >four &&
112         git add three four &&
113         git commit -m "add three and four" &&
114
115         git checkout -b another adder^ &&
116         test_write_lines 1 2 3 4 5 6 7 >three &&
117         test_write_lines 1 2 3 four 5 6 7 >four &&
118         git add three four &&
119         git commit -m "add three and four" &&
120
121         # Merging another should be similar to applying this patch
122         git diff adder...another >P.diff &&
123
124         git checkout adder^0 &&
125         test_must_fail git merge --no-commit another &&
126         git ls-files -s >expect.ls &&
127         print_sanitized_conflicted_diff >expect.diff
128 '
129
130 test_expect_success 'apply -3 with add/add conflict' '
131         # should fail to apply ...
132         git reset --hard &&
133         git checkout adder^0 &&
134         test_must_fail git apply --index --3way P.diff &&
135         # ... and leave conflicts in the index and in the working tree
136         git ls-files -s >actual.ls &&
137         print_sanitized_conflicted_diff >actual.diff &&
138
139         # The result should resemble the corresponding merge
140         test_cmp expect.ls actual.ls &&
141         test_cmp expect.diff actual.diff
142 '
143
144 test_expect_success 'apply -3 with add/add conflict (dirty working tree)' '
145         # should fail to apply ...
146         git reset --hard &&
147         git checkout adder^0 &&
148         echo >>four &&
149         cat four >four.save &&
150         cat three >three.save &&
151         git ls-files -s >expect.ls &&
152         test_must_fail git apply --index --3way P.diff &&
153         # ... and should not touch anything
154         git ls-files -s >actual.ls &&
155         test_cmp expect.ls actual.ls &&
156         test_cmp four.save four &&
157         test_cmp three.save three
158 '
159
160 test_done