]> rtime.felk.cvut.cz Git - git.git/blob - t/t5505-remote.sh
builtin-remote: teach show to display remote HEAD
[git.git] / t / t5505-remote.sh
1 #!/bin/sh
2
3 test_description='git remote porcelain-ish'
4
5 . ./test-lib.sh
6
7 setup_repository () {
8         mkdir "$1" && (
9         cd "$1" &&
10         git init &&
11         >file &&
12         git add file &&
13         test_tick &&
14         git commit -m "Initial" &&
15         git checkout -b side &&
16         >elif &&
17         git add elif &&
18         test_tick &&
19         git commit -m "Second" &&
20         git checkout master
21         )
22 }
23
24 tokens_match () {
25         echo "$1" | tr ' ' '\012' | sort | sed -e '/^$/d' >expect &&
26         echo "$2" | tr ' ' '\012' | sort | sed -e '/^$/d' >actual &&
27         test_cmp expect actual
28 }
29
30 check_remote_track () {
31         actual=$(git remote show "$1" | sed -e '1,/Tracked/d') &&
32         shift &&
33         tokens_match "$*" "$actual"
34 }
35
36 check_tracking_branch () {
37         f="" &&
38         r=$(git for-each-ref "--format=%(refname)" |
39                 sed -ne "s|^refs/remotes/$1/||p") &&
40         shift &&
41         tokens_match "$*" "$r"
42 }
43
44 test_expect_success setup '
45
46         setup_repository one &&
47         setup_repository two &&
48         (
49                 cd two && git branch another
50         ) &&
51         git clone one test
52
53 '
54
55 test_expect_success 'remote information for the origin' '
56 (
57         cd test &&
58         tokens_match origin "$(git remote)" &&
59         check_remote_track origin master side &&
60         check_tracking_branch origin HEAD master side
61 )
62 '
63
64 test_expect_success 'add another remote' '
65 (
66         cd test &&
67         git remote add -f second ../two &&
68         tokens_match "origin second" "$(git remote)" &&
69         check_remote_track origin master side &&
70         check_remote_track second master side another &&
71         check_tracking_branch second master side another &&
72         git for-each-ref "--format=%(refname)" refs/remotes |
73         sed -e "/^refs\/remotes\/origin\//d" \
74             -e "/^refs\/remotes\/second\//d" >actual &&
75         >expect &&
76         test_cmp expect actual
77 )
78 '
79
80 test_expect_success 'remote forces tracking branches' '
81 (
82         cd test &&
83         case `git config remote.second.fetch` in
84         +*) true ;;
85          *) false ;;
86         esac
87 )
88 '
89
90 test_expect_success 'remove remote' '
91 (
92         cd test &&
93         git symbolic-ref refs/remotes/second/HEAD refs/remotes/second/master &&
94         git remote rm second
95 )
96 '
97
98 test_expect_success 'remove remote' '
99 (
100         cd test &&
101         tokens_match origin "$(git remote)" &&
102         check_remote_track origin master side &&
103         git for-each-ref "--format=%(refname)" refs/remotes |
104         sed -e "/^refs\/remotes\/origin\//d" >actual &&
105         >expect &&
106         test_cmp expect actual
107 )
108 '
109
110 test_expect_success 'remove remote protects non-remote branches' '
111 (
112         cd test &&
113         (cat >expect1 <<EOF
114 Note: A non-remote branch was not removed; to delete it, use:
115   git branch -d master
116 EOF
117     cat >expect2 <<EOF
118 Note: Non-remote branches were not removed; to delete them, use:
119   git branch -d foobranch
120   git branch -d master
121 EOF
122 ) &&
123         git tag footag
124         git config --add remote.oops.fetch "+refs/*:refs/*" &&
125         git remote rm oops 2>actual1 &&
126         git branch foobranch &&
127         git config --add remote.oops.fetch "+refs/*:refs/*" &&
128         git remote rm oops 2>actual2 &&
129         git branch -d foobranch &&
130         git tag -d footag &&
131         test_cmp expect1 actual1 &&
132         test_cmp expect2 actual2
133 )
134 '
135
136 cat > test/expect << EOF
137 * remote origin
138   URL: $(pwd)/one
139   HEAD branch: master
140   Remote branch merged with 'git pull' while on branch master
141     master
142   New remote branch (next fetch will store in remotes/origin)
143     master
144   Tracked remote branches
145     master
146     side
147   Local branches pushed with 'git push'
148     master:upstream
149     +refs/tags/lastbackup
150 * remote two
151   URL: ../two
152   HEAD branch (remote HEAD is ambiguous, may be one of the following):
153     another
154     master
155 EOF
156
157 test_expect_success 'show' '
158         (cd test &&
159          git config --add remote.origin.fetch \
160                 refs/heads/master:refs/heads/upstream &&
161          git fetch &&
162          git branch -d -r origin/master &&
163          git config --add remote.two.url ../two &&
164          (cd ../one &&
165           echo 1 > file &&
166           test_tick &&
167           git commit -m update file) &&
168          git config remote.origin.push \
169                 refs/heads/master:refs/heads/upstream &&
170          git config --add remote.origin.push \
171                 +refs/tags/lastbackup &&
172          git remote show origin two > output &&
173          test_cmp expect output)
174 '
175
176 cat > test/expect << EOF
177 * remote origin
178   URL: $(pwd)/one
179   HEAD branch: (not queried)
180   Remote branch merged with 'git pull' while on branch master
181     master
182   Tracked remote branches
183     master
184     side
185   Local branches pushed with 'git push'
186     master:upstream
187     +refs/tags/lastbackup
188 EOF
189
190 test_expect_success 'show -n' '
191         (mv one one.unreachable &&
192          cd test &&
193          git remote show -n origin > output &&
194          mv ../one.unreachable ../one &&
195          test_cmp expect output)
196 '
197
198 test_expect_success 'prune' '
199         (cd one &&
200          git branch -m side side2) &&
201         (cd test &&
202          git fetch origin &&
203          git remote prune origin &&
204          git rev-parse refs/remotes/origin/side2 &&
205          test_must_fail git rev-parse refs/remotes/origin/side)
206 '
207
208 cat > test/expect << EOF
209 Pruning origin
210 URL: $(pwd)/one
211  * [would prune] origin/side2
212 EOF
213
214 test_expect_success 'prune --dry-run' '
215         (cd one &&
216          git branch -m side2 side) &&
217         (cd test &&
218          git remote prune --dry-run origin > output &&
219          git rev-parse refs/remotes/origin/side2 &&
220          test_must_fail git rev-parse refs/remotes/origin/side &&
221         (cd ../one &&
222          git branch -m side side2) &&
223          test_cmp expect output)
224 '
225
226 test_expect_success 'add --mirror && prune' '
227         (mkdir mirror &&
228          cd mirror &&
229          git init --bare &&
230          git remote add --mirror -f origin ../one) &&
231         (cd one &&
232          git branch -m side2 side) &&
233         (cd mirror &&
234          git rev-parse --verify refs/heads/side2 &&
235          test_must_fail git rev-parse --verify refs/heads/side &&
236          git fetch origin &&
237          git remote prune origin &&
238          test_must_fail git rev-parse --verify refs/heads/side2 &&
239          git rev-parse --verify refs/heads/side)
240 '
241
242 test_expect_success 'add alt && prune' '
243         (mkdir alttst &&
244          cd alttst &&
245          git init &&
246          git remote add -f origin ../one &&
247          git config remote.alt.url ../one &&
248          git config remote.alt.fetch "+refs/heads/*:refs/remotes/origin/*") &&
249         (cd one &&
250          git branch -m side side2) &&
251         (cd alttst &&
252          git rev-parse --verify refs/remotes/origin/side &&
253          test_must_fail git rev-parse --verify refs/remotes/origin/side2 &&
254          git fetch alt &&
255          git remote prune alt &&
256          test_must_fail git rev-parse --verify refs/remotes/origin/side &&
257          git rev-parse --verify refs/remotes/origin/side2)
258 '
259
260 cat > one/expect << EOF
261   apis/master
262   apis/side
263   drosophila/another
264   drosophila/master
265   drosophila/side
266 EOF
267
268 test_expect_success 'update' '
269
270         (cd one &&
271          git remote add drosophila ../two &&
272          git remote add apis ../mirror &&
273          git remote update &&
274          git branch -r > output &&
275          test_cmp expect output)
276
277 '
278
279 cat > one/expect << EOF
280   drosophila/another
281   drosophila/master
282   drosophila/side
283   manduca/master
284   manduca/side
285   megaloprepus/master
286   megaloprepus/side
287 EOF
288
289 test_expect_success 'update with arguments' '
290
291         (cd one &&
292          for b in $(git branch -r)
293          do
294                 git branch -r -d $b || break
295          done &&
296          git remote add manduca ../mirror &&
297          git remote add megaloprepus ../mirror &&
298          git config remotes.phobaeticus "drosophila megaloprepus" &&
299          git config remotes.titanus manduca &&
300          git remote update phobaeticus titanus &&
301          git branch -r > output &&
302          test_cmp expect output)
303
304 '
305
306 cat > one/expect << EOF
307   apis/master
308   apis/side
309   manduca/master
310   manduca/side
311   megaloprepus/master
312   megaloprepus/side
313 EOF
314
315 test_expect_success 'update default' '
316
317         (cd one &&
318          for b in $(git branch -r)
319          do
320                 git branch -r -d $b || break
321          done &&
322          git config remote.drosophila.skipDefaultUpdate true &&
323          git remote update default &&
324          git branch -r > output &&
325          test_cmp expect output)
326
327 '
328
329 cat > one/expect << EOF
330   drosophila/another
331   drosophila/master
332   drosophila/side
333 EOF
334
335 test_expect_success 'update default (overridden, with funny whitespace)' '
336
337         (cd one &&
338          for b in $(git branch -r)
339          do
340                 git branch -r -d $b || break
341          done &&
342          git config remotes.default "$(printf "\t drosophila  \n")" &&
343          git remote update default &&
344          git branch -r > output &&
345          test_cmp expect output)
346
347 '
348
349 test_expect_success '"remote show" does not show symbolic refs' '
350
351         git clone one three &&
352         (cd three &&
353          git remote show origin > output &&
354          ! grep "^ *HEAD$" < output &&
355          ! grep -i stale < output)
356
357 '
358
359 test_expect_success 'reject adding remote with an invalid name' '
360
361         test_must_fail git remote add some:url desired-name
362
363 '
364
365 # The first three test if the tracking branches are properly renamed,
366 # the last two ones check if the config is updated.
367
368 test_expect_success 'rename a remote' '
369
370         git clone one four &&
371         (cd four &&
372          git remote rename origin upstream &&
373          rmdir .git/refs/remotes/origin &&
374          test "$(git symbolic-ref refs/remotes/upstream/HEAD)" = "refs/remotes/upstream/master" &&
375          test "$(git rev-parse upstream/master)" = "$(git rev-parse master)" &&
376          test "$(git config remote.upstream.fetch)" = "+refs/heads/*:refs/remotes/upstream/*" &&
377          test "$(git config branch.master.remote)" = "upstream")
378
379 '
380
381 cat > remotes_origin << EOF
382 URL: $(pwd)/one
383 Push: refs/heads/master:refs/heads/upstream
384 Pull: refs/heads/master:refs/heads/origin
385 EOF
386
387 test_expect_success 'migrate a remote from named file in $GIT_DIR/remotes' '
388         git clone one five &&
389         origin_url=$(pwd)/one &&
390         (cd five &&
391          git remote rm origin &&
392          mkdir -p .git/remotes &&
393          cat ../remotes_origin > .git/remotes/origin &&
394          git remote rename origin origin &&
395          ! test -f .git/remotes/origin &&
396          test "$(git config remote.origin.url)" = "$origin_url" &&
397          test "$(git config remote.origin.push)" = "refs/heads/master:refs/heads/upstream" &&
398          test "$(git config remote.origin.fetch)" = "refs/heads/master:refs/heads/origin")
399 '
400
401 test_expect_success 'migrate a remote from named file in $GIT_DIR/branches' '
402         git clone one six &&
403         origin_url=$(pwd)/one &&
404         (cd six &&
405          git remote rm origin &&
406          echo "$origin_url" > .git/branches/origin &&
407          git remote rename origin origin &&
408          ! test -f .git/branches/origin &&
409          test "$(git config remote.origin.url)" = "$origin_url" &&
410          test "$(git config remote.origin.fetch)" = "refs/heads/master:refs/heads/origin")
411 '
412
413 test_expect_success 'remote prune to cause a dangling symref' '
414         git clone one seven &&
415         (
416                 cd one &&
417                 git checkout side2 &&
418                 git branch -D master
419         ) &&
420         (
421                 cd seven &&
422                 git remote prune origin
423         ) 2>err &&
424         grep "has become dangling" err &&
425
426         : And the dangling symref will not cause other annoying errors
427         (
428                 cd seven &&
429                 git branch -a
430         ) 2>err &&
431         ! grep "points nowhere" err
432         (
433                 cd seven &&
434                 test_must_fail git branch nomore origin
435         ) 2>err &&
436         grep "dangling symref" err
437 '
438
439 test_done
440