Git 2.45
[git/gitster.git] / t / t5558-clone-bundle-uri.sh
blob1ca5f745e73bd30deb9fc2dfa79baa10d63345bf
1 #!/bin/sh
3 test_description='test fetching bundles with --bundle-uri'
5 . ./test-lib.sh
7 test_expect_success 'fail to clone from non-existent file' '
8 test_when_finished rm -rf test &&
9 git clone --bundle-uri="$(pwd)/does-not-exist" . test 2>err &&
10 grep "failed to download bundle from URI" err
13 test_expect_success 'fail to clone from non-bundle file' '
14 test_when_finished rm -rf test &&
15 echo bogus >bogus &&
16 git clone --bundle-uri="$(pwd)/bogus" . test 2>err &&
17 grep "is not a bundle" err
20 test_expect_success 'create bundle' '
21 git init clone-from &&
22 git -C clone-from checkout -b topic &&
23 test_commit -C clone-from A &&
24 test_commit -C clone-from B &&
25 git -C clone-from bundle create B.bundle topic
28 test_expect_success 'clone with path bundle' '
29 git clone --bundle-uri="clone-from/B.bundle" \
30 clone-from clone-path &&
31 git -C clone-path rev-parse refs/bundles/topic >actual &&
32 git -C clone-from rev-parse topic >expect &&
33 test_cmp expect actual
36 test_expect_success 'clone with path bundle and non-default hash' '
37 test_when_finished "rm -rf clone-path-non-default-hash" &&
38 GIT_DEFAULT_HASH=sha256 git clone --bundle-uri="clone-from/B.bundle" \
39 clone-from clone-path-non-default-hash &&
40 git -C clone-path-non-default-hash rev-parse refs/bundles/topic >actual &&
41 git -C clone-from rev-parse topic >expect &&
42 test_cmp expect actual
45 test_expect_success 'clone with file:// bundle' '
46 git clone --bundle-uri="file://$(pwd)/clone-from/B.bundle" \
47 clone-from clone-file &&
48 git -C clone-file rev-parse refs/bundles/topic >actual &&
49 git -C clone-from rev-parse topic >expect &&
50 test_cmp expect actual
53 # To get interesting tests for bundle lists, we need to construct a
54 # somewhat-interesting commit history.
56 # ---------------- bundle-4
58 # 4
59 # / \
60 # ----|---|------- bundle-3
61 # | |
62 # | 3
63 # | |
64 # ----|---|------- bundle-2
65 # | |
66 # 2 |
67 # | |
68 # ----|---|------- bundle-1
69 # \ /
70 # 1
71 # |
72 # (previous commits)
73 test_expect_success 'construct incremental bundle list' '
75 cd clone-from &&
76 git checkout -b base &&
77 test_commit 1 &&
78 git checkout -b left &&
79 test_commit 2 &&
80 git checkout -b right base &&
81 test_commit 3 &&
82 git checkout -b merge left &&
83 git merge right -m "4" &&
85 git bundle create bundle-1.bundle base &&
86 git bundle create bundle-2.bundle base..left &&
87 git bundle create bundle-3.bundle base..right &&
88 git bundle create bundle-4.bundle merge --not left right
92 test_expect_success 'clone bundle list (file, no heuristic)' '
93 cat >bundle-list <<-EOF &&
94 [bundle]
95 version = 1
96 mode = all
98 [bundle "bundle-1"]
99 uri = file://$(pwd)/clone-from/bundle-1.bundle
101 [bundle "bundle-2"]
102 uri = file://$(pwd)/clone-from/bundle-2.bundle
104 [bundle "bundle-3"]
105 uri = file://$(pwd)/clone-from/bundle-3.bundle
107 [bundle "bundle-4"]
108 uri = file://$(pwd)/clone-from/bundle-4.bundle
111 git clone --bundle-uri="file://$(pwd)/bundle-list" \
112 clone-from clone-list-file 2>err &&
113 ! grep "Repository lacks these prerequisite commits" err &&
115 git -C clone-from for-each-ref --format="%(objectname)" >oids &&
116 git -C clone-list-file cat-file --batch-check <oids &&
118 git -C clone-list-file for-each-ref --format="%(refname)" >refs &&
119 grep "refs/bundles/" refs >actual &&
120 cat >expect <<-\EOF &&
121 refs/bundles/base
122 refs/bundles/left
123 refs/bundles/merge
124 refs/bundles/right
126 test_cmp expect actual
129 test_expect_success 'clone bundle list (file, all mode, some failures)' '
130 cat >bundle-list <<-EOF &&
131 [bundle]
132 version = 1
133 mode = all
135 # Does not exist. Should be skipped.
136 [bundle "bundle-0"]
137 uri = file://$(pwd)/clone-from/bundle-0.bundle
139 [bundle "bundle-1"]
140 uri = file://$(pwd)/clone-from/bundle-1.bundle
142 [bundle "bundle-2"]
143 uri = file://$(pwd)/clone-from/bundle-2.bundle
145 # No bundle-3 means bundle-4 will not apply.
147 [bundle "bundle-4"]
148 uri = file://$(pwd)/clone-from/bundle-4.bundle
150 # Does not exist. Should be skipped.
151 [bundle "bundle-5"]
152 uri = file://$(pwd)/clone-from/bundle-5.bundle
155 GIT_TRACE2_PERF=1 \
156 git clone --bundle-uri="file://$(pwd)/bundle-list" \
157 clone-from clone-all-some 2>err &&
158 ! grep "Repository lacks these prerequisite commits" err &&
159 ! grep "fatal" err &&
160 grep "warning: failed to download bundle from URI" err &&
162 git -C clone-from for-each-ref --format="%(objectname)" >oids &&
163 git -C clone-all-some cat-file --batch-check <oids &&
165 git -C clone-all-some for-each-ref --format="%(refname)" >refs &&
166 grep "refs/bundles/" refs >actual &&
167 cat >expect <<-\EOF &&
168 refs/bundles/base
169 refs/bundles/left
171 test_cmp expect actual
174 test_expect_success 'clone bundle list (file, all mode, all failures)' '
175 cat >bundle-list <<-EOF &&
176 [bundle]
177 version = 1
178 mode = all
180 # Does not exist. Should be skipped.
181 [bundle "bundle-0"]
182 uri = file://$(pwd)/clone-from/bundle-0.bundle
184 # Does not exist. Should be skipped.
185 [bundle "bundle-5"]
186 uri = file://$(pwd)/clone-from/bundle-5.bundle
189 git clone --bundle-uri="file://$(pwd)/bundle-list" \
190 clone-from clone-all-fail 2>err &&
191 ! grep "Repository lacks these prerequisite commits" err &&
192 ! grep "fatal" err &&
193 grep "warning: failed to download bundle from URI" err &&
195 git -C clone-from for-each-ref --format="%(objectname)" >oids &&
196 git -C clone-all-fail cat-file --batch-check <oids &&
198 git -C clone-all-fail for-each-ref --format="%(refname)" >refs &&
199 ! grep "refs/bundles/" refs
202 test_expect_success 'clone bundle list (file, any mode)' '
203 cat >bundle-list <<-EOF &&
204 [bundle]
205 version = 1
206 mode = any
208 # Does not exist. Should be skipped.
209 [bundle "bundle-0"]
210 uri = file://$(pwd)/clone-from/bundle-0.bundle
212 [bundle "bundle-1"]
213 uri = file://$(pwd)/clone-from/bundle-1.bundle
215 # Does not exist. Should be skipped.
216 [bundle "bundle-5"]
217 uri = file://$(pwd)/clone-from/bundle-5.bundle
220 git clone --bundle-uri="file://$(pwd)/bundle-list" \
221 clone-from clone-any-file 2>err &&
222 ! grep "Repository lacks these prerequisite commits" err &&
224 git -C clone-from for-each-ref --format="%(objectname)" >oids &&
225 git -C clone-any-file cat-file --batch-check <oids &&
227 git -C clone-any-file for-each-ref --format="%(refname)" >refs &&
228 grep "refs/bundles/" refs >actual &&
229 cat >expect <<-\EOF &&
230 refs/bundles/base
232 test_cmp expect actual
235 test_expect_success 'clone bundle list (file, any mode, all failures)' '
236 cat >bundle-list <<-EOF &&
237 [bundle]
238 version = 1
239 mode = any
241 # Does not exist. Should be skipped.
242 [bundle "bundle-0"]
243 uri = $HTTPD_URL/bundle-0.bundle
245 # Does not exist. Should be skipped.
246 [bundle "bundle-5"]
247 uri = $HTTPD_URL/bundle-5.bundle
250 git clone --bundle-uri="file://$(pwd)/bundle-list" \
251 clone-from clone-any-fail 2>err &&
252 ! grep "fatal" err &&
253 grep "warning: failed to download bundle from URI" err &&
255 git -C clone-from for-each-ref --format="%(objectname)" >oids &&
256 git -C clone-any-fail cat-file --batch-check <oids &&
258 git -C clone-any-fail for-each-ref --format="%(refname)" >refs &&
259 ! grep "refs/bundles/" refs
262 #########################################################################
263 # HTTP tests begin here
265 . "$TEST_DIRECTORY"/lib-httpd.sh
266 start_httpd
268 test_expect_success 'fail to fetch from non-existent HTTP URL' '
269 test_when_finished rm -rf test &&
270 git clone --bundle-uri="$HTTPD_URL/does-not-exist" . test 2>err &&
271 grep "failed to download bundle from URI" err
274 test_expect_success 'fail to fetch from non-bundle HTTP URL' '
275 test_when_finished rm -rf test &&
276 echo bogus >"$HTTPD_DOCUMENT_ROOT_PATH/bogus" &&
277 git clone --bundle-uri="$HTTPD_URL/bogus" . test 2>err &&
278 grep "is not a bundle" err
281 test_expect_success 'clone HTTP bundle' '
282 cp clone-from/B.bundle "$HTTPD_DOCUMENT_ROOT_PATH/B.bundle" &&
284 git clone --no-local --mirror clone-from \
285 "$HTTPD_DOCUMENT_ROOT_PATH/fetch.git" &&
287 git clone --bundle-uri="$HTTPD_URL/B.bundle" \
288 "$HTTPD_URL/smart/fetch.git" clone-http &&
289 git -C clone-http rev-parse refs/bundles/topic >actual &&
290 git -C clone-from rev-parse topic >expect &&
291 test_cmp expect actual &&
293 test_config -C clone-http log.excludedecoration refs/bundle/
296 test_expect_success 'clone HTTP bundle with non-default hash' '
297 test_when_finished "rm -rf clone-http-non-default-hash" &&
298 GIT_DEFAULT_HASH=sha256 git clone --bundle-uri="$HTTPD_URL/B.bundle" \
299 "$HTTPD_URL/smart/fetch.git" clone-http-non-default-hash &&
300 git -C clone-http-non-default-hash rev-parse refs/bundles/topic >actual &&
301 git -C clone-from rev-parse topic >expect &&
302 test_cmp expect actual
305 test_expect_success 'clone bundle list (HTTP, no heuristic)' '
306 test_when_finished rm -f trace*.txt &&
308 cp clone-from/bundle-*.bundle "$HTTPD_DOCUMENT_ROOT_PATH/" &&
309 cat >"$HTTPD_DOCUMENT_ROOT_PATH/bundle-list" <<-EOF &&
310 [bundle]
311 version = 1
312 mode = all
314 [bundle "bundle-1"]
315 uri = $HTTPD_URL/bundle-1.bundle
317 [bundle "bundle-2"]
318 uri = $HTTPD_URL/bundle-2.bundle
320 [bundle "bundle-3"]
321 uri = $HTTPD_URL/bundle-3.bundle
323 [bundle "bundle-4"]
324 uri = $HTTPD_URL/bundle-4.bundle
327 GIT_TRACE2_EVENT="$(pwd)/trace-clone.txt" \
328 git clone --bundle-uri="$HTTPD_URL/bundle-list" \
329 clone-from clone-list-http 2>err &&
330 ! grep "Repository lacks these prerequisite commits" err &&
332 git -C clone-from for-each-ref --format="%(objectname)" >oids &&
333 git -C clone-list-http cat-file --batch-check <oids &&
335 cat >expect <<-EOF &&
336 $HTTPD_URL/bundle-1.bundle
337 $HTTPD_URL/bundle-2.bundle
338 $HTTPD_URL/bundle-3.bundle
339 $HTTPD_URL/bundle-4.bundle
340 $HTTPD_URL/bundle-list
343 # Sort the list, since the order is not well-defined
344 # without a heuristic.
345 test_remote_https_urls <trace-clone.txt | sort >actual &&
346 test_cmp expect actual
349 test_expect_success 'clone bundle list (HTTP, any mode)' '
350 cp clone-from/bundle-*.bundle "$HTTPD_DOCUMENT_ROOT_PATH/" &&
351 cat >"$HTTPD_DOCUMENT_ROOT_PATH/bundle-list" <<-EOF &&
352 [bundle]
353 version = 1
354 mode = any
356 # Does not exist. Should be skipped.
357 [bundle "bundle-0"]
358 uri = $HTTPD_URL/bundle-0.bundle
360 [bundle "bundle-1"]
361 uri = $HTTPD_URL/bundle-1.bundle
363 # Does not exist. Should be skipped.
364 [bundle "bundle-5"]
365 uri = $HTTPD_URL/bundle-5.bundle
368 git clone --bundle-uri="$HTTPD_URL/bundle-list" \
369 clone-from clone-any-http 2>err &&
370 ! grep "fatal" err &&
371 grep "warning: failed to download bundle from URI" err &&
373 git -C clone-from for-each-ref --format="%(objectname)" >oids &&
374 git -C clone-any-http cat-file --batch-check <oids &&
376 git -C clone-list-file for-each-ref --format="%(refname)" >refs &&
377 grep "refs/bundles/" refs >actual &&
378 cat >expect <<-\EOF &&
379 refs/bundles/base
380 refs/bundles/left
381 refs/bundles/merge
382 refs/bundles/right
384 test_cmp expect actual
387 test_expect_success 'clone bundle list (http, creationToken)' '
388 test_when_finished rm -f trace*.txt &&
390 cp clone-from/bundle-*.bundle "$HTTPD_DOCUMENT_ROOT_PATH/" &&
391 cat >"$HTTPD_DOCUMENT_ROOT_PATH/bundle-list" <<-EOF &&
392 [bundle]
393 version = 1
394 mode = all
395 heuristic = creationToken
397 [bundle "bundle-1"]
398 uri = bundle-1.bundle
399 creationToken = 1
401 [bundle "bundle-2"]
402 uri = bundle-2.bundle
403 creationToken = 2
405 [bundle "bundle-3"]
406 uri = bundle-3.bundle
407 creationToken = 3
409 [bundle "bundle-4"]
410 uri = bundle-4.bundle
411 creationToken = 4
414 GIT_TRACE2_EVENT="$(pwd)/trace-clone.txt" git \
415 clone --bundle-uri="$HTTPD_URL/bundle-list" \
416 "$HTTPD_URL/smart/fetch.git" clone-list-http-2 &&
418 git -C clone-from for-each-ref --format="%(objectname)" >oids &&
419 git -C clone-list-http-2 cat-file --batch-check <oids &&
421 cat >expect <<-EOF &&
422 $HTTPD_URL/bundle-list
423 $HTTPD_URL/bundle-4.bundle
424 $HTTPD_URL/bundle-3.bundle
425 $HTTPD_URL/bundle-2.bundle
426 $HTTPD_URL/bundle-1.bundle
429 test_remote_https_urls <trace-clone.txt >actual &&
430 test_cmp expect actual
433 test_expect_success 'clone incomplete bundle list (http, creationToken)' '
434 test_when_finished rm -f trace*.txt &&
436 cp clone-from/bundle-*.bundle "$HTTPD_DOCUMENT_ROOT_PATH/" &&
437 cat >"$HTTPD_DOCUMENT_ROOT_PATH/bundle-list" <<-EOF &&
438 [bundle]
439 version = 1
440 mode = all
441 heuristic = creationToken
443 [bundle "bundle-1"]
444 uri = bundle-1.bundle
445 creationToken = 1
448 GIT_TRACE2_EVENT=$(pwd)/trace-clone.txt \
449 git clone --bundle-uri="$HTTPD_URL/bundle-list" \
450 --single-branch --branch=base --no-tags \
451 "$HTTPD_URL/smart/fetch.git" clone-token-http &&
453 test_cmp_config -C clone-token-http "$HTTPD_URL/bundle-list" fetch.bundleuri &&
454 test_cmp_config -C clone-token-http 1 fetch.bundlecreationtoken &&
456 cat >expect <<-EOF &&
457 $HTTPD_URL/bundle-list
458 $HTTPD_URL/bundle-1.bundle
461 test_remote_https_urls <trace-clone.txt >actual &&
462 test_cmp expect actual &&
464 # We now have only one bundle ref.
465 git -C clone-token-http for-each-ref --format="%(refname)" "refs/bundles/*" >refs &&
466 cat >expect <<-\EOF &&
467 refs/bundles/base
469 test_cmp expect refs &&
471 # Add remaining bundles, exercising the "deepening" strategy
472 # for downloading via the creationToken heurisitc.
473 cat >>"$HTTPD_DOCUMENT_ROOT_PATH/bundle-list" <<-EOF &&
474 [bundle "bundle-2"]
475 uri = bundle-2.bundle
476 creationToken = 2
478 [bundle "bundle-3"]
479 uri = bundle-3.bundle
480 creationToken = 3
482 [bundle "bundle-4"]
483 uri = bundle-4.bundle
484 creationToken = 4
487 GIT_TRACE2_EVENT="$(pwd)/trace1.txt" \
488 git -C clone-token-http fetch origin --no-tags \
489 refs/heads/merge:refs/heads/merge &&
490 test_cmp_config -C clone-token-http 4 fetch.bundlecreationtoken &&
492 cat >expect <<-EOF &&
493 $HTTPD_URL/bundle-list
494 $HTTPD_URL/bundle-4.bundle
495 $HTTPD_URL/bundle-3.bundle
496 $HTTPD_URL/bundle-2.bundle
499 test_remote_https_urls <trace1.txt >actual &&
500 test_cmp expect actual &&
502 # We now have all bundle refs.
503 git -C clone-token-http for-each-ref --format="%(refname)" "refs/bundles/*" >refs &&
505 cat >expect <<-\EOF &&
506 refs/bundles/base
507 refs/bundles/left
508 refs/bundles/merge
509 refs/bundles/right
511 test_cmp expect refs
514 test_expect_success 'http clone with bundle.heuristic creates fetch.bundleURI' '
515 test_when_finished rm -rf fetch-http-4 trace*.txt &&
517 cat >"$HTTPD_DOCUMENT_ROOT_PATH/bundle-list" <<-EOF &&
518 [bundle]
519 version = 1
520 mode = all
521 heuristic = creationToken
523 [bundle "bundle-1"]
524 uri = bundle-1.bundle
525 creationToken = 1
528 GIT_TRACE2_EVENT="$(pwd)/trace-clone.txt" \
529 git clone --single-branch --branch=base \
530 --bundle-uri="$HTTPD_URL/bundle-list" \
531 "$HTTPD_URL/smart/fetch.git" fetch-http-4 &&
533 test_cmp_config -C fetch-http-4 "$HTTPD_URL/bundle-list" fetch.bundleuri &&
534 test_cmp_config -C fetch-http-4 1 fetch.bundlecreationtoken &&
536 cat >expect <<-EOF &&
537 $HTTPD_URL/bundle-list
538 $HTTPD_URL/bundle-1.bundle
541 test_remote_https_urls <trace-clone.txt >actual &&
542 test_cmp expect actual &&
544 # only received base ref from bundle-1
545 git -C fetch-http-4 for-each-ref --format="%(refname)" "refs/bundles/*" >refs &&
546 cat >expect <<-\EOF &&
547 refs/bundles/base
549 test_cmp expect refs &&
551 cat >>"$HTTPD_DOCUMENT_ROOT_PATH/bundle-list" <<-EOF &&
552 [bundle "bundle-2"]
553 uri = bundle-2.bundle
554 creationToken = 2
557 # Fetch the objects for bundle-2 _and_ bundle-3.
558 GIT_TRACE2_EVENT="$(pwd)/trace1.txt" \
559 git -C fetch-http-4 fetch origin --no-tags \
560 refs/heads/left:refs/heads/left \
561 refs/heads/right:refs/heads/right &&
562 test_cmp_config -C fetch-http-4 2 fetch.bundlecreationtoken &&
564 cat >expect <<-EOF &&
565 $HTTPD_URL/bundle-list
566 $HTTPD_URL/bundle-2.bundle
569 test_remote_https_urls <trace1.txt >actual &&
570 test_cmp expect actual &&
572 # received left from bundle-2
573 git -C fetch-http-4 for-each-ref --format="%(refname)" "refs/bundles/*" >refs &&
574 cat >expect <<-\EOF &&
575 refs/bundles/base
576 refs/bundles/left
578 test_cmp expect refs &&
580 # No-op fetch
581 GIT_TRACE2_EVENT="$(pwd)/trace1b.txt" \
582 git -C fetch-http-4 fetch origin --no-tags \
583 refs/heads/left:refs/heads/left \
584 refs/heads/right:refs/heads/right &&
586 cat >expect <<-EOF &&
587 $HTTPD_URL/bundle-list
589 test_remote_https_urls <trace1b.txt >actual &&
590 test_cmp expect actual &&
592 cat >>"$HTTPD_DOCUMENT_ROOT_PATH/bundle-list" <<-EOF &&
593 [bundle "bundle-3"]
594 uri = bundle-3.bundle
595 creationToken = 3
597 [bundle "bundle-4"]
598 uri = bundle-4.bundle
599 creationToken = 4
602 # This fetch should skip bundle-3.bundle, since its objects are
603 # already local (we have the requisite commits for bundle-4.bundle).
604 GIT_TRACE2_EVENT="$(pwd)/trace2.txt" \
605 git -C fetch-http-4 fetch origin --no-tags \
606 refs/heads/merge:refs/heads/merge &&
607 test_cmp_config -C fetch-http-4 4 fetch.bundlecreationtoken &&
609 cat >expect <<-EOF &&
610 $HTTPD_URL/bundle-list
611 $HTTPD_URL/bundle-4.bundle
614 test_remote_https_urls <trace2.txt >actual &&
615 test_cmp expect actual &&
617 # received merge ref from bundle-4, but right is missing
618 # because we did not download bundle-3.
619 git -C fetch-http-4 for-each-ref --format="%(refname)" "refs/bundles/*" >refs &&
621 cat >expect <<-\EOF &&
622 refs/bundles/base
623 refs/bundles/left
624 refs/bundles/merge
626 test_cmp expect refs &&
628 # No-op fetch
629 GIT_TRACE2_EVENT="$(pwd)/trace2b.txt" \
630 git -C fetch-http-4 fetch origin &&
632 cat >expect <<-EOF &&
633 $HTTPD_URL/bundle-list
635 test_remote_https_urls <trace2b.txt >actual &&
636 test_cmp expect actual
639 test_expect_success 'creationToken heuristic with failed downloads (clone)' '
640 test_when_finished rm -rf download-* trace*.txt &&
642 # Case 1: base bundle does not exist, nothing can unbundle
643 cat >"$HTTPD_DOCUMENT_ROOT_PATH/bundle-list" <<-EOF &&
644 [bundle]
645 version = 1
646 mode = all
647 heuristic = creationToken
649 [bundle "bundle-1"]
650 uri = fake.bundle
651 creationToken = 1
653 [bundle "bundle-2"]
654 uri = bundle-2.bundle
655 creationToken = 2
657 [bundle "bundle-3"]
658 uri = bundle-3.bundle
659 creationToken = 3
661 [bundle "bundle-4"]
662 uri = bundle-4.bundle
663 creationToken = 4
666 GIT_TRACE2_EVENT="$(pwd)/trace-clone-1.txt" \
667 git clone --single-branch --branch=base \
668 --bundle-uri="$HTTPD_URL/bundle-list" \
669 "$HTTPD_URL/smart/fetch.git" download-1 &&
671 # Bundle failure does not set these configs.
672 test_must_fail git -C download-1 config fetch.bundleuri &&
673 test_must_fail git -C download-1 config fetch.bundlecreationtoken &&
675 cat >expect <<-EOF &&
676 $HTTPD_URL/bundle-list
677 $HTTPD_URL/bundle-4.bundle
678 $HTTPD_URL/bundle-3.bundle
679 $HTTPD_URL/bundle-2.bundle
680 $HTTPD_URL/fake.bundle
682 test_remote_https_urls <trace-clone-1.txt >actual &&
683 test_cmp expect actual &&
685 # All bundles failed to unbundle
686 git -C download-1 for-each-ref --format="%(refname)" "refs/bundles/*" >refs &&
687 test_must_be_empty refs &&
689 # Case 2: middle bundle does not exist, only two bundles can unbundle
690 cat >"$HTTPD_DOCUMENT_ROOT_PATH/bundle-list" <<-EOF &&
691 [bundle]
692 version = 1
693 mode = all
694 heuristic = creationToken
696 [bundle "bundle-1"]
697 uri = bundle-1.bundle
698 creationToken = 1
700 [bundle "bundle-2"]
701 uri = fake.bundle
702 creationToken = 2
704 [bundle "bundle-3"]
705 uri = bundle-3.bundle
706 creationToken = 3
708 [bundle "bundle-4"]
709 uri = bundle-4.bundle
710 creationToken = 4
713 GIT_TRACE2_EVENT="$(pwd)/trace-clone-2.txt" \
714 git clone --single-branch --branch=base \
715 --bundle-uri="$HTTPD_URL/bundle-list" \
716 "$HTTPD_URL/smart/fetch.git" download-2 &&
718 # Bundle failure does not set these configs.
719 test_must_fail git -C download-2 config fetch.bundleuri &&
720 test_must_fail git -C download-2 config fetch.bundlecreationtoken &&
722 cat >expect <<-EOF &&
723 $HTTPD_URL/bundle-list
724 $HTTPD_URL/bundle-4.bundle
725 $HTTPD_URL/bundle-3.bundle
726 $HTTPD_URL/fake.bundle
727 $HTTPD_URL/bundle-1.bundle
729 test_remote_https_urls <trace-clone-2.txt >actual &&
730 test_cmp expect actual &&
732 # bundle-1 and bundle-3 could unbundle, but bundle-4 could not
733 git -C download-2 for-each-ref --format="%(refname)" "refs/bundles/*" >refs &&
734 cat >expect <<-EOF &&
735 refs/bundles/base
736 refs/bundles/right
738 test_cmp expect refs &&
740 # Case 3: top bundle does not exist, rest unbundle fine.
741 cat >"$HTTPD_DOCUMENT_ROOT_PATH/bundle-list" <<-EOF &&
742 [bundle]
743 version = 1
744 mode = all
745 heuristic = creationToken
747 [bundle "bundle-1"]
748 uri = bundle-1.bundle
749 creationToken = 1
751 [bundle "bundle-2"]
752 uri = bundle-2.bundle
753 creationToken = 2
755 [bundle "bundle-3"]
756 uri = bundle-3.bundle
757 creationToken = 3
759 [bundle "bundle-4"]
760 uri = fake.bundle
761 creationToken = 4
764 GIT_TRACE2_EVENT="$(pwd)/trace-clone-3.txt" \
765 git clone --single-branch --branch=base \
766 --bundle-uri="$HTTPD_URL/bundle-list" \
767 "$HTTPD_URL/smart/fetch.git" download-3 &&
769 # As long as we have continguous successful downloads,
770 # we _do_ set these configs.
771 test_cmp_config -C download-3 "$HTTPD_URL/bundle-list" fetch.bundleuri &&
772 test_cmp_config -C download-3 3 fetch.bundlecreationtoken &&
774 cat >expect <<-EOF &&
775 $HTTPD_URL/bundle-list
776 $HTTPD_URL/fake.bundle
777 $HTTPD_URL/bundle-3.bundle
778 $HTTPD_URL/bundle-2.bundle
779 $HTTPD_URL/bundle-1.bundle
781 test_remote_https_urls <trace-clone-3.txt >actual &&
782 test_cmp expect actual &&
784 # fake.bundle did not unbundle, but the others did.
785 git -C download-3 for-each-ref --format="%(refname)" "refs/bundles/*" >refs &&
786 cat >expect <<-EOF &&
787 refs/bundles/base
788 refs/bundles/left
789 refs/bundles/right
791 test_cmp expect refs
794 # Expand the bundle list to include other interesting shapes, specifically
795 # interesting for use when fetching from a previous state.
797 # ---------------- bundle-7
799 # _/|\_
800 # ---/--|--\------ bundle-6
801 # 5 | 6
802 # --|---|---|----- bundle-4
803 # | 4 |
804 # | / \ /
805 # --|-|---|/------ bundle-3 (the client will be caught up to this point.)
806 # \ | 3
807 # ---\|---|------- bundle-2
808 # 2 |
809 # ----|---|------- bundle-1
810 # \ /
813 # (previous commits)
814 test_expect_success 'expand incremental bundle list' '
816 cd clone-from &&
817 git checkout -b lefter left &&
818 test_commit 5 &&
819 git checkout -b righter right &&
820 test_commit 6 &&
821 git checkout -b top lefter &&
822 git merge -m "7" merge righter &&
824 git bundle create bundle-6.bundle lefter righter --not left right &&
825 git bundle create bundle-7.bundle top --not lefter merge righter &&
827 cp bundle-*.bundle "$HTTPD_DOCUMENT_ROOT_PATH/"
828 ) &&
829 git -C "$HTTPD_DOCUMENT_ROOT_PATH/fetch.git" fetch origin +refs/heads/*:refs/heads/*
832 test_expect_success 'creationToken heuristic with failed downloads (fetch)' '
833 test_when_finished rm -rf download-* trace*.txt &&
835 cat >"$HTTPD_DOCUMENT_ROOT_PATH/bundle-list" <<-EOF &&
836 [bundle]
837 version = 1
838 mode = all
839 heuristic = creationToken
841 [bundle "bundle-1"]
842 uri = bundle-1.bundle
843 creationToken = 1
845 [bundle "bundle-2"]
846 uri = bundle-2.bundle
847 creationToken = 2
849 [bundle "bundle-3"]
850 uri = bundle-3.bundle
851 creationToken = 3
854 git clone --single-branch --branch=left \
855 --bundle-uri="$HTTPD_URL/bundle-list" \
856 "$HTTPD_URL/smart/fetch.git" fetch-base &&
857 test_cmp_config -C fetch-base "$HTTPD_URL/bundle-list" fetch.bundleURI &&
858 test_cmp_config -C fetch-base 3 fetch.bundleCreationToken &&
860 # Case 1: all bundles exist: successful unbundling of all bundles
861 cat >"$HTTPD_DOCUMENT_ROOT_PATH/bundle-list" <<-EOF &&
862 [bundle]
863 version = 1
864 mode = all
865 heuristic = creationToken
867 [bundle "bundle-1"]
868 uri = bundle-1.bundle
869 creationToken = 1
871 [bundle "bundle-2"]
872 uri = bundle-2.bundle
873 creationToken = 2
875 [bundle "bundle-3"]
876 uri = bundle-3.bundle
877 creationToken = 3
879 [bundle "bundle-4"]
880 uri = bundle-4.bundle
881 creationToken = 4
883 [bundle "bundle-6"]
884 uri = bundle-6.bundle
885 creationToken = 6
887 [bundle "bundle-7"]
888 uri = bundle-7.bundle
889 creationToken = 7
892 cp -r fetch-base fetch-1 &&
893 GIT_TRACE2_EVENT="$(pwd)/trace-fetch-1.txt" \
894 git -C fetch-1 fetch origin &&
895 test_cmp_config -C fetch-1 7 fetch.bundlecreationtoken &&
897 cat >expect <<-EOF &&
898 $HTTPD_URL/bundle-list
899 $HTTPD_URL/bundle-7.bundle
900 $HTTPD_URL/bundle-6.bundle
901 $HTTPD_URL/bundle-4.bundle
903 test_remote_https_urls <trace-fetch-1.txt >actual &&
904 test_cmp expect actual &&
906 # Check which bundles have unbundled by refs
907 git -C fetch-1 for-each-ref --format="%(refname)" "refs/bundles/*" >refs &&
908 cat >expect <<-EOF &&
909 refs/bundles/base
910 refs/bundles/left
911 refs/bundles/lefter
912 refs/bundles/merge
913 refs/bundles/right
914 refs/bundles/righter
915 refs/bundles/top
917 test_cmp expect refs &&
919 # Case 2: middle bundle does not exist, only bundle-4 can unbundle
920 cat >"$HTTPD_DOCUMENT_ROOT_PATH/bundle-list" <<-EOF &&
921 [bundle]
922 version = 1
923 mode = all
924 heuristic = creationToken
926 [bundle "bundle-1"]
927 uri = bundle-1.bundle
928 creationToken = 1
930 [bundle "bundle-2"]
931 uri = bundle-2.bundle
932 creationToken = 2
934 [bundle "bundle-3"]
935 uri = bundle-3.bundle
936 creationToken = 3
938 [bundle "bundle-4"]
939 uri = bundle-4.bundle
940 creationToken = 4
942 [bundle "bundle-6"]
943 uri = fake.bundle
944 creationToken = 6
946 [bundle "bundle-7"]
947 uri = bundle-7.bundle
948 creationToken = 7
951 cp -r fetch-base fetch-2 &&
952 GIT_TRACE2_EVENT="$(pwd)/trace-fetch-2.txt" \
953 git -C fetch-2 fetch origin &&
955 # Since bundle-7 fails to unbundle, do not update creation token.
956 test_cmp_config -C fetch-2 3 fetch.bundlecreationtoken &&
958 cat >expect <<-EOF &&
959 $HTTPD_URL/bundle-list
960 $HTTPD_URL/bundle-7.bundle
961 $HTTPD_URL/fake.bundle
962 $HTTPD_URL/bundle-4.bundle
964 test_remote_https_urls <trace-fetch-2.txt >actual &&
965 test_cmp expect actual &&
967 # Check which bundles have unbundled by refs
968 git -C fetch-2 for-each-ref --format="%(refname)" "refs/bundles/*" >refs &&
969 cat >expect <<-EOF &&
970 refs/bundles/base
971 refs/bundles/left
972 refs/bundles/merge
973 refs/bundles/right
975 test_cmp expect refs &&
977 # Case 3: top bundle does not exist, rest unbundle fine.
978 cat >"$HTTPD_DOCUMENT_ROOT_PATH/bundle-list" <<-EOF &&
979 [bundle]
980 version = 1
981 mode = all
982 heuristic = creationToken
984 [bundle "bundle-1"]
985 uri = bundle-1.bundle
986 creationToken = 1
988 [bundle "bundle-2"]
989 uri = bundle-2.bundle
990 creationToken = 2
992 [bundle "bundle-3"]
993 uri = bundle-3.bundle
994 creationToken = 3
996 [bundle "bundle-4"]
997 uri = bundle-4.bundle
998 creationToken = 4
1000 [bundle "bundle-6"]
1001 uri = bundle-6.bundle
1002 creationToken = 6
1004 [bundle "bundle-7"]
1005 uri = fake.bundle
1006 creationToken = 7
1009 cp -r fetch-base fetch-3 &&
1010 GIT_TRACE2_EVENT="$(pwd)/trace-fetch-3.txt" \
1011 git -C fetch-3 fetch origin &&
1013 # As long as we have continguous successful downloads,
1014 # we _do_ set the maximum creation token.
1015 test_cmp_config -C fetch-3 6 fetch.bundlecreationtoken &&
1017 # NOTE: the fetch skips bundle-4 since bundle-6 successfully
1018 # unbundles itself and bundle-7 failed to download.
1019 cat >expect <<-EOF &&
1020 $HTTPD_URL/bundle-list
1021 $HTTPD_URL/fake.bundle
1022 $HTTPD_URL/bundle-6.bundle
1024 test_remote_https_urls <trace-fetch-3.txt >actual &&
1025 test_cmp expect actual &&
1027 # Check which bundles have unbundled by refs
1028 git -C fetch-3 for-each-ref --format="%(refname)" "refs/bundles/*" >refs &&
1029 cat >expect <<-EOF &&
1030 refs/bundles/base
1031 refs/bundles/left
1032 refs/bundles/lefter
1033 refs/bundles/right
1034 refs/bundles/righter
1036 test_cmp expect refs
1039 test_expect_success 'bundles are downloaded once during fetch --all' '
1040 test_when_finished rm -rf download-* trace*.txt fetch-mult &&
1042 cat >"$HTTPD_DOCUMENT_ROOT_PATH/bundle-list" <<-EOF &&
1043 [bundle]
1044 version = 1
1045 mode = all
1046 heuristic = creationToken
1048 [bundle "bundle-1"]
1049 uri = bundle-1.bundle
1050 creationToken = 1
1052 [bundle "bundle-2"]
1053 uri = bundle-2.bundle
1054 creationToken = 2
1056 [bundle "bundle-3"]
1057 uri = bundle-3.bundle
1058 creationToken = 3
1061 git clone --single-branch --branch=left \
1062 --bundle-uri="$HTTPD_URL/bundle-list" \
1063 "$HTTPD_URL/smart/fetch.git" fetch-mult &&
1064 git -C fetch-mult remote add dup1 "$HTTPD_URL/smart/fetch.git" &&
1065 git -C fetch-mult remote add dup2 "$HTTPD_URL/smart/fetch.git" &&
1067 GIT_TRACE2_EVENT="$(pwd)/trace-mult.txt" \
1068 git -C fetch-mult fetch --all &&
1069 grep "\"child_start\".*\"git-remote-https\",\"$HTTPD_URL/bundle-list\"" \
1070 trace-mult.txt >bundle-fetches &&
1071 test_line_count = 1 bundle-fetches
1073 # Do not add tests here unless they use the HTTP server, as they will
1074 # not run unless the HTTP dependencies exist.
1076 test_done