t/t3437: simplify and document the test helpers
[git] / t / t3437-rebase-fixup-options.sh
1 #!/bin/sh
2 #
3 # Copyright (c) 2018 Phillip Wood
4 #
5
6 test_description='git rebase interactive fixup options
7
8 This test checks the "fixup [-C|-c]" command of rebase interactive.
9 In addition to amending the contents of the commit, "fixup -C"
10 replaces the original commit message with the message of the fixup
11 commit. "fixup -c" also replaces the original message, but opens the
12 editor to allow the user to edit the message before committing. Similar
13 to the "fixup" command that works with "fixup!", "fixup -C" works with
14 "amend!" upon --autosquash.
15 '
16
17 . ./test-lib.sh
18
19 . "$TEST_DIRECTORY"/lib-rebase.sh
20
21 EMPTY=""
22
23 # test_commit_message <rev> -m <msg>
24 # test_commit_message <rev> <path>
25 # Verify that the commit message of <rev> matches
26 # <msg> or the content of <path>.
27 test_commit_message () {
28         git show --no-patch --pretty=format:%B "$1" >actual &&
29         case "$2" in
30         -m)
31                 echo "$3" >expect &&
32                 test_cmp expect actual ;;
33         *)
34                 test_cmp "$2" actual ;;
35         esac
36 }
37
38 get_author () {
39         rev="$1" &&
40         git log -1 --pretty=format:"%an %ae %at" "$rev"
41 }
42
43 test_expect_success 'setup' '
44         cat >message <<-EOF &&
45         amend! B
46         $EMPTY
47         new subject
48         $EMPTY
49         new
50         body
51         EOF
52
53         test_commit A A &&
54         test_commit B B &&
55         get_author HEAD >expected-author &&
56         ORIG_AUTHOR_NAME="$GIT_AUTHOR_NAME" &&
57         ORIG_AUTHOR_EMAIL="$GIT_AUTHOR_EMAIL" &&
58         GIT_AUTHOR_NAME="Amend Author" &&
59         GIT_AUTHOR_EMAIL="amend@example.com" &&
60         test_commit "$(cat message)" A A1 A1 &&
61         test_commit A2 A &&
62         test_commit A3 A &&
63         GIT_AUTHOR_NAME="$ORIG_AUTHOR_NAME" &&
64         GIT_AUTHOR_EMAIL="$ORIG_AUTHOR_EMAIL" &&
65         git checkout -b conflicts-branch A &&
66         test_commit conflicts A &&
67
68         set_fake_editor &&
69         git checkout -b branch B &&
70         echo B1 >B &&
71         test_tick &&
72         git commit --fixup=HEAD -a &&
73         test_tick &&
74         git commit --allow-empty -F - <<-EOF &&
75         amend! B
76         $EMPTY
77         B
78         $EMPTY
79         edited 1
80         EOF
81         test_tick &&
82         git commit --allow-empty -F - <<-EOF &&
83         amend! amend! B
84         $EMPTY
85         B
86         $EMPTY
87         edited 1
88         $EMPTY
89         edited 2
90         EOF
91         echo B2 >B &&
92         test_tick &&
93         FAKE_COMMIT_AMEND="edited squash" git commit --squash=HEAD -a &&
94         echo B3 >B &&
95         test_tick &&
96         git commit -a -F - <<-EOF &&
97         amend! amend! amend! B
98         $EMPTY
99         B
100         $EMPTY
101         edited 1
102         $EMPTY
103         edited 2
104         $EMPTY
105         edited 3
106         EOF
107
108         GIT_AUTHOR_NAME="Rebase Author" &&
109         GIT_AUTHOR_EMAIL="rebase.author@example.com" &&
110         GIT_COMMITTER_NAME="Rebase Committer" &&
111         GIT_COMMITTER_EMAIL="rebase.committer@example.com"
112 '
113
114 test_expect_success 'simple fixup -C works' '
115         test_when_finished "test_might_fail git rebase --abort" &&
116         git checkout --detach A2 &&
117         FAKE_LINES="1 fixup_-C 2" git rebase -i B &&
118         test_cmp_rev HEAD^ B &&
119         test_cmp_rev HEAD^{tree} A2^{tree} &&
120         test_commit_message HEAD -m "A2"
121 '
122
123 test_expect_success 'simple fixup -c works' '
124         test_when_finished "test_might_fail git rebase --abort" &&
125         git checkout --detach A2 &&
126         git log -1 --pretty=format:%B >expected-fixup-message &&
127         test_write_lines "" "Modified A2" >>expected-fixup-message &&
128         FAKE_LINES="1 fixup_-c 2" \
129                 FAKE_COMMIT_AMEND="Modified A2" \
130                 git rebase -i B &&
131         test_cmp_rev HEAD^ B &&
132         test_cmp_rev HEAD^{tree} A2^{tree} &&
133         test_commit_message HEAD expected-fixup-message
134 '
135
136 test_expect_success 'fixup -C removes amend! from message' '
137         test_when_finished "test_might_fail git rebase --abort" &&
138         git checkout --detach A1 &&
139         git log -1 --pretty=format:%b >expected-message &&
140         FAKE_LINES="1 fixup_-C 2" git rebase -i A &&
141         test_cmp_rev HEAD^ A &&
142         test_cmp_rev HEAD^{tree} A1^{tree} &&
143         test_commit_message HEAD expected-message &&
144         get_author HEAD >actual-author &&
145         test_cmp expected-author actual-author
146 '
147
148 test_expect_success 'fixup -C with conflicts gives correct message' '
149         test_when_finished "test_might_fail git rebase --abort" &&
150         git checkout --detach A1 &&
151         git log -1 --pretty=format:%b >expected-message &&
152         test_write_lines "" "edited" >>expected-message &&
153         test_must_fail env FAKE_LINES="1 fixup_-C 2" git rebase -i conflicts &&
154         git checkout --theirs -- A &&
155         git add A &&
156         FAKE_COMMIT_AMEND=edited git rebase --continue &&
157         test_cmp_rev HEAD^ conflicts &&
158         test_cmp_rev HEAD^{tree} A1^{tree} &&
159         test_commit_message HEAD expected-message &&
160         get_author HEAD >actual-author &&
161         test_cmp expected-author actual-author
162 '
163
164 test_expect_success 'skipping fixup -C after fixup gives correct message' '
165         test_when_finished "test_might_fail git rebase --abort" &&
166         git checkout --detach A3 &&
167         test_must_fail env FAKE_LINES="1 fixup 2 fixup_-C 4" git rebase -i A &&
168         git reset --hard &&
169         FAKE_COMMIT_AMEND=edited git rebase --continue &&
170         test_commit_message HEAD -m "B"
171 '
172
173 test_expect_success 'sequence of fixup, fixup -C & squash --signoff works' '
174         git checkout --detach branch &&
175         FAKE_LINES="1 fixup 2 fixup_-C 3 fixup_-C 4 squash 5 fixup_-C 6" \
176                 FAKE_COMMIT_AMEND=squashed \
177                 FAKE_MESSAGE_COPY=actual-squash-message \
178                 git -c commit.status=false rebase -ik --signoff A &&
179         git diff-tree --exit-code --patch HEAD branch -- &&
180         test_cmp_rev HEAD^ A &&
181         test_i18ncmp "$TEST_DIRECTORY/t3437/expected-squash-message" \
182                 actual-squash-message
183 '
184
185 test_expect_success 'first fixup -C commented out in sequence fixup fixup -C fixup -C' '
186         test_when_finished "test_might_fail git rebase --abort" &&
187         git checkout branch && git checkout --detach branch~2 &&
188         git log -1 --pretty=format:%b >expected-message &&
189         FAKE_LINES="1 fixup 2 fixup_-C 3 fixup_-C 4" git rebase -i A &&
190         test_cmp_rev HEAD^ A &&
191         test_commit_message HEAD expected-message
192 '
193
194 test_expect_success 'multiple fixup -c opens editor once' '
195         test_when_finished "test_might_fail git rebase --abort" &&
196         git checkout --detach A3 &&
197         base=$(git rev-parse HEAD~4) &&
198         FAKE_COMMIT_MESSAGE="Modified-A3" \
199                 FAKE_LINES="1 fixup_-C 2 fixup_-c 3 fixup_-c 4" \
200                 EXPECT_HEADER_COUNT=4 \
201                 git rebase -i $base &&
202         test_cmp_rev $base HEAD^ &&
203         get_author HEAD >actual-author &&
204         test_cmp expected-author actual-author &&
205         test 1 = $(git show | grep Modified-A3 | wc -l)
206 '
207
208 test_expect_success 'sequence squash, fixup & fixup -c gives combined message' '
209         test_when_finished "test_might_fail git rebase --abort" &&
210         git checkout --detach A3 &&
211         FAKE_LINES="1 squash 2 fixup 3 fixup_-c 4" \
212                 FAKE_MESSAGE_COPY=actual-combined-message \
213                 git -c commit.status=false rebase -i A &&
214         test_i18ncmp "$TEST_DIRECTORY/t3437/expected-combined-message" \
215                 actual-combined-message &&
216         test_cmp_rev HEAD^ A
217 '
218
219 test_expect_success 'fixup -C works upon --autosquash with amend!' '
220         git checkout --detach branch &&
221         FAKE_COMMIT_AMEND=squashed \
222                 FAKE_MESSAGE_COPY=actual-squash-message \
223                 git -c commit.status=false rebase -ik --autosquash \
224                                                 --signoff A &&
225         git diff-tree --exit-code --patch HEAD branch -- &&
226         test_cmp_rev HEAD^ A &&
227         test_i18ncmp "$TEST_DIRECTORY/t3437/expected-squash-message" \
228                 actual-squash-message
229 '
230
231 test_done