Merge branch 'jn/maint-plug-leak'
[git] / t / t7006-pager.sh
1 #!/bin/sh
2
3 test_description='Test automatic use of a pager.'
4
5 . ./test-lib.sh
6 . "$TEST_DIRECTORY"/lib-pager.sh
7
8 cleanup_fail() {
9         echo >&2 cleanup failed
10         (exit 1)
11 }
12
13 test_expect_success 'set up terminal for tests' '
14         rm -f stdout_is_tty ||
15         cleanup_fail &&
16
17         if test -t 1
18         then
19                 >stdout_is_tty
20         elif
21                 test_have_prereq PERL &&
22                 "$PERL_PATH" "$TEST_DIRECTORY"/t7006/test-terminal.perl \
23                         sh -c "test -t 1"
24         then
25                 >test_terminal_works
26         fi
27 '
28
29 if test -e stdout_is_tty
30 then
31         test_terminal() { "$@"; }
32         test_set_prereq TTY
33 elif test -e test_terminal_works
34 then
35         test_terminal() {
36                 "$PERL_PATH" "$TEST_DIRECTORY"/t7006/test-terminal.perl "$@"
37         }
38         test_set_prereq TTY
39 else
40         say "# no usable terminal, so skipping some tests"
41 fi
42
43 test_expect_success 'setup' '
44         unset GIT_PAGER GIT_PAGER_IN_USE;
45         test_might_fail git config --unset core.pager &&
46
47         PAGER="cat >paginated.out" &&
48         export PAGER &&
49
50         test_commit initial
51 '
52
53 test_expect_success TTY 'some commands use a pager' '
54         rm -f paginated.out ||
55         cleanup_fail &&
56
57         test_terminal git log &&
58         test -e paginated.out
59 '
60
61 test_expect_success TTY 'some commands do not use a pager' '
62         rm -f paginated.out ||
63         cleanup_fail &&
64
65         test_terminal git rev-list HEAD &&
66         ! test -e paginated.out
67 '
68
69 test_expect_success 'no pager when stdout is a pipe' '
70         rm -f paginated.out ||
71         cleanup_fail &&
72
73         git log | cat &&
74         ! test -e paginated.out
75 '
76
77 test_expect_success 'no pager when stdout is a regular file' '
78         rm -f paginated.out ||
79         cleanup_fail &&
80
81         git log >file &&
82         ! test -e paginated.out
83 '
84
85 test_expect_success TTY 'git --paginate rev-list uses a pager' '
86         rm -f paginated.out ||
87         cleanup_fail &&
88
89         test_terminal git --paginate rev-list HEAD &&
90         test -e paginated.out
91 '
92
93 test_expect_success 'no pager even with --paginate when stdout is a pipe' '
94         rm -f file paginated.out ||
95         cleanup_fail &&
96
97         git --paginate log | cat &&
98         ! test -e paginated.out
99 '
100
101 test_expect_success TTY 'no pager with --no-pager' '
102         rm -f paginated.out ||
103         cleanup_fail &&
104
105         test_terminal git --no-pager log &&
106         ! test -e paginated.out
107 '
108
109 # A colored commit log will begin with an appropriate ANSI escape
110 # for the first color; the text "commit" comes later.
111 colorful() {
112         read firstline <$1
113         ! expr "$firstline" : "[a-zA-Z]" >/dev/null
114 }
115
116 test_expect_success 'tests can detect color' '
117         rm -f colorful.log colorless.log ||
118         cleanup_fail &&
119
120         git log --no-color >colorless.log &&
121         git log --color >colorful.log &&
122         ! colorful colorless.log &&
123         colorful colorful.log
124 '
125
126 test_expect_success 'no color when stdout is a regular file' '
127         rm -f colorless.log &&
128         git config color.ui auto ||
129         cleanup_fail &&
130
131         git log >colorless.log &&
132         ! colorful colorless.log
133 '
134
135 test_expect_success TTY 'color when writing to a pager' '
136         rm -f paginated.out &&
137         git config color.ui auto ||
138         cleanup_fail &&
139
140         (
141                 TERM=vt100 &&
142                 export TERM &&
143                 test_terminal git log
144         ) &&
145         colorful paginated.out
146 '
147
148 test_expect_success 'color when writing to a file intended for a pager' '
149         rm -f colorful.log &&
150         git config color.ui auto ||
151         cleanup_fail &&
152
153         (
154                 TERM=vt100 &&
155                 GIT_PAGER_IN_USE=true &&
156                 export TERM GIT_PAGER_IN_USE &&
157                 git log >colorful.log
158         ) &&
159         colorful colorful.log
160 '
161
162 if test_have_prereq SIMPLEPAGER && test_have_prereq TTY
163 then
164         test_set_prereq SIMPLEPAGERTTY
165 fi
166
167 # Use this helper to make it easy for the caller of your
168 # terminal-using function to specify whether it should fail.
169 # If you write
170 #
171 #       your_test() {
172 #               parse_args "$@"
173 #
174 #               $test_expectation "$cmd - behaves well" "
175 #                       ...
176 #                       $full_command &&
177 #                       ...
178 #               "
179 #       }
180 #
181 # then your test can be used like this:
182 #
183 #       your_test expect_(success|failure) [test_must_fail] 'git foo'
184 #
185 parse_args() {
186         test_expectation="test_$1"
187         shift
188         if test "$1" = test_must_fail
189         then
190                 full_command="test_must_fail test_terminal "
191                 shift
192         else
193                 full_command="test_terminal "
194         fi
195         cmd=$1
196         full_command="$full_command $1"
197 }
198
199 test_default_pager() {
200         parse_args "$@"
201
202         $test_expectation SIMPLEPAGERTTY "$cmd - default pager is used by default" "
203                 unset PAGER GIT_PAGER;
204                 test_might_fail git config --unset core.pager &&
205                 rm -f default_pager_used ||
206                 cleanup_fail &&
207
208                 cat >\$less <<-\EOF &&
209                 #!/bin/sh
210                 wc >default_pager_used
211                 EOF
212                 chmod +x \$less &&
213                 (
214                         PATH=.:\$PATH &&
215                         export PATH &&
216                         $full_command
217                 ) &&
218                 test -e default_pager_used
219         "
220 }
221
222 test_PAGER_overrides() {
223         parse_args "$@"
224
225         $test_expectation TTY "$cmd - PAGER overrides default pager" "
226                 unset GIT_PAGER;
227                 test_might_fail git config --unset core.pager &&
228                 rm -f PAGER_used ||
229                 cleanup_fail &&
230
231                 PAGER='wc >PAGER_used' &&
232                 export PAGER &&
233                 $full_command &&
234                 test -e PAGER_used
235         "
236 }
237
238 test_core_pager_overrides() {
239         if_local_config=
240         used_if_wanted='overrides PAGER'
241         test_core_pager "$@"
242 }
243
244 test_local_config_ignored() {
245         if_local_config='! '
246         used_if_wanted='is not used'
247         test_core_pager "$@"
248 }
249
250 test_core_pager() {
251         parse_args "$@"
252
253         $test_expectation TTY "$cmd - repository-local core.pager setting $used_if_wanted" "
254                 unset GIT_PAGER;
255                 rm -f core.pager_used ||
256                 cleanup_fail &&
257
258                 PAGER=wc &&
259                 export PAGER &&
260                 git config core.pager 'wc >core.pager_used' &&
261                 $full_command &&
262                 ${if_local_config}test -e core.pager_used
263         "
264 }
265
266 test_core_pager_subdir() {
267         if_local_config=
268         used_if_wanted='overrides PAGER'
269         test_pager_subdir_helper "$@"
270 }
271
272 test_no_local_config_subdir() {
273         if_local_config='! '
274         used_if_wanted='is not used'
275         test_pager_subdir_helper "$@"
276 }
277
278 test_pager_subdir_helper() {
279         parse_args "$@"
280
281         $test_expectation TTY "$cmd - core.pager $used_if_wanted from subdirectory" "
282                 unset GIT_PAGER;
283                 rm -f core.pager_used &&
284                 rm -fr sub ||
285                 cleanup_fail &&
286
287                 PAGER=wc &&
288                 stampname=\$(pwd)/core.pager_used &&
289                 export PAGER stampname &&
290                 git config core.pager 'wc >\"\$stampname\"' &&
291                 mkdir sub &&
292                 (
293                         cd sub &&
294                         $full_command
295                 ) &&
296                 ${if_local_config}test -e core.pager_used
297         "
298 }
299
300 test_GIT_PAGER_overrides() {
301         parse_args "$@"
302
303         $test_expectation TTY "$cmd - GIT_PAGER overrides core.pager" "
304                 rm -f GIT_PAGER_used ||
305                 cleanup_fail &&
306
307                 git config core.pager wc &&
308                 GIT_PAGER='wc >GIT_PAGER_used' &&
309                 export GIT_PAGER &&
310                 $full_command &&
311                 test -e GIT_PAGER_used
312         "
313 }
314
315 test_doesnt_paginate() {
316         parse_args "$@"
317
318         $test_expectation TTY "no pager for '$cmd'" "
319                 rm -f GIT_PAGER_used ||
320                 cleanup_fail &&
321
322                 GIT_PAGER='wc >GIT_PAGER_used' &&
323                 export GIT_PAGER &&
324                 $full_command &&
325                 ! test -e GIT_PAGER_used
326         "
327 }
328
329 test_pager_choices() {
330         test_default_pager        expect_success "$@"
331         test_PAGER_overrides      expect_success "$@"
332         test_core_pager_overrides expect_success "$@"
333         test_core_pager_subdir    expect_success "$@"
334         test_GIT_PAGER_overrides  expect_success "$@"
335 }
336
337 test_expect_success 'setup: some aliases' '
338         git config alias.aliasedlog log &&
339         git config alias.true "!true"
340 '
341
342 test_pager_choices                       'git log'
343 test_pager_choices                       'git -p log'
344 test_pager_choices                       'git aliasedlog'
345
346 test_default_pager        expect_success 'git -p aliasedlog'
347 test_PAGER_overrides      expect_success 'git -p aliasedlog'
348 test_core_pager_overrides expect_success 'git -p aliasedlog'
349 test_core_pager_subdir    expect_failure 'git -p aliasedlog'
350 test_GIT_PAGER_overrides  expect_success 'git -p aliasedlog'
351
352 test_default_pager        expect_success 'git -p true'
353 test_PAGER_overrides      expect_success 'git -p true'
354 test_core_pager_overrides expect_success 'git -p true'
355 test_core_pager_subdir    expect_failure 'git -p true'
356 test_GIT_PAGER_overrides  expect_success 'git -p true'
357
358 test_default_pager        expect_success test_must_fail 'git -p request-pull'
359 test_PAGER_overrides      expect_success test_must_fail 'git -p request-pull'
360 test_core_pager_overrides expect_success test_must_fail 'git -p request-pull'
361 test_core_pager_subdir    expect_failure test_must_fail 'git -p request-pull'
362 test_GIT_PAGER_overrides  expect_success test_must_fail 'git -p request-pull'
363
364 test_default_pager        expect_success test_must_fail 'git -p'
365 test_PAGER_overrides      expect_success test_must_fail 'git -p'
366 test_local_config_ignored expect_failure test_must_fail 'git -p'
367 test_no_local_config_subdir expect_success test_must_fail 'git -p'
368 test_GIT_PAGER_overrides  expect_success test_must_fail 'git -p'
369
370 test_doesnt_paginate      expect_failure test_must_fail 'git -p nonsense'
371
372 test_done