1#!/bin/sh
2#
3# Copyright (c) 2012 SZEDER Gábor
4#
5
6test_description='test git-specific bash prompt functions'
7
8. ./lib-bash.sh
9
10. "$GIT_BUILD_DIR/contrib/completion/git-prompt.sh"
11
12actual="$TRASH_DIRECTORY/actual"
13c_red='\\[\\e[31m\\]'
14c_green='\\[\\e[32m\\]'
15c_lblue='\\[\\e[1;34m\\]'
16c_clear='\\[\\e[0m\\]'
17
18test_expect_success 'setup for prompt tests' '
19 git init otherrepo &&
20 echo 1 >file &&
21 git add file &&
22 test_tick &&
23 git commit -m initial &&
24 git tag -a -m msg1 t1 &&
25 git checkout -b b1 &&
26 echo 2 >file &&
27 git commit -m "second b1" file &&
28 echo 3 >file &&
29 git commit -m "third b1" file &&
30 git tag -a -m msg2 t2 &&
31 git checkout -b b2 master &&
32 echo 0 >file &&
33 git commit -m "second b2" file &&
34 echo 00 >file &&
35 git commit -m "another b2" file &&
36 echo 000 >file &&
37 git commit -m "yet another b2" file &&
38 git checkout master
39'
40
41test_expect_success 'prompt - branch name' '
42 printf " (master)" >expected &&
43 __git_ps1 >"$actual" &&
44 test_cmp expected "$actual"
45'
46
47test_expect_success SYMLINKS 'prompt - branch name - symlink symref' '
48 printf " (master)" >expected &&
49 test_when_finished "git checkout master" &&
50 test_config core.preferSymlinkRefs true &&
51 git checkout master &&
52 __git_ps1 >"$actual" &&
53 test_cmp expected "$actual"
54'
55
56test_expect_success 'prompt - unborn branch' '
57 printf " (unborn)" >expected &&
58 git checkout --orphan unborn &&
59 test_when_finished "git checkout master" &&
60 __git_ps1 >"$actual" &&
61 test_cmp expected "$actual"
62'
63
64test_expect_success 'prompt - detached head' '
65 printf " ((%s...))" $(git log -1 --format="%h" --abbrev=13 b1^) >expected &&
66 test_config core.abbrev 13 &&
67 git checkout b1^ &&
68 test_when_finished "git checkout master" &&
69 __git_ps1 >"$actual" &&
70 test_cmp expected "$actual"
71'
72
73test_expect_success 'prompt - describe detached head - contains' '
74 printf " ((t2~1))" >expected &&
75 git checkout b1^ &&
76 test_when_finished "git checkout master" &&
77 (
78 GIT_PS1_DESCRIBE_STYLE=contains &&
79 __git_ps1 >"$actual"
80 ) &&
81 test_cmp expected "$actual"
82'
83
84test_expect_success 'prompt - describe detached head - branch' '
85 printf " ((b1~1))" >expected &&
86 git checkout b1^ &&
87 test_when_finished "git checkout master" &&
88 (
89 GIT_PS1_DESCRIBE_STYLE=branch &&
90 __git_ps1 >"$actual"
91 ) &&
92 test_cmp expected "$actual"
93'
94
95test_expect_success 'prompt - describe detached head - describe' '
96 printf " ((t1-1-g%s))" $(git log -1 --format="%h" b1^) >expected &&
97 git checkout b1^ &&
98 test_when_finished "git checkout master" &&
99 (
100 GIT_PS1_DESCRIBE_STYLE=describe &&
101 __git_ps1 >"$actual"
102 ) &&
103 test_cmp expected "$actual"
104'
105
106test_expect_success 'prompt - describe detached head - default' '
107 printf " ((t2))" >expected &&
108 git checkout --detach b1 &&
109 test_when_finished "git checkout master" &&
110 __git_ps1 >"$actual" &&
111 test_cmp expected "$actual"
112'
113
114test_expect_success 'prompt - inside .git directory' '
115 printf " (GIT_DIR!)" >expected &&
116 (
117 cd .git &&
118 __git_ps1 >"$actual"
119 ) &&
120 test_cmp expected "$actual"
121'
122
123test_expect_success 'prompt - deep inside .git directory' '
124 printf " (GIT_DIR!)" >expected &&
125 (
126 cd .git/refs/heads &&
127 __git_ps1 >"$actual"
128 ) &&
129 test_cmp expected "$actual"
130'
131
132test_expect_success 'prompt - inside bare repository' '
133 printf " (BARE:master)" >expected &&
134 git init --bare bare.git &&
135 test_when_finished "rm -rf bare.git" &&
136 (
137 cd bare.git &&
138 __git_ps1 >"$actual"
139 ) &&
140 test_cmp expected "$actual"
141'
142
143test_expect_success 'prompt - interactive rebase' '
144 printf " (b1|REBASE-i 2/3)" >expected
145 write_script fake_editor.sh <<-\EOF &&
146 echo "exec echo" >"$1"
147 echo "edit $(git log -1 --format="%h")" >>"$1"
148 echo "exec echo" >>"$1"
149 EOF
150 test_when_finished "rm -f fake_editor.sh" &&
151 test_set_editor "$TRASH_DIRECTORY/fake_editor.sh" &&
152 git checkout b1 &&
153 test_when_finished "git checkout master" &&
154 git rebase -i HEAD^ &&
155 test_when_finished "git rebase --abort"
156 __git_ps1 >"$actual" &&
157 test_cmp expected "$actual"
158'
159
160test_expect_success 'prompt - rebase merge' '
161 printf " (b2|REBASE-m 1/3)" >expected &&
162 git checkout b2 &&
163 test_when_finished "git checkout master" &&
164 test_must_fail git rebase --merge b1 b2 &&
165 test_when_finished "git rebase --abort" &&
166 __git_ps1 >"$actual" &&
167 test_cmp expected "$actual"
168'
169
170test_expect_success 'prompt - rebase' '
171 printf " (b2|REBASE 1/3)" >expected &&
172 git checkout b2 &&
173 test_when_finished "git checkout master" &&
174 test_must_fail git rebase b1 b2 &&
175 test_when_finished "git rebase --abort" &&
176 __git_ps1 >"$actual" &&
177 test_cmp expected "$actual"
178'
179
180test_expect_success 'prompt - merge' '
181 printf " (b1|MERGING)" >expected &&
182 git checkout b1 &&
183 test_when_finished "git checkout master" &&
184 test_must_fail git merge b2 &&
185 test_when_finished "git reset --hard" &&
186 __git_ps1 >"$actual" &&
187 test_cmp expected "$actual"
188'
189
190test_expect_success 'prompt - cherry-pick' '
191 printf " (master|CHERRY-PICKING)" >expected &&
192 test_must_fail git cherry-pick b1 &&
193 test_when_finished "git reset --hard" &&
194 __git_ps1 >"$actual" &&
195 test_cmp expected "$actual"
196'
197
198test_expect_success 'prompt - bisect' '
199 printf " (master|BISECTING)" >expected &&
200 git bisect start &&
201 test_when_finished "git bisect reset" &&
202 __git_ps1 >"$actual" &&
203 test_cmp expected "$actual"
204'
205
206test_expect_success 'prompt - dirty status indicator - clean' '
207 printf " (master)" >expected &&
208 (
209 GIT_PS1_SHOWDIRTYSTATE=y &&
210 __git_ps1 >"$actual"
211 ) &&
212 test_cmp expected "$actual"
213'
214
215test_expect_success 'prompt - dirty status indicator - dirty worktree' '
216 printf " (master *)" >expected &&
217 echo "dirty" >file &&
218 test_when_finished "git reset --hard" &&
219 (
220 GIT_PS1_SHOWDIRTYSTATE=y &&
221 __git_ps1 >"$actual"
222 ) &&
223 test_cmp expected "$actual"
224'
225
226test_expect_success 'prompt - dirty status indicator - dirty index' '
227 printf " (master +)" >expected &&
228 echo "dirty" >file &&
229 test_when_finished "git reset --hard" &&
230 git add -u &&
231 (
232 GIT_PS1_SHOWDIRTYSTATE=y &&
233 __git_ps1 >"$actual"
234 ) &&
235 test_cmp expected "$actual"
236'
237
238test_expect_success 'prompt - dirty status indicator - dirty index and worktree' '
239 printf " (master *+)" >expected &&
240 echo "dirty index" >file &&
241 test_when_finished "git reset --hard" &&
242 git add -u &&
243 echo "dirty worktree" >file &&
244 (
245 GIT_PS1_SHOWDIRTYSTATE=y &&
246 __git_ps1 >"$actual"
247 ) &&
248 test_cmp expected "$actual"
249'
250
251test_expect_success 'prompt - dirty status indicator - before root commit' '
252 printf " (master #)" >expected &&
253 (
254 GIT_PS1_SHOWDIRTYSTATE=y &&
255 cd otherrepo &&
256 __git_ps1 >"$actual"
257 ) &&
258 test_cmp expected "$actual"
259'
260
261test_expect_success 'prompt - dirty status indicator - shell variable unset with config disabled' '
262 printf " (master)" >expected &&
263 echo "dirty" >file &&
264 test_when_finished "git reset --hard" &&
265 test_config bash.showDirtyState false &&
266 (
267 sane_unset GIT_PS1_SHOWDIRTYSTATE &&
268 __git_ps1 >"$actual"
269 ) &&
270 test_cmp expected "$actual"
271'
272
273test_expect_success 'prompt - dirty status indicator - shell variable unset with config enabled' '
274 printf " (master)" >expected &&
275 echo "dirty" >file &&
276 test_when_finished "git reset --hard" &&
277 test_config bash.showDirtyState true &&
278 (
279 sane_unset GIT_PS1_SHOWDIRTYSTATE &&
280 __git_ps1 >"$actual"
281 ) &&
282 test_cmp expected "$actual"
283'
284
285test_expect_success 'prompt - dirty status indicator - shell variable set with config disabled' '
286 printf " (master)" >expected &&
287 echo "dirty" >file &&
288 test_when_finished "git reset --hard" &&
289 test_config bash.showDirtyState false &&
290 (
291 GIT_PS1_SHOWDIRTYSTATE=y &&
292 __git_ps1 >"$actual"
293 ) &&
294 test_cmp expected "$actual"
295'
296
297test_expect_success 'prompt - dirty status indicator - shell variable set with config enabled' '
298 printf " (master *)" >expected &&
299 echo "dirty" >file &&
300 test_when_finished "git reset --hard" &&
301 test_config bash.showDirtyState true &&
302 (
303 GIT_PS1_SHOWDIRTYSTATE=y &&
304 __git_ps1 >"$actual"
305 ) &&
306 test_cmp expected "$actual"
307'
308
309test_expect_success 'prompt - dirty status indicator - not shown inside .git directory' '
310 printf " (GIT_DIR!)" >expected &&
311 echo "dirty" >file &&
312 test_when_finished "git reset --hard" &&
313 (
314 GIT_PS1_SHOWDIRTYSTATE=y &&
315 cd .git &&
316 __git_ps1 >"$actual"
317 ) &&
318 test_cmp expected "$actual"
319'
320
321test_expect_success 'prompt - stash status indicator - no stash' '
322 printf " (master)" >expected &&
323 (
324 GIT_PS1_SHOWSTASHSTATE=y &&
325 __git_ps1 >"$actual"
326 ) &&
327 test_cmp expected "$actual"
328'
329
330test_expect_success 'prompt - stash status indicator - stash' '
331 printf " (master $)" >expected &&
332 echo 2 >file &&
333 git stash &&
334 test_when_finished "git stash drop" &&
335 git pack-refs --all &&
336 (
337 GIT_PS1_SHOWSTASHSTATE=y &&
338 __git_ps1 >"$actual"
339 ) &&
340 test_cmp expected "$actual"
341'
342
343test_expect_success 'prompt - stash status indicator - not shown inside .git directory' '
344 printf " (GIT_DIR!)" >expected &&
345 echo 2 >file &&
346 git stash &&
347 test_when_finished "git stash drop" &&
348 (
349 GIT_PS1_SHOWSTASHSTATE=y &&
350 cd .git &&
351 __git_ps1 >"$actual"
352 ) &&
353 test_cmp expected "$actual"
354'
355
356test_expect_success 'prompt - untracked files status indicator - no untracked files' '
357 printf " (master)" >expected &&
358 (
359 GIT_PS1_SHOWUNTRACKEDFILES=y &&
360 cd otherrepo &&
361 __git_ps1 >"$actual"
362 ) &&
363 test_cmp expected "$actual"
364'
365
366test_expect_success 'prompt - untracked files status indicator - untracked files' '
367 printf " (master %%)" >expected &&
368 (
369 GIT_PS1_SHOWUNTRACKEDFILES=y &&
370 __git_ps1 >"$actual"
371 ) &&
372 test_cmp expected "$actual"
373'
374
375test_expect_success 'prompt - untracked files status indicator - shell variable unset with config disabled' '
376 printf " (master)" >expected &&
377 test_config bash.showUntrackedFiles false &&
378 (
379 sane_unset GIT_PS1_SHOWUNTRACKEDFILES &&
380 __git_ps1 >"$actual"
381 ) &&
382 test_cmp expected "$actual"
383'
384
385test_expect_success 'prompt - untracked files status indicator - shell variable unset with config enabled' '
386 printf " (master)" >expected &&
387 test_config bash.showUntrackedFiles true &&
388 (
389 sane_unset GIT_PS1_SHOWUNTRACKEDFILES &&
390 __git_ps1 >"$actual"
391 ) &&
392 test_cmp expected "$actual"
393'
394
395test_expect_success 'prompt - untracked files status indicator - shell variable set with config disabled' '
396 printf " (master)" >expected &&
397 test_config bash.showUntrackedFiles false &&
398 (
399 GIT_PS1_SHOWUNTRACKEDFILES=y &&
400 __git_ps1 >"$actual"
401 ) &&
402 test_cmp expected "$actual"
403'
404
405test_expect_success 'prompt - untracked files status indicator - shell variable set with config enabled' '
406 printf " (master %%)" >expected &&
407 test_config bash.showUntrackedFiles true &&
408 (
409 GIT_PS1_SHOWUNTRACKEDFILES=y &&
410 __git_ps1 >"$actual"
411 ) &&
412 test_cmp expected "$actual"
413'
414
415test_expect_success 'prompt - untracked files status indicator - not shown inside .git directory' '
416 printf " (GIT_DIR!)" >expected &&
417 (
418 GIT_PS1_SHOWUNTRACKEDFILES=y &&
419 cd .git &&
420 __git_ps1 >"$actual"
421 ) &&
422 test_cmp expected "$actual"
423'
424
425test_expect_success 'prompt - format string starting with dash' '
426 printf -- "-master" >expected &&
427 __git_ps1 "-%s" >"$actual" &&
428 test_cmp expected "$actual"
429'
430
431test_expect_success 'prompt - pc mode' '
432 printf "BEFORE: (master):AFTER" >expected &&
433 printf "" >expected_output &&
434 (
435 __git_ps1 "BEFORE:" ":AFTER" >"$actual" &&
436 test_cmp expected_output "$actual" &&
437 printf "%s" "$PS1" >"$actual"
438 ) &&
439 test_cmp expected "$actual"
440'
441
442test_expect_success 'prompt - bash color pc mode - branch name' '
443 printf "BEFORE: (${c_green}master${c_clear}):AFTER" >expected &&
444 (
445 GIT_PS1_SHOWCOLORHINTS=y &&
446 __git_ps1 "BEFORE:" ":AFTER" >"$actual"
447 printf "%s" "$PS1" >"$actual"
448 ) &&
449 test_cmp expected "$actual"
450'
451
452test_expect_success 'prompt - bash color pc mode - detached head' '
453 printf "BEFORE: (${c_red}(%s...)${c_clear}):AFTER" $(git log -1 --format="%h" b1^) >expected &&
454 git checkout b1^ &&
455 test_when_finished "git checkout master" &&
456 (
457 GIT_PS1_SHOWCOLORHINTS=y &&
458 __git_ps1 "BEFORE:" ":AFTER" &&
459 printf "%s" "$PS1" >"$actual"
460 ) &&
461 test_cmp expected "$actual"
462'
463
464test_expect_success 'prompt - bash color pc mode - dirty status indicator - dirty worktree' '
465 printf "BEFORE: (${c_green}master${c_clear} ${c_red}*${c_clear}):AFTER" >expected &&
466 echo "dirty" >file &&
467 test_when_finished "git reset --hard" &&
468 (
469 GIT_PS1_SHOWDIRTYSTATE=y &&
470 GIT_PS1_SHOWCOLORHINTS=y &&
471 __git_ps1 "BEFORE:" ":AFTER" &&
472 printf "%s" "$PS1" >"$actual"
473 ) &&
474 test_cmp expected "$actual"
475'
476
477test_expect_success 'prompt - bash color pc mode - dirty status indicator - dirty index' '
478 printf "BEFORE: (${c_green}master${c_clear} ${c_green}+${c_clear}):AFTER" >expected &&
479 echo "dirty" >file &&
480 test_when_finished "git reset --hard" &&
481 git add -u &&
482 (
483 GIT_PS1_SHOWDIRTYSTATE=y &&
484 GIT_PS1_SHOWCOLORHINTS=y &&
485 __git_ps1 "BEFORE:" ":AFTER" &&
486 printf "%s" "$PS1" >"$actual"
487 ) &&
488 test_cmp expected "$actual"
489'
490
491test_expect_success 'prompt - bash color pc mode - dirty status indicator - dirty index and worktree' '
492 printf "BEFORE: (${c_green}master${c_clear} ${c_red}*${c_green}+${c_clear}):AFTER" >expected &&
493 echo "dirty index" >file &&
494 test_when_finished "git reset --hard" &&
495 git add -u &&
496 echo "dirty worktree" >file &&
497 (
498 GIT_PS1_SHOWCOLORHINTS=y &&
499 GIT_PS1_SHOWDIRTYSTATE=y &&
500 __git_ps1 "BEFORE:" ":AFTER" &&
501 printf "%s" "$PS1" >"$actual"
502 ) &&
503 test_cmp expected "$actual"
504'
505
506test_expect_success 'prompt - bash color pc mode - dirty status indicator - before root commit' '
507 printf "BEFORE: (${c_green}master${c_clear} ${c_green}#${c_clear}):AFTER" >expected &&
508 (
509 GIT_PS1_SHOWDIRTYSTATE=y &&
510 GIT_PS1_SHOWCOLORHINTS=y &&
511 cd otherrepo &&
512 __git_ps1 "BEFORE:" ":AFTER" &&
513 printf "%s" "$PS1" >"$actual"
514 ) &&
515 test_cmp expected "$actual"
516'
517
518test_expect_success 'prompt - bash color pc mode - inside .git directory' '
519 printf "BEFORE: (${c_green}GIT_DIR!${c_clear}):AFTER" >expected &&
520 echo "dirty" >file &&
521 test_when_finished "git reset --hard" &&
522 (
523 GIT_PS1_SHOWDIRTYSTATE=y &&
524 GIT_PS1_SHOWCOLORHINTS=y &&
525 cd .git &&
526 __git_ps1 "BEFORE:" ":AFTER" &&
527 printf "%s" "$PS1" >"$actual"
528 ) &&
529 test_cmp expected "$actual"
530'
531
532test_expect_success 'prompt - bash color pc mode - stash status indicator' '
533 printf "BEFORE: (${c_green}master${c_clear} ${c_lblue}\$${c_clear}):AFTER" >expected &&
534 echo 2 >file &&
535 git stash &&
536 test_when_finished "git stash drop" &&
537 (
538 GIT_PS1_SHOWSTASHSTATE=y &&
539 GIT_PS1_SHOWCOLORHINTS=y &&
540 __git_ps1 "BEFORE:" ":AFTER" &&
541 printf "%s" "$PS1" >"$actual"
542 ) &&
543 test_cmp expected "$actual"
544'
545
546test_expect_success 'prompt - bash color pc mode - untracked files status indicator' '
547 printf "BEFORE: (${c_green}master${c_clear} ${c_red}%%${c_clear}):AFTER" >expected &&
548 (
549 GIT_PS1_SHOWUNTRACKEDFILES=y &&
550 GIT_PS1_SHOWCOLORHINTS=y &&
551 __git_ps1 "BEFORE:" ":AFTER" &&
552 printf "%s" "$PS1" >"$actual"
553 ) &&
554 test_cmp expected "$actual"
555'
556
557test_expect_success 'prompt - zsh color pc mode' '
558 printf "BEFORE: (%%F{green}master%%f):AFTER" >expected &&
559 (
560 ZSH_VERSION=5.0.0 &&
561 GIT_PS1_SHOWCOLORHINTS=y &&
562 __git_ps1 "BEFORE:" ":AFTER" >"$actual"
563 printf "%s" "$PS1" >"$actual"
564 ) &&
565 test_cmp expected "$actual"
566'
567
568test_done