144 lines
		
	
	
		
			4.3 KiB
		
	
	
	
		
			Bash
		
	
	
		
			Executable File
		
	
			
		
		
	
	
			144 lines
		
	
	
		
			4.3 KiB
		
	
	
	
		
			Bash
		
	
	
		
			Executable File
		
	
| #!/bin/sh
 | |
| 
 | |
| test_description='exercise delta islands'
 | |
| . ./test-lib.sh
 | |
| 
 | |
| # returns true iff $1 is a delta based on $2
 | |
| is_delta_base () {
 | |
| 	delta_base=$(echo "$1" | git cat-file --batch-check='%(deltabase)') &&
 | |
| 	echo >&2 "$1 has base $delta_base" &&
 | |
| 	test "$delta_base" = "$2"
 | |
| }
 | |
| 
 | |
| # generate a commit on branch $1 with a single file, "file", whose
 | |
| # content is mostly based on the seed $2, but with a unique bit
 | |
| # of content $3 appended. This should allow us to see whether
 | |
| # blobs of different refs delta against each other.
 | |
| commit() {
 | |
| 	blob=$({ test-tool genrandom "$2" 10240 && echo "$3"; } |
 | |
| 	       git hash-object -w --stdin) &&
 | |
| 	tree=$(printf '100644 blob %s\tfile\n' "$blob" | git mktree) &&
 | |
| 	commit=$(echo "$2-$3" | git commit-tree "$tree" ${4:+-p "$4"}) &&
 | |
| 	git update-ref "refs/heads/$1" "$commit" &&
 | |
| 	eval "$1"'=$(git rev-parse $1:file)' &&
 | |
| 	eval "echo >&2 $1=\$$1"
 | |
| }
 | |
| 
 | |
| test_expect_success 'setup commits' '
 | |
| 	commit one seed 1 &&
 | |
| 	commit two seed 12
 | |
| '
 | |
| 
 | |
| # Note: This is heavily dependent on the "prefer larger objects as base"
 | |
| # heuristic.
 | |
| test_expect_success 'vanilla repack deltas one against two' '
 | |
| 	git repack -adf &&
 | |
| 	is_delta_base $one $two
 | |
| '
 | |
| 
 | |
| test_expect_success 'island repack with no island definition is vanilla' '
 | |
| 	git repack -adfi &&
 | |
| 	is_delta_base $one $two
 | |
| '
 | |
| 
 | |
| test_expect_success 'island repack with no matches is vanilla' '
 | |
| 	git -c "pack.island=refs/foo" repack -adfi &&
 | |
| 	is_delta_base $one $two
 | |
| '
 | |
| 
 | |
| test_expect_success 'separate islands disallows delta' '
 | |
| 	git -c "pack.island=refs/heads/(.*)" repack -adfi &&
 | |
| 	! is_delta_base $one $two &&
 | |
| 	! is_delta_base $two $one
 | |
| '
 | |
| 
 | |
| test_expect_success 'same island allows delta' '
 | |
| 	git -c "pack.island=refs/heads" repack -adfi &&
 | |
| 	is_delta_base $one $two
 | |
| '
 | |
| 
 | |
| test_expect_success 'coalesce same-named islands' '
 | |
| 	git \
 | |
| 		-c "pack.island=refs/(.*)/one" \
 | |
| 		-c "pack.island=refs/(.*)/two" \
 | |
| 		repack -adfi &&
 | |
| 	is_delta_base $one $two
 | |
| '
 | |
| 
 | |
| test_expect_success 'island restrictions drop reused deltas' '
 | |
| 	git repack -adfi &&
 | |
| 	is_delta_base $one $two &&
 | |
| 	git -c "pack.island=refs/heads/(.*)" repack -adi &&
 | |
| 	! is_delta_base $one $two &&
 | |
| 	! is_delta_base $two $one
 | |
| '
 | |
| 
 | |
| test_expect_success 'island regexes are left-anchored' '
 | |
| 	git -c "pack.island=heads/(.*)" repack -adfi &&
 | |
| 	is_delta_base $one $two
 | |
| '
 | |
| 
 | |
| test_expect_success 'island regexes follow last-one-wins scheme' '
 | |
| 	git \
 | |
| 		-c "pack.island=refs/heads/(.*)" \
 | |
| 		-c "pack.island=refs/heads/" \
 | |
| 		repack -adfi &&
 | |
| 	is_delta_base $one $two
 | |
| '
 | |
| 
 | |
| test_expect_success 'setup shared history' '
 | |
| 	commit root shared root &&
 | |
| 	commit one shared 1 root &&
 | |
| 	commit two shared 12-long root
 | |
| '
 | |
| 
 | |
| # We know that $two will be preferred as a base from $one,
 | |
| # because we can transform it with a pure deletion.
 | |
| #
 | |
| # We also expect $root as a delta against $two by the "longest is base" rule.
 | |
| test_expect_success 'vanilla delta goes between branches' '
 | |
| 	git repack -adf &&
 | |
| 	is_delta_base $one $two &&
 | |
| 	is_delta_base $root $two
 | |
| '
 | |
| 
 | |
| # Here we should allow $one to base itself on $root; even though
 | |
| # they are in different islands, the objects in $root are in a superset
 | |
| # of islands compared to those in $one.
 | |
| #
 | |
| # Similarly, $two can delta against $root by our rules. And unlike $one,
 | |
| # in which we are just allowing it, the island rules actually put $root
 | |
| # as a possible base for $two, which it would not otherwise be (due to the size
 | |
| # sorting).
 | |
| test_expect_success 'deltas allowed against superset islands' '
 | |
| 	git -c "pack.island=refs/heads/(.*)" repack -adfi &&
 | |
| 	is_delta_base $one $root &&
 | |
| 	is_delta_base $two $root
 | |
| '
 | |
| 
 | |
| # We are going to test the packfile order here, so we again have to make some
 | |
| # assumptions. We assume that "$root", as part of our core "one", must come
 | |
| # before "$two". This should be guaranteed by the island code. However, for
 | |
| # this test to fail without islands, we are also assuming that it would not
 | |
| # otherwise do so. This is true by the current write order, which will put
 | |
| # commits (and their contents) before their parents.
 | |
| test_expect_success 'island core places core objects first' '
 | |
| 	cat >expect <<-EOF &&
 | |
| 	$root
 | |
| 	$two
 | |
| 	EOF
 | |
| 	git -c "pack.island=refs/heads/(.*)" \
 | |
| 	    -c "pack.islandcore=one" \
 | |
| 	    repack -adfi &&
 | |
| 	git verify-pack -v .git/objects/pack/*.pack |
 | |
| 	cut -d" " -f1 |
 | |
| 	egrep "$root|$two" >actual &&
 | |
| 	test_cmp expect actual
 | |
| '
 | |
| 
 | |
| test_expect_success 'unmatched island core is not fatal' '
 | |
| 	git -c "pack.islandcore=one" repack -adfi
 | |
| '
 | |
| 
 | |
| test_done
 |