]>
Commit | Line | Data |
---|---|---|
cf9dc653 MW |
1 | #!/bin/sh |
2 | # | |
3 | # Copyright (C) 2006 Martin Waitz <tali@admingilde.org> | |
4 | # | |
5 | ||
6 | test_description='test clone --reference' | |
7 | . ./test-lib.sh | |
8 | ||
46d76d6c | 9 | base_dir=$(pwd) |
cf9dc653 | 10 | |
4ba776c2 DB |
11 | U=$base_dir/UPLOAD_LOG |
12 | ||
bc192300 JK |
13 | # create a commit in repo $1 with name $2 |
14 | commit_in () { | |
15 | ( | |
16 | cd "$1" && | |
17 | echo "$2" >"$2" && | |
18 | git add "$2" && | |
19 | git commit -m "$2" | |
20 | ) | |
21 | } | |
22 | ||
23 | # check that there are $2 loose objects in repo $1 | |
24 | test_objcount () { | |
25 | echo "$2" >expect && | |
26 | git -C "$1" count-objects >actual.raw && | |
27 | cut -d' ' -f1 <actual.raw >actual && | |
28 | test_cmp expect actual | |
29 | } | |
30 | ||
31 | test_expect_success 'preparing first repository' ' | |
32 | test_create_repo A && | |
33 | commit_in A file1 | |
34 | ' | |
cf9dc653 | 35 | |
bc192300 JK |
36 | test_expect_success 'preparing second repository' ' |
37 | git clone A B && | |
38 | commit_in B file2 && | |
39 | git -C B repack -ad && | |
40 | git -C B prune | |
41 | ' | |
cf9dc653 | 42 | |
bc192300 JK |
43 | test_expect_success 'cloning with reference (-l -s)' ' |
44 | git clone -l -s --reference B A C | |
45 | ' | |
cf9dc653 | 46 | |
bc192300 JK |
47 | test_expect_success 'existence of info/alternates' ' |
48 | test_line_count = 2 C/.git/objects/info/alternates | |
49 | ' | |
cf9dc653 | 50 | |
bc192300 JK |
51 | test_expect_success 'pulling from reference' ' |
52 | git -C C pull ../B master | |
53 | ' | |
cf9dc653 | 54 | |
bc192300 JK |
55 | test_expect_success 'that reference gets used' ' |
56 | test_objcount C 0 | |
57 | ' | |
4ba776c2 | 58 | |
2ad23273 JK |
59 | test_expect_success 'cloning with reference (no -l -s)' ' |
60 | GIT_TRACE_PACKET=$U.D git clone --reference B "file://$(pwd)/A" D | |
61 | ' | |
4ba776c2 | 62 | |
2ad23273 JK |
63 | test_expect_success 'fetched no objects' ' |
64 | test -s "$U.D" && | |
65 | ! grep " want" "$U.D" | |
66 | ' | |
1f7d1a53 | 67 | |
bc192300 JK |
68 | test_expect_success 'existence of info/alternates' ' |
69 | test_line_count = 1 D/.git/objects/info/alternates | |
70 | ' | |
1f7d1a53 | 71 | |
bc192300 JK |
72 | test_expect_success 'pulling from reference' ' |
73 | git -C D pull ../B master | |
74 | ' | |
cf9dc653 | 75 | |
bc192300 JK |
76 | test_expect_success 'that reference gets used' ' |
77 | test_objcount D 0 | |
78 | ' | |
cf9dc653 | 79 | |
bc192300 JK |
80 | test_expect_success 'updating origin' ' |
81 | commit_in A file3 && | |
82 | git -C A repack -ad && | |
83 | git -C A prune | |
84 | ' | |
cf9dc653 | 85 | |
bc192300 JK |
86 | test_expect_success 'pulling changes from origin' ' |
87 | git -C C pull origin | |
88 | ' | |
cf9dc653 MW |
89 | |
90 | # the 2 local objects are commit and tree from the merge | |
bc192300 JK |
91 | test_expect_success 'that alternate to origin gets used' ' |
92 | test_objcount C 2 | |
93 | ' | |
1f7d1a53 | 94 | |
bc192300 JK |
95 | test_expect_success 'pulling changes from origin' ' |
96 | git -C D pull origin | |
97 | ' | |
1f7d1a53 JH |
98 | |
99 | # the 5 local objects are expected; file3 blob, commit in A to add it | |
100 | # and its tree, and 2 are our tree and the merge commit. | |
bc192300 JK |
101 | test_expect_success 'check objects expected to exist locally' ' |
102 | test_objcount D 5 | |
103 | ' | |
fabb0199 | 104 | |
bc192300 JK |
105 | test_expect_success 'preparing alternate repository #1' ' |
106 | test_create_repo F && | |
107 | commit_in F file1 | |
108 | ' | |
fabb0199 | 109 | |
bc192300 JK |
110 | test_expect_success 'cloning alternate repo #2 and adding changes to repo #1' ' |
111 | git clone F G && | |
112 | commit_in F file2 | |
113 | ' | |
fabb0199 | 114 | |
bc192300 JK |
115 | test_expect_success 'cloning alternate repo #1, using #2 as reference' ' |
116 | git clone --reference G F H | |
117 | ' | |
b50c8469 | 118 | |
bc192300 JK |
119 | test_expect_success 'cloning with reference being subset of source (-l -s)' ' |
120 | git clone -l -s --reference A B E | |
121 | ' | |
b50c8469 | 122 | |
77b9b1d1 JK |
123 | test_expect_success 'cloning with multiple references drops duplicates' ' |
124 | git clone -s --reference B --reference A --reference B A dups && | |
125 | test_line_count = 2 dups/.git/objects/info/alternates | |
126 | ' | |
127 | ||
09116a1c JH |
128 | test_expect_success 'clone with reference from a tagged repository' ' |
129 | ( | |
bc192300 | 130 | cd A && git tag -a -m tagged HEAD |
09116a1c JH |
131 | ) && |
132 | git clone --reference=A A I | |
133 | ' | |
134 | ||
acede2eb MH |
135 | test_expect_success 'prepare branched repository' ' |
136 | git clone A J && | |
137 | ( | |
138 | cd J && | |
139 | git checkout -b other master^ && | |
140 | echo other >otherfile && | |
141 | git add otherfile && | |
142 | git commit -m other && | |
143 | git checkout master | |
144 | ) | |
145 | ' | |
146 | ||
f2576591 | 147 | test_expect_success 'fetch with incomplete alternates' ' |
acede2eb MH |
148 | git init K && |
149 | echo "$base_dir/A/.git/objects" >K/.git/objects/info/alternates && | |
150 | ( | |
151 | cd K && | |
152 | git remote add J "file://$base_dir/J" && | |
2ad23273 | 153 | GIT_TRACE_PACKET=$U.K git fetch J |
acede2eb MH |
154 | ) && |
155 | master_object=$(cd A && git for-each-ref --format="%(objectname)" refs/heads/master) && | |
2ad23273 | 156 | test -s "$U.K" && |
97a83fa8 | 157 | ! grep " want $master_object" "$U.K" && |
acede2eb | 158 | tag_object=$(cd A && git for-each-ref --format="%(objectname)" refs/tags/HEAD) && |
97a83fa8 | 159 | ! grep " want $tag_object" "$U.K" |
acede2eb MH |
160 | ' |
161 | ||
b552b56d AS |
162 | test_expect_success 'clone using repo with gitfile as a reference' ' |
163 | git clone --separate-git-dir=L A M && | |
164 | git clone --reference=M A N && | |
165 | echo "$base_dir/L/objects" >expected && | |
166 | test_cmp expected "$base_dir/N/.git/objects/info/alternates" | |
167 | ' | |
168 | ||
169 | test_expect_success 'clone using repo pointed at by gitfile as reference' ' | |
170 | git clone --reference=M/.git A O && | |
171 | echo "$base_dir/L/objects" >expected && | |
172 | test_cmp expected "$base_dir/O/.git/objects/info/alternates" | |
173 | ' | |
174 | ||
fb1d6dab JH |
175 | test_expect_success 'clone and dissociate from reference' ' |
176 | git init P && | |
177 | ( | |
178 | cd P && test_commit one | |
179 | ) && | |
180 | git clone P Q && | |
181 | ( | |
182 | cd Q && test_commit two | |
183 | ) && | |
184 | git clone --no-local --reference=P Q R && | |
185 | git clone --no-local --reference=P --dissociate Q S && | |
186 | # removing the reference P would corrupt R but not S | |
187 | rm -fr P && | |
188 | test_must_fail git -C R fsck && | |
189 | git -C S fsck | |
190 | ' | |
786b150c | 191 | test_expect_success 'clone, dissociate from partial reference and repack' ' |
11911bf7 JS |
192 | rm -fr P Q R && |
193 | git init P && | |
194 | ( | |
195 | cd P && | |
196 | test_commit one && | |
197 | git repack && | |
198 | test_commit two && | |
199 | git repack | |
200 | ) && | |
201 | git clone --bare P Q && | |
202 | ( | |
203 | cd P && | |
204 | git checkout -b second && | |
205 | test_commit three && | |
206 | git repack | |
207 | ) && | |
208 | git clone --bare --dissociate --reference=P Q R && | |
209 | ls R/objects/pack/*.pack >packs.txt && | |
210 | test_line_count = 1 packs.txt | |
211 | ' | |
fb1d6dab | 212 | |
0181681e AR |
213 | test_expect_success 'clone, dissociate from alternates' ' |
214 | rm -fr A B C && | |
215 | test_create_repo A && | |
216 | commit_in A file1 && | |
217 | git clone --reference=A A B && | |
218 | test_line_count = 1 B/.git/objects/info/alternates && | |
219 | git clone --local --dissociate B C && | |
220 | ! test -f C/.git/objects/info/alternates && | |
221 | ( cd C && git fsck ) | |
222 | ' | |
223 | ||
03156169 ÆAB |
224 | test_expect_success 'setup repo with garbage in objects/*' ' |
225 | git init S && | |
226 | ( | |
227 | cd S && | |
228 | test_commit A && | |
229 | ||
230 | cd .git/objects && | |
231 | >.some-hidden-file && | |
232 | >some-file && | |
233 | mkdir .some-hidden-dir && | |
234 | >.some-hidden-dir/some-file && | |
235 | >.some-hidden-dir/.some-dot-file && | |
236 | mkdir some-dir && | |
237 | >some-dir/some-file && | |
238 | >some-dir/.some-dot-file | |
239 | ) | |
240 | ' | |
241 | ||
242 | test_expect_success 'clone a repo with garbage in objects/*' ' | |
243 | for option in --local --no-hardlinks --shared --dissociate | |
244 | do | |
245 | git clone $option S S$option || return 1 && | |
246 | git -C S$option fsck || return 1 | |
247 | done && | |
248 | find S-* -name "*some*" | sort >actual && | |
249 | cat >expected <<-EOF && | |
68c7c59c MT |
250 | S--dissociate/.git/objects/.some-hidden-dir |
251 | S--dissociate/.git/objects/.some-hidden-dir/.some-dot-file | |
252 | S--dissociate/.git/objects/.some-hidden-dir/some-file | |
03156169 ÆAB |
253 | S--dissociate/.git/objects/.some-hidden-file |
254 | S--dissociate/.git/objects/some-dir | |
255 | S--dissociate/.git/objects/some-dir/.some-dot-file | |
256 | S--dissociate/.git/objects/some-dir/some-file | |
257 | S--dissociate/.git/objects/some-file | |
68c7c59c MT |
258 | S--local/.git/objects/.some-hidden-dir |
259 | S--local/.git/objects/.some-hidden-dir/.some-dot-file | |
260 | S--local/.git/objects/.some-hidden-dir/some-file | |
03156169 ÆAB |
261 | S--local/.git/objects/.some-hidden-file |
262 | S--local/.git/objects/some-dir | |
263 | S--local/.git/objects/some-dir/.some-dot-file | |
264 | S--local/.git/objects/some-dir/some-file | |
265 | S--local/.git/objects/some-file | |
68c7c59c MT |
266 | S--no-hardlinks/.git/objects/.some-hidden-dir |
267 | S--no-hardlinks/.git/objects/.some-hidden-dir/.some-dot-file | |
268 | S--no-hardlinks/.git/objects/.some-hidden-dir/some-file | |
03156169 ÆAB |
269 | S--no-hardlinks/.git/objects/.some-hidden-file |
270 | S--no-hardlinks/.git/objects/some-dir | |
271 | S--no-hardlinks/.git/objects/some-dir/.some-dot-file | |
272 | S--no-hardlinks/.git/objects/some-dir/some-file | |
273 | S--no-hardlinks/.git/objects/some-file | |
274 | EOF | |
275 | test_cmp expected actual | |
276 | ' | |
277 | ||
36596fd2 | 278 | test_expect_success SYMLINKS 'setup repo with manually symlinked or unknown files at objects/' ' |
03156169 ÆAB |
279 | git init T && |
280 | ( | |
281 | cd T && | |
282 | git config gc.auto 0 && | |
283 | test_commit A && | |
284 | git gc && | |
285 | test_commit B && | |
286 | ||
287 | cd .git/objects && | |
288 | mv pack packs && | |
289 | ln -s packs pack && | |
290 | find ?? -type d >loose-dirs && | |
291 | last_loose=$(tail -n 1 loose-dirs) && | |
03156169 ÆAB |
292 | mv $last_loose a-loose-dir && |
293 | ln -s a-loose-dir $last_loose && | |
36596fd2 MT |
294 | first_loose=$(head -n 1 loose-dirs) && |
295 | rm -f loose-dirs && | |
296 | ||
297 | cd $first_loose && | |
298 | obj=$(ls *) && | |
299 | mv $obj ../an-object && | |
300 | ln -s ../an-object $obj && | |
301 | ||
302 | cd ../ && | |
03156169 | 303 | find . -type f | sort >../../../T.objects-files.raw && |
36596fd2 | 304 | find . -type l | sort >../../../T.objects-symlinks.raw && |
03156169 ÆAB |
305 | echo unknown_content >unknown_file |
306 | ) && | |
307 | git -C T fsck && | |
308 | git -C T rev-list --all --objects >T.objects | |
309 | ' | |
310 | ||
311 | ||
36596fd2 | 312 | test_expect_success SYMLINKS 'clone repo with symlinked or unknown files at objects/' ' |
03156169 ÆAB |
313 | for option in --local --no-hardlinks --shared --dissociate |
314 | do | |
315 | git clone $option T T$option || return 1 && | |
316 | git -C T$option fsck || return 1 && | |
317 | git -C T$option rev-list --all --objects >T$option.objects && | |
318 | test_cmp T.objects T$option.objects && | |
319 | ( | |
320 | cd T$option/.git/objects && | |
36596fd2 MT |
321 | find . -type f | sort >../../../T$option.objects-files.raw && |
322 | find . -type l | sort >../../../T$option.objects-symlinks.raw | |
03156169 ÆAB |
323 | ) |
324 | done && | |
325 | ||
326 | for raw in $(ls T*.raw) | |
327 | do | |
328 | sed -e "s!/../!/Y/!; s![0-9a-f]\{38,\}!Z!" -e "/commit-graph/d" \ | |
329 | -e "/multi-pack-index/d" <$raw >$raw.de-sha || return 1 | |
330 | done && | |
331 | ||
332 | cat >expected-files <<-EOF && | |
333 | ./Y/Z | |
334 | ./Y/Z | |
335 | ./a-loose-dir/Z | |
36596fd2 | 336 | ./an-object |
03156169 ÆAB |
337 | ./Y/Z |
338 | ./info/packs | |
339 | ./pack/pack-Z.idx | |
340 | ./pack/pack-Z.pack | |
341 | ./packs/pack-Z.idx | |
342 | ./packs/pack-Z.pack | |
343 | ./unknown_file | |
344 | EOF | |
345 | ||
36596fd2 | 346 | for option in --local --no-hardlinks --dissociate |
03156169 | 347 | do |
36596fd2 MT |
348 | test_cmp expected-files T$option.objects-files.raw.de-sha || return 1 && |
349 | test_must_be_empty T$option.objects-symlinks.raw.de-sha || return 1 | |
03156169 ÆAB |
350 | done && |
351 | ||
352 | echo ./info/alternates >expected-files && | |
36596fd2 MT |
353 | test_cmp expected-files T--shared.objects-files.raw && |
354 | test_must_be_empty T--shared.objects-symlinks.raw | |
03156169 ÆAB |
355 | ' |
356 | ||
cf9dc653 | 357 | test_done |