Merge branch 'ot/ref-filter-cleanup'
[git] / t / t7063-status-untracked-cache.sh
1 #!/bin/sh
2
3 test_description='test untracked cache'
4
5 . ./test-lib.sh
6
7 # On some filesystems (e.g. FreeBSD's ext2 and ufs) directory mtime
8 # is updated lazily after contents in the directory changes, which
9 # forces the untracked cache code to take the slow path.  A test
10 # that wants to make sure that the fast path works correctly should
11 # call this helper to make mtime of the containing directory in sync
12 # with the reality before checking the fast path behaviour.
13 #
14 # See <20160803174522.5571-1-pclouds@gmail.com> if you want to know
15 # more.
16
17 sync_mtime () {
18         find . -type d -ls >/dev/null
19 }
20
21 avoid_racy() {
22         sleep 1
23 }
24
25 status_is_clean() {
26         >../status.expect &&
27         git status --porcelain >../status.actual &&
28         test_cmp ../status.expect ../status.actual
29 }
30
31 test_lazy_prereq UNTRACKED_CACHE '
32         { git update-index --test-untracked-cache; ret=$?; } &&
33         test $ret -ne 1
34 '
35
36 if ! test_have_prereq UNTRACKED_CACHE; then
37         skip_all='This system does not support untracked cache'
38         test_done
39 fi
40
41 test_expect_success 'core.untrackedCache is unset' '
42         test_must_fail git config --get core.untrackedCache
43 '
44
45 test_expect_success 'setup' '
46         git init worktree &&
47         cd worktree &&
48         mkdir done dtwo dthree &&
49         touch one two three done/one dtwo/two dthree/three &&
50         git add one two done/one &&
51         : >.git/info/exclude &&
52         git update-index --untracked-cache
53 '
54
55 test_expect_success 'untracked cache is empty' '
56         test-dump-untracked-cache >../actual &&
57         cat >../expect-empty <<EOF &&
58 info/exclude 0000000000000000000000000000000000000000
59 core.excludesfile 0000000000000000000000000000000000000000
60 exclude_per_dir .gitignore
61 flags 00000006
62 EOF
63         test_cmp ../expect-empty ../actual
64 '
65
66 cat >../status.expect <<EOF &&
67 A  done/one
68 A  one
69 A  two
70 ?? dthree/
71 ?? dtwo/
72 ?? three
73 EOF
74
75 cat >../dump.expect <<EOF &&
76 info/exclude $EMPTY_BLOB
77 core.excludesfile 0000000000000000000000000000000000000000
78 exclude_per_dir .gitignore
79 flags 00000006
80 / 0000000000000000000000000000000000000000 recurse valid
81 dthree/
82 dtwo/
83 three
84 /done/ 0000000000000000000000000000000000000000 recurse valid
85 /dthree/ 0000000000000000000000000000000000000000 recurse check_only valid
86 three
87 /dtwo/ 0000000000000000000000000000000000000000 recurse check_only valid
88 two
89 EOF
90
91 test_expect_success 'status first time (empty cache)' '
92         avoid_racy &&
93         : >../trace &&
94         GIT_TRACE_UNTRACKED_STATS="$TRASH_DIRECTORY/trace" \
95         git status --porcelain >../actual &&
96         test_cmp ../status.expect ../actual &&
97         cat >../trace.expect <<EOF &&
98 node creation: 3
99 gitignore invalidation: 1
100 directory invalidation: 0
101 opendir: 4
102 EOF
103         test_cmp ../trace.expect ../trace
104 '
105
106 test_expect_success 'untracked cache after first status' '
107         test-dump-untracked-cache >../actual &&
108         test_cmp ../dump.expect ../actual
109 '
110
111 test_expect_success 'status second time (fully populated cache)' '
112         avoid_racy &&
113         : >../trace &&
114         GIT_TRACE_UNTRACKED_STATS="$TRASH_DIRECTORY/trace" \
115         git status --porcelain >../actual &&
116         test_cmp ../status.expect ../actual &&
117         cat >../trace.expect <<EOF &&
118 node creation: 0
119 gitignore invalidation: 0
120 directory invalidation: 0
121 opendir: 0
122 EOF
123         test_cmp ../trace.expect ../trace
124 '
125
126 test_expect_success 'untracked cache after second status' '
127         test-dump-untracked-cache >../actual &&
128         test_cmp ../dump.expect ../actual
129 '
130
131 test_expect_success 'modify in root directory, one dir invalidation' '
132         avoid_racy &&
133         : >four &&
134         : >../trace &&
135         GIT_TRACE_UNTRACKED_STATS="$TRASH_DIRECTORY/trace" \
136         git status --porcelain >../actual &&
137         cat >../status.expect <<EOF &&
138 A  done/one
139 A  one
140 A  two
141 ?? dthree/
142 ?? dtwo/
143 ?? four
144 ?? three
145 EOF
146         test_cmp ../status.expect ../actual &&
147         cat >../trace.expect <<EOF &&
148 node creation: 0
149 gitignore invalidation: 0
150 directory invalidation: 1
151 opendir: 1
152 EOF
153         test_cmp ../trace.expect ../trace
154
155 '
156
157 test_expect_success 'verify untracked cache dump' '
158         test-dump-untracked-cache >../actual &&
159         cat >../expect <<EOF &&
160 info/exclude $EMPTY_BLOB
161 core.excludesfile 0000000000000000000000000000000000000000
162 exclude_per_dir .gitignore
163 flags 00000006
164 / 0000000000000000000000000000000000000000 recurse valid
165 dthree/
166 dtwo/
167 four
168 three
169 /done/ 0000000000000000000000000000000000000000 recurse valid
170 /dthree/ 0000000000000000000000000000000000000000 recurse check_only valid
171 three
172 /dtwo/ 0000000000000000000000000000000000000000 recurse check_only valid
173 two
174 EOF
175         test_cmp ../expect ../actual
176 '
177
178 test_expect_success 'new .gitignore invalidates recursively' '
179         avoid_racy &&
180         echo four >.gitignore &&
181         : >../trace &&
182         GIT_TRACE_UNTRACKED_STATS="$TRASH_DIRECTORY/trace" \
183         git status --porcelain >../actual &&
184         cat >../status.expect <<EOF &&
185 A  done/one
186 A  one
187 A  two
188 ?? .gitignore
189 ?? dthree/
190 ?? dtwo/
191 ?? three
192 EOF
193         test_cmp ../status.expect ../actual &&
194         cat >../trace.expect <<EOF &&
195 node creation: 0
196 gitignore invalidation: 1
197 directory invalidation: 1
198 opendir: 4
199 EOF
200         test_cmp ../trace.expect ../trace
201
202 '
203
204 test_expect_success 'verify untracked cache dump' '
205         test-dump-untracked-cache >../actual &&
206         cat >../expect <<EOF &&
207 info/exclude $EMPTY_BLOB
208 core.excludesfile 0000000000000000000000000000000000000000
209 exclude_per_dir .gitignore
210 flags 00000006
211 / e6fcc8f2ee31bae321d66afd183fcb7237afae6e recurse valid
212 .gitignore
213 dthree/
214 dtwo/
215 three
216 /done/ 0000000000000000000000000000000000000000 recurse valid
217 /dthree/ 0000000000000000000000000000000000000000 recurse check_only valid
218 three
219 /dtwo/ 0000000000000000000000000000000000000000 recurse check_only valid
220 two
221 EOF
222         test_cmp ../expect ../actual
223 '
224
225 test_expect_success 'new info/exclude invalidates everything' '
226         avoid_racy &&
227         echo three >>.git/info/exclude &&
228         : >../trace &&
229         GIT_TRACE_UNTRACKED_STATS="$TRASH_DIRECTORY/trace" \
230         git status --porcelain >../actual &&
231         cat >../status.expect <<EOF &&
232 A  done/one
233 A  one
234 A  two
235 ?? .gitignore
236 ?? dtwo/
237 EOF
238         test_cmp ../status.expect ../actual &&
239         cat >../trace.expect <<EOF &&
240 node creation: 0
241 gitignore invalidation: 1
242 directory invalidation: 0
243 opendir: 4
244 EOF
245         test_cmp ../trace.expect ../trace
246 '
247
248 test_expect_success 'verify untracked cache dump' '
249         test-dump-untracked-cache >../actual &&
250         cat >../expect <<EOF &&
251 info/exclude 13263c0978fb9fad16b2d580fb800b6d811c3ff0
252 core.excludesfile 0000000000000000000000000000000000000000
253 exclude_per_dir .gitignore
254 flags 00000006
255 / e6fcc8f2ee31bae321d66afd183fcb7237afae6e recurse valid
256 .gitignore
257 dtwo/
258 /done/ 0000000000000000000000000000000000000000 recurse valid
259 /dthree/ 0000000000000000000000000000000000000000 recurse check_only valid
260 /dtwo/ 0000000000000000000000000000000000000000 recurse check_only valid
261 two
262 EOF
263         test_cmp ../expect ../actual
264 '
265
266 test_expect_success 'move two from tracked to untracked' '
267         git rm --cached two &&
268         test-dump-untracked-cache >../actual &&
269         cat >../expect <<EOF &&
270 info/exclude 13263c0978fb9fad16b2d580fb800b6d811c3ff0
271 core.excludesfile 0000000000000000000000000000000000000000
272 exclude_per_dir .gitignore
273 flags 00000006
274 / e6fcc8f2ee31bae321d66afd183fcb7237afae6e recurse
275 /done/ 0000000000000000000000000000000000000000 recurse valid
276 /dthree/ 0000000000000000000000000000000000000000 recurse check_only valid
277 /dtwo/ 0000000000000000000000000000000000000000 recurse check_only valid
278 two
279 EOF
280         test_cmp ../expect ../actual
281 '
282
283 test_expect_success 'status after the move' '
284         : >../trace &&
285         GIT_TRACE_UNTRACKED_STATS="$TRASH_DIRECTORY/trace" \
286         git status --porcelain >../actual &&
287         cat >../status.expect <<EOF &&
288 A  done/one
289 A  one
290 ?? .gitignore
291 ?? dtwo/
292 ?? two
293 EOF
294         test_cmp ../status.expect ../actual &&
295         cat >../trace.expect <<EOF &&
296 node creation: 0
297 gitignore invalidation: 0
298 directory invalidation: 0
299 opendir: 1
300 EOF
301         test_cmp ../trace.expect ../trace
302 '
303
304 test_expect_success 'verify untracked cache dump' '
305         test-dump-untracked-cache >../actual &&
306         cat >../expect <<EOF &&
307 info/exclude 13263c0978fb9fad16b2d580fb800b6d811c3ff0
308 core.excludesfile 0000000000000000000000000000000000000000
309 exclude_per_dir .gitignore
310 flags 00000006
311 / e6fcc8f2ee31bae321d66afd183fcb7237afae6e recurse valid
312 .gitignore
313 dtwo/
314 two
315 /done/ 0000000000000000000000000000000000000000 recurse valid
316 /dthree/ 0000000000000000000000000000000000000000 recurse check_only valid
317 /dtwo/ 0000000000000000000000000000000000000000 recurse check_only valid
318 two
319 EOF
320         test_cmp ../expect ../actual
321 '
322
323 test_expect_success 'move two from untracked to tracked' '
324         git add two &&
325         test-dump-untracked-cache >../actual &&
326         cat >../expect <<EOF &&
327 info/exclude 13263c0978fb9fad16b2d580fb800b6d811c3ff0
328 core.excludesfile 0000000000000000000000000000000000000000
329 exclude_per_dir .gitignore
330 flags 00000006
331 / e6fcc8f2ee31bae321d66afd183fcb7237afae6e recurse
332 /done/ 0000000000000000000000000000000000000000 recurse valid
333 /dthree/ 0000000000000000000000000000000000000000 recurse check_only valid
334 /dtwo/ 0000000000000000000000000000000000000000 recurse check_only valid
335 two
336 EOF
337         test_cmp ../expect ../actual
338 '
339
340 test_expect_success 'status after the move' '
341         : >../trace &&
342         GIT_TRACE_UNTRACKED_STATS="$TRASH_DIRECTORY/trace" \
343         git status --porcelain >../actual &&
344         cat >../status.expect <<EOF &&
345 A  done/one
346 A  one
347 A  two
348 ?? .gitignore
349 ?? dtwo/
350 EOF
351         test_cmp ../status.expect ../actual &&
352         cat >../trace.expect <<EOF &&
353 node creation: 0
354 gitignore invalidation: 0
355 directory invalidation: 0
356 opendir: 1
357 EOF
358         test_cmp ../trace.expect ../trace
359 '
360
361 test_expect_success 'verify untracked cache dump' '
362         test-dump-untracked-cache >../actual &&
363         cat >../expect <<EOF &&
364 info/exclude 13263c0978fb9fad16b2d580fb800b6d811c3ff0
365 core.excludesfile 0000000000000000000000000000000000000000
366 exclude_per_dir .gitignore
367 flags 00000006
368 / e6fcc8f2ee31bae321d66afd183fcb7237afae6e recurse valid
369 .gitignore
370 dtwo/
371 /done/ 0000000000000000000000000000000000000000 recurse valid
372 /dthree/ 0000000000000000000000000000000000000000 recurse check_only valid
373 /dtwo/ 0000000000000000000000000000000000000000 recurse check_only valid
374 two
375 EOF
376         test_cmp ../expect ../actual
377 '
378
379 test_expect_success 'set up for sparse checkout testing' '
380         echo two >done/.gitignore &&
381         echo three >>done/.gitignore &&
382         echo two >done/two &&
383         git add -f done/two done/.gitignore &&
384         git commit -m "first commit"
385 '
386
387 test_expect_success 'status after commit' '
388         : >../trace &&
389         GIT_TRACE_UNTRACKED_STATS="$TRASH_DIRECTORY/trace" \
390         git status --porcelain >../actual &&
391         cat >../status.expect <<EOF &&
392 ?? .gitignore
393 ?? dtwo/
394 EOF
395         test_cmp ../status.expect ../actual &&
396         cat >../trace.expect <<EOF &&
397 node creation: 0
398 gitignore invalidation: 0
399 directory invalidation: 0
400 opendir: 2
401 EOF
402         test_cmp ../trace.expect ../trace
403 '
404
405 test_expect_success 'untracked cache correct after commit' '
406         test-dump-untracked-cache >../actual &&
407         cat >../expect <<EOF &&
408 info/exclude 13263c0978fb9fad16b2d580fb800b6d811c3ff0
409 core.excludesfile 0000000000000000000000000000000000000000
410 exclude_per_dir .gitignore
411 flags 00000006
412 / e6fcc8f2ee31bae321d66afd183fcb7237afae6e recurse valid
413 .gitignore
414 dtwo/
415 /done/ 0000000000000000000000000000000000000000 recurse valid
416 /dthree/ 0000000000000000000000000000000000000000 recurse check_only valid
417 /dtwo/ 0000000000000000000000000000000000000000 recurse check_only valid
418 two
419 EOF
420         test_cmp ../expect ../actual
421 '
422
423 test_expect_success 'set up sparse checkout' '
424         echo "done/[a-z]*" >.git/info/sparse-checkout &&
425         test_config core.sparsecheckout true &&
426         git checkout master &&
427         git update-index --force-untracked-cache &&
428         git status --porcelain >/dev/null && # prime the cache
429         test_path_is_missing done/.gitignore &&
430         test_path_is_file done/one
431 '
432
433 test_expect_success 'create/modify files, some of which are gitignored' '
434         echo two bis >done/two &&
435         echo three >done/three && # three is gitignored
436         echo four >done/four && # four is gitignored at a higher level
437         echo five >done/five && # five is not gitignored
438         echo test >base && #we need to ensure that the root dir is touched
439         rm base &&
440         sync_mtime
441 '
442
443 test_expect_success 'test sparse status with untracked cache' '
444         : >../trace &&
445         avoid_racy &&
446         GIT_TRACE_UNTRACKED_STATS="$TRASH_DIRECTORY/trace" \
447         git status --porcelain >../status.actual &&
448         cat >../status.expect <<EOF &&
449  M done/two
450 ?? .gitignore
451 ?? done/five
452 ?? dtwo/
453 EOF
454         test_cmp ../status.expect ../status.actual &&
455         cat >../trace.expect <<EOF &&
456 node creation: 0
457 gitignore invalidation: 1
458 directory invalidation: 2
459 opendir: 2
460 EOF
461         test_cmp ../trace.expect ../trace
462 '
463
464 test_expect_success 'untracked cache correct after status' '
465         test-dump-untracked-cache >../actual &&
466         cat >../expect <<EOF &&
467 info/exclude 13263c0978fb9fad16b2d580fb800b6d811c3ff0
468 core.excludesfile 0000000000000000000000000000000000000000
469 exclude_per_dir .gitignore
470 flags 00000006
471 / e6fcc8f2ee31bae321d66afd183fcb7237afae6e recurse valid
472 .gitignore
473 dtwo/
474 /done/ 1946f0437f90c5005533cbe1736a6451ca301714 recurse valid
475 five
476 /dthree/ 0000000000000000000000000000000000000000 recurse check_only valid
477 /dtwo/ 0000000000000000000000000000000000000000 recurse check_only valid
478 two
479 EOF
480         test_cmp ../expect ../actual
481 '
482
483 test_expect_success 'test sparse status again with untracked cache' '
484         avoid_racy &&
485         : >../trace &&
486         GIT_TRACE_UNTRACKED_STATS="$TRASH_DIRECTORY/trace" \
487         git status --porcelain >../status.actual &&
488         cat >../status.expect <<EOF &&
489  M done/two
490 ?? .gitignore
491 ?? done/five
492 ?? dtwo/
493 EOF
494         test_cmp ../status.expect ../status.actual &&
495         cat >../trace.expect <<EOF &&
496 node creation: 0
497 gitignore invalidation: 0
498 directory invalidation: 0
499 opendir: 0
500 EOF
501         test_cmp ../trace.expect ../trace
502 '
503
504 test_expect_success 'set up for test of subdir and sparse checkouts' '
505         mkdir done/sub &&
506         mkdir done/sub/sub &&
507         echo "sub" > done/sub/sub/file
508 '
509
510 test_expect_success 'test sparse status with untracked cache and subdir' '
511         avoid_racy &&
512         : >../trace &&
513         GIT_TRACE_UNTRACKED_STATS="$TRASH_DIRECTORY/trace" \
514         git status --porcelain >../status.actual &&
515         cat >../status.expect <<EOF &&
516  M done/two
517 ?? .gitignore
518 ?? done/five
519 ?? done/sub/
520 ?? dtwo/
521 EOF
522         test_cmp ../status.expect ../status.actual &&
523         cat >../trace.expect <<EOF &&
524 node creation: 2
525 gitignore invalidation: 0
526 directory invalidation: 1
527 opendir: 3
528 EOF
529         test_cmp ../trace.expect ../trace
530 '
531
532 test_expect_success 'verify untracked cache dump (sparse/subdirs)' '
533         test-dump-untracked-cache >../actual &&
534         cat >../expect-from-test-dump <<EOF &&
535 info/exclude 13263c0978fb9fad16b2d580fb800b6d811c3ff0
536 core.excludesfile 0000000000000000000000000000000000000000
537 exclude_per_dir .gitignore
538 flags 00000006
539 / e6fcc8f2ee31bae321d66afd183fcb7237afae6e recurse valid
540 .gitignore
541 dtwo/
542 /done/ 1946f0437f90c5005533cbe1736a6451ca301714 recurse valid
543 five
544 sub/
545 /done/sub/ 0000000000000000000000000000000000000000 recurse check_only valid
546 sub/
547 /done/sub/sub/ 0000000000000000000000000000000000000000 recurse check_only valid
548 file
549 /dthree/ 0000000000000000000000000000000000000000 recurse check_only valid
550 /dtwo/ 0000000000000000000000000000000000000000 recurse check_only valid
551 two
552 EOF
553         test_cmp ../expect-from-test-dump ../actual
554 '
555
556 test_expect_success 'test sparse status again with untracked cache and subdir' '
557         avoid_racy &&
558         : >../trace &&
559         GIT_TRACE_UNTRACKED_STATS="$TRASH_DIRECTORY/trace" \
560         git status --porcelain >../status.actual &&
561         test_cmp ../status.expect ../status.actual &&
562         cat >../trace.expect <<EOF &&
563 node creation: 0
564 gitignore invalidation: 0
565 directory invalidation: 0
566 opendir: 0
567 EOF
568         test_cmp ../trace.expect ../trace
569 '
570
571 test_expect_success 'move entry in subdir from untracked to cached' '
572         git add dtwo/two &&
573         git status --porcelain >../status.actual &&
574         cat >../status.expect <<EOF &&
575  M done/two
576 A  dtwo/two
577 ?? .gitignore
578 ?? done/five
579 ?? done/sub/
580 EOF
581         test_cmp ../status.expect ../status.actual
582 '
583
584 test_expect_success 'move entry in subdir from cached to untracked' '
585         git rm --cached dtwo/two &&
586         git status --porcelain >../status.actual &&
587         cat >../status.expect <<EOF &&
588  M done/two
589 ?? .gitignore
590 ?? done/five
591 ?? done/sub/
592 ?? dtwo/
593 EOF
594         test_cmp ../status.expect ../status.actual
595 '
596
597 test_expect_success '--no-untracked-cache removes the cache' '
598         git update-index --no-untracked-cache &&
599         test-dump-untracked-cache >../actual &&
600         echo "no untracked cache" >../expect-no-uc &&
601         test_cmp ../expect-no-uc ../actual
602 '
603
604 test_expect_success 'git status does not change anything' '
605         git status &&
606         test-dump-untracked-cache >../actual &&
607         test_cmp ../expect-no-uc ../actual
608 '
609
610 test_expect_success 'setting core.untrackedCache to true and using git status creates the cache' '
611         git config core.untrackedCache true &&
612         test-dump-untracked-cache >../actual &&
613         test_cmp ../expect-no-uc ../actual &&
614         git status &&
615         test-dump-untracked-cache >../actual &&
616         test_cmp ../expect-from-test-dump ../actual
617 '
618
619 test_expect_success 'using --no-untracked-cache does not fail when core.untrackedCache is true' '
620         git update-index --no-untracked-cache &&
621         test-dump-untracked-cache >../actual &&
622         test_cmp ../expect-no-uc ../actual &&
623         git update-index --untracked-cache &&
624         test-dump-untracked-cache >../actual &&
625         test_cmp ../expect-empty ../actual
626 '
627
628 test_expect_success 'setting core.untrackedCache to false and using git status removes the cache' '
629         git config core.untrackedCache false &&
630         test-dump-untracked-cache >../actual &&
631         test_cmp ../expect-empty ../actual &&
632         git status &&
633         test-dump-untracked-cache >../actual &&
634         test_cmp ../expect-no-uc ../actual
635 '
636
637 test_expect_success 'using --untracked-cache does not fail when core.untrackedCache is false' '
638         git update-index --untracked-cache &&
639         test-dump-untracked-cache >../actual &&
640         test_cmp ../expect-empty ../actual
641 '
642
643 test_expect_success 'setting core.untrackedCache to keep' '
644         git config core.untrackedCache keep &&
645         git update-index --untracked-cache &&
646         test-dump-untracked-cache >../actual &&
647         test_cmp ../expect-empty ../actual &&
648         git status &&
649         test-dump-untracked-cache >../actual &&
650         test_cmp ../expect-from-test-dump ../actual &&
651         git update-index --no-untracked-cache &&
652         test-dump-untracked-cache >../actual &&
653         test_cmp ../expect-no-uc ../actual &&
654         git update-index --force-untracked-cache &&
655         test-dump-untracked-cache >../actual &&
656         test_cmp ../expect-empty ../actual &&
657         git status &&
658         test-dump-untracked-cache >../actual &&
659         test_cmp ../expect-from-test-dump ../actual
660 '
661
662 test_expect_success 'test ident field is working' '
663         mkdir ../other_worktree &&
664         cp -R done dthree dtwo four three ../other_worktree &&
665         GIT_WORK_TREE=../other_worktree git status 2>../err &&
666         echo "warning: Untracked cache is disabled on this system or location." >../expect &&
667         test_i18ncmp ../expect ../err
668 '
669
670 test_expect_success 'untracked cache survives a checkout' '
671         git commit --allow-empty -m empty &&
672         test-dump-untracked-cache >../before &&
673         test_when_finished  "git checkout master" &&
674         git checkout -b other_branch &&
675         test-dump-untracked-cache >../after &&
676         test_cmp ../before ../after &&
677         test_commit test &&
678         test-dump-untracked-cache >../before &&
679         git checkout master &&
680         test-dump-untracked-cache >../after &&
681         test_cmp ../before ../after
682 '
683
684 test_expect_success 'untracked cache survives a commit' '
685         test-dump-untracked-cache >../before &&
686         git add done/two &&
687         git commit -m commit &&
688         test-dump-untracked-cache >../after &&
689         test_cmp ../before ../after
690 '
691
692 test_expect_success 'teardown worktree' '
693         cd ..
694 '
695
696 test_expect_success SYMLINKS 'setup worktree for symlink test' '
697         git init worktree-symlink &&
698         cd worktree-symlink &&
699         git config core.untrackedCache true &&
700         mkdir one two &&
701         touch one/file two/file &&
702         git add one/file two/file &&
703         git commit -m"first commit" &&
704         git rm -rf one &&
705         ln -s two one &&
706         git add one &&
707         git commit -m"second commit"
708 '
709
710 test_expect_success SYMLINKS '"status" after symlink replacement should be clean with UC=true' '
711         git checkout HEAD~ &&
712         status_is_clean &&
713         status_is_clean &&
714         git checkout master &&
715         avoid_racy &&
716         status_is_clean &&
717         status_is_clean
718 '
719
720 test_expect_success SYMLINKS '"status" after symlink replacement should be clean with UC=false' '
721         git config core.untrackedCache false &&
722         git checkout HEAD~ &&
723         status_is_clean &&
724         status_is_clean &&
725         git checkout master &&
726         avoid_racy &&
727         status_is_clean &&
728         status_is_clean
729 '
730
731 test_expect_success 'setup worktree for non-symlink test' '
732         git init worktree-non-symlink &&
733         cd worktree-non-symlink &&
734         git config core.untrackedCache true &&
735         mkdir one two &&
736         touch one/file two/file &&
737         git add one/file two/file &&
738         git commit -m"first commit" &&
739         git rm -rf one &&
740         cp two/file one &&
741         git add one &&
742         git commit -m"second commit"
743 '
744
745 test_expect_success '"status" after file replacement should be clean with UC=true' '
746         git checkout HEAD~ &&
747         status_is_clean &&
748         status_is_clean &&
749         git checkout master &&
750         avoid_racy &&
751         status_is_clean &&
752         test-dump-untracked-cache >../actual &&
753         grep -F "recurse valid" ../actual >../actual.grep &&
754         cat >../expect.grep <<EOF &&
755 / 0000000000000000000000000000000000000000 recurse valid
756 /two/ 0000000000000000000000000000000000000000 recurse valid
757 EOF
758         status_is_clean &&
759         test_cmp ../expect.grep ../actual.grep
760 '
761
762 test_expect_success '"status" after file replacement should be clean with UC=false' '
763         git config core.untrackedCache false &&
764         git checkout HEAD~ &&
765         status_is_clean &&
766         status_is_clean &&
767         git checkout master &&
768         avoid_racy &&
769         status_is_clean &&
770         status_is_clean
771 '
772
773 test_done