##// END OF EJS Templates
fetch: use cmdutil.bailifchanged()...
Martin von Zweigbergk -
r22676:a014fdc9 default
parent child Browse files
Show More
@@ -1,155 +1,149 b''
1 1 # fetch.py - pull and merge remote changes
2 2 #
3 3 # Copyright 2006 Vadim Gelfer <vadim.gelfer@gmail.com>
4 4 #
5 5 # This software may be used and distributed according to the terms of the
6 6 # GNU General Public License version 2 or any later version.
7 7
8 8 '''pull, update and merge in one command (DEPRECATED)'''
9 9
10 10 from mercurial.i18n import _
11 from mercurial.node import nullid, short
11 from mercurial.node import short
12 12 from mercurial import commands, cmdutil, hg, util, error
13 13 from mercurial.lock import release
14 14
15 15 cmdtable = {}
16 16 command = cmdutil.command(cmdtable)
17 17 testedwith = 'internal'
18 18
19 19 @command('fetch',
20 20 [('r', 'rev', [],
21 21 _('a specific revision you would like to pull'), _('REV')),
22 22 ('e', 'edit', None, _('invoke editor on commit messages')),
23 23 ('', 'force-editor', None, _('edit commit message (DEPRECATED)')),
24 24 ('', 'switch-parent', None, _('switch parents when merging')),
25 25 ] + commands.commitopts + commands.commitopts2 + commands.remoteopts,
26 26 _('hg fetch [SOURCE]'))
27 27 def fetch(ui, repo, source='default', **opts):
28 28 '''pull changes from a remote repository, merge new changes if needed.
29 29
30 30 This finds all changes from the repository at the specified path
31 31 or URL and adds them to the local repository.
32 32
33 33 If the pulled changes add a new branch head, the head is
34 34 automatically merged, and the result of the merge is committed.
35 35 Otherwise, the working directory is updated to include the new
36 36 changes.
37 37
38 38 When a merge is needed, the working directory is first updated to
39 39 the newly pulled changes. Local changes are then merged into the
40 40 pulled changes. To switch the merge order, use --switch-parent.
41 41
42 42 See :hg:`help dates` for a list of formats valid for -d/--date.
43 43
44 44 Returns 0 on success.
45 45 '''
46 46
47 47 date = opts.get('date')
48 48 if date:
49 49 opts['date'] = util.parsedate(date)
50 50
51 parent, p2 = repo.dirstate.parents()
51 parent, _p2 = repo.dirstate.parents()
52 52 branch = repo.dirstate.branch()
53 53 try:
54 54 branchnode = repo.branchtip(branch)
55 55 except error.RepoLookupError:
56 56 branchnode = None
57 57 if parent != branchnode:
58 58 raise util.Abort(_('working dir not at branch tip '
59 59 '(use "hg update" to check out branch tip)'))
60 60
61 if p2 != nullid:
62 raise util.Abort(_('outstanding uncommitted merge'))
63
64 61 wlock = lock = None
65 62 try:
66 63 wlock = repo.wlock()
67 64 lock = repo.lock()
68 mod, add, rem, del_ = repo.status()[:4]
69 65
70 if mod or add or rem:
71 raise util.Abort(_('outstanding uncommitted changes'))
72 if del_:
73 raise util.Abort(_('working directory is missing some files'))
66 cmdutil.bailifchanged(repo)
67
74 68 bheads = repo.branchheads(branch)
75 69 bheads = [head for head in bheads if len(repo[head].children()) == 0]
76 70 if len(bheads) > 1:
77 71 raise util.Abort(_('multiple heads in this branch '
78 72 '(use "hg heads ." and "hg merge" to merge)'))
79 73
80 74 other = hg.peer(repo, opts, ui.expandpath(source))
81 75 ui.status(_('pulling from %s\n') %
82 76 util.hidepassword(ui.expandpath(source)))
83 77 revs = None
84 78 if opts['rev']:
85 79 try:
86 80 revs = [other.lookup(rev) for rev in opts['rev']]
87 81 except error.CapabilityError:
88 82 err = _("other repository doesn't support revision lookup, "
89 83 "so a rev cannot be specified.")
90 84 raise util.Abort(err)
91 85
92 86 # Are there any changes at all?
93 87 modheads = repo.pull(other, heads=revs)
94 88 if modheads == 0:
95 89 return 0
96 90
97 91 # Is this a simple fast-forward along the current branch?
98 92 newheads = repo.branchheads(branch)
99 93 newchildren = repo.changelog.nodesbetween([parent], newheads)[2]
100 94 if len(newheads) == 1 and len(newchildren):
101 95 if newchildren[0] != parent:
102 96 return hg.update(repo, newchildren[0])
103 97 else:
104 98 return 0
105 99
106 100 # Are there more than one additional branch heads?
107 101 newchildren = [n for n in newchildren if n != parent]
108 102 newparent = parent
109 103 if newchildren:
110 104 newparent = newchildren[0]
111 105 hg.clean(repo, newparent)
112 106 newheads = [n for n in newheads if n != newparent]
113 107 if len(newheads) > 1:
114 108 ui.status(_('not merging with %d other new branch heads '
115 109 '(use "hg heads ." and "hg merge" to merge them)\n') %
116 110 (len(newheads) - 1))
117 111 return 1
118 112
119 113 if not newheads:
120 114 return 0
121 115
122 116 # Otherwise, let's merge.
123 117 err = False
124 118 if newheads:
125 119 # By default, we consider the repository we're pulling
126 120 # *from* as authoritative, so we merge our changes into
127 121 # theirs.
128 122 if opts['switch_parent']:
129 123 firstparent, secondparent = newparent, newheads[0]
130 124 else:
131 125 firstparent, secondparent = newheads[0], newparent
132 126 ui.status(_('updating to %d:%s\n') %
133 127 (repo.changelog.rev(firstparent),
134 128 short(firstparent)))
135 129 hg.clean(repo, firstparent)
136 130 ui.status(_('merging with %d:%s\n') %
137 131 (repo.changelog.rev(secondparent), short(secondparent)))
138 132 err = hg.merge(repo, secondparent, remind=False)
139 133
140 134 if not err:
141 135 # we don't translate commit messages
142 136 message = (cmdutil.logmessage(ui, opts) or
143 137 ('Automated merge with %s' %
144 138 util.removeauth(other.url())))
145 139 editopt = opts.get('edit') or opts.get('force_editor')
146 140 editor = cmdutil.getcommiteditor(edit=editopt, editform='fetch')
147 141 n = repo.commit(message, opts['user'], opts['date'], editor=editor)
148 142 ui.status(_('new changeset %d:%s merges remote changes '
149 143 'with local\n') % (repo.changelog.rev(n),
150 144 short(n)))
151 145
152 146 return err
153 147
154 148 finally:
155 149 release(lock, wlock)
@@ -1,431 +1,431 b''
1 1 #require serve
2 2
3 3 $ echo "[extensions]" >> $HGRCPATH
4 4 $ echo "fetch=" >> $HGRCPATH
5 5
6 6 test fetch with default branches only
7 7
8 8 $ hg init a
9 9 $ echo a > a/a
10 10 $ hg --cwd a commit -Ama
11 11 adding a
12 12 $ hg clone a b
13 13 updating to branch default
14 14 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
15 15 $ hg clone a c
16 16 updating to branch default
17 17 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
18 18 $ echo b > a/b
19 19 $ hg --cwd a commit -Amb
20 20 adding b
21 21 $ hg --cwd a parents -q
22 22 1:d2ae7f538514
23 23
24 24 should pull one change
25 25
26 26 $ hg --cwd b fetch ../a
27 27 pulling from ../a
28 28 searching for changes
29 29 adding changesets
30 30 adding manifests
31 31 adding file changes
32 32 added 1 changesets with 1 changes to 1 files
33 33 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
34 34 $ hg --cwd b parents -q
35 35 1:d2ae7f538514
36 36 $ echo c > c/c
37 37 $ hg --cwd c commit -Amc
38 38 adding c
39 39 $ hg clone c d
40 40 updating to branch default
41 41 2 files updated, 0 files merged, 0 files removed, 0 files unresolved
42 42 $ hg clone c e
43 43 updating to branch default
44 44 2 files updated, 0 files merged, 0 files removed, 0 files unresolved
45 45
46 46 We cannot use the default commit message if fetching from a local
47 47 repo, because the path of the repo will be included in the commit
48 48 message, making every commit appear different.
49 49 should merge c into a
50 50
51 51 $ hg --cwd c fetch -d '0 0' -m 'automated merge' ../a
52 52 pulling from ../a
53 53 searching for changes
54 54 adding changesets
55 55 adding manifests
56 56 adding file changes
57 57 added 1 changesets with 1 changes to 1 files (+1 heads)
58 58 updating to 2:d2ae7f538514
59 59 1 files updated, 0 files merged, 1 files removed, 0 files unresolved
60 60 merging with 1:d36c0562f908
61 61 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
62 62 new changeset 3:a323a0c43ec4 merges remote changes with local
63 63 $ ls c
64 64 a
65 65 b
66 66 c
67 67 $ hg --cwd a serve -a localhost -p $HGPORT -d --pid-file=hg.pid
68 68 $ cat a/hg.pid >> "$DAEMON_PIDS"
69 69
70 70 fetch over http, no auth
71 71 (this also tests that editor is invoked if '--edit' is specified)
72 72
73 73 $ HGEDITOR=cat hg --cwd d fetch --edit http://localhost:$HGPORT/
74 74 pulling from http://localhost:$HGPORT/
75 75 searching for changes
76 76 adding changesets
77 77 adding manifests
78 78 adding file changes
79 79 added 1 changesets with 1 changes to 1 files (+1 heads)
80 80 updating to 2:d2ae7f538514
81 81 1 files updated, 0 files merged, 1 files removed, 0 files unresolved
82 82 merging with 1:d36c0562f908
83 83 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
84 84 Automated merge with http://localhost:$HGPORT/
85 85
86 86
87 87 HG: Enter commit message. Lines beginning with 'HG:' are removed.
88 88 HG: Leave message empty to abort commit.
89 89 HG: --
90 90 HG: user: test
91 91 HG: branch merge
92 92 HG: branch 'default'
93 93 HG: changed c
94 94 new changeset 3:* merges remote changes with local (glob)
95 95 $ hg --cwd d tip --template '{desc}\n'
96 96 Automated merge with http://localhost:$HGPORT/
97 97 $ hg --cwd d status --rev 'tip^1' --rev tip
98 98 A c
99 99 $ hg --cwd d status --rev 'tip^2' --rev tip
100 100 A b
101 101
102 102 fetch over http with auth (should be hidden in desc)
103 103 (this also tests that editor is not invoked if '--edit' is not
104 104 specified, even though commit message is not specified explicitly)
105 105
106 106 $ HGEDITOR=cat hg --cwd e fetch http://user:password@localhost:$HGPORT/
107 107 pulling from http://user:***@localhost:$HGPORT/
108 108 searching for changes
109 109 adding changesets
110 110 adding manifests
111 111 adding file changes
112 112 added 1 changesets with 1 changes to 1 files (+1 heads)
113 113 updating to 2:d2ae7f538514
114 114 1 files updated, 0 files merged, 1 files removed, 0 files unresolved
115 115 merging with 1:d36c0562f908
116 116 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
117 117 new changeset 3:* merges remote changes with local (glob)
118 118 $ hg --cwd e tip --template '{desc}\n'
119 119 Automated merge with http://localhost:$HGPORT/
120 120 $ hg clone a f
121 121 updating to branch default
122 122 2 files updated, 0 files merged, 0 files removed, 0 files unresolved
123 123 $ hg clone a g
124 124 updating to branch default
125 125 2 files updated, 0 files merged, 0 files removed, 0 files unresolved
126 126 $ echo f > f/f
127 127 $ hg --cwd f ci -Amf
128 128 adding f
129 129 $ echo g > g/g
130 130 $ hg --cwd g ci -Amg
131 131 adding g
132 132 $ hg clone -q f h
133 133 $ hg clone -q g i
134 134
135 135 should merge f into g
136 136
137 137 $ hg --cwd g fetch -d '0 0' --switch -m 'automated merge' ../f
138 138 pulling from ../f
139 139 searching for changes
140 140 adding changesets
141 141 adding manifests
142 142 adding file changes
143 143 added 1 changesets with 1 changes to 1 files (+1 heads)
144 144 0 files updated, 0 files merged, 0 files removed, 0 files unresolved
145 145 merging with 3:6343ca3eff20
146 146 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
147 147 new changeset 4:f7faa0b7d3c6 merges remote changes with local
148 148 $ rm i/g
149 149
150 150 should abort, because i is modified
151 151
152 152 $ hg --cwd i fetch ../h
153 abort: working directory is missing some files
153 abort: uncommitted changes
154 154 [255]
155 155
156 156 test fetch with named branches
157 157
158 158 $ hg init nbase
159 159 $ echo base > nbase/a
160 160 $ hg -R nbase ci -Am base
161 161 adding a
162 162 $ hg -R nbase branch a
163 163 marked working directory as branch a
164 164 (branches are permanent and global, did you want a bookmark?)
165 165 $ echo a > nbase/a
166 166 $ hg -R nbase ci -m a
167 167 $ hg -R nbase up -C 0
168 168 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
169 169 $ hg -R nbase branch b
170 170 marked working directory as branch b
171 171 (branches are permanent and global, did you want a bookmark?)
172 172 $ echo b > nbase/b
173 173 $ hg -R nbase ci -Am b
174 174 adding b
175 175
176 176 pull in change on foreign branch
177 177
178 178 $ hg clone nbase n1
179 179 updating to branch default
180 180 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
181 181 $ hg clone nbase n2
182 182 updating to branch default
183 183 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
184 184 $ hg -R n1 up -C a
185 185 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
186 186 $ echo aa > n1/a
187 187 $ hg -R n1 ci -m a1
188 188 $ hg -R n2 up -C b
189 189 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
190 190 $ hg -R n2 fetch -m 'merge' n1
191 191 pulling from n1
192 192 searching for changes
193 193 adding changesets
194 194 adding manifests
195 195 adding file changes
196 196 added 1 changesets with 1 changes to 1 files
197 197
198 198 parent should be 2 (no automatic update)
199 199
200 200 $ hg -R n2 parents --template '{rev}\n'
201 201 2
202 202 $ rm -fr n1 n2
203 203
204 204 pull in changes on both foreign and local branches
205 205
206 206 $ hg clone nbase n1
207 207 updating to branch default
208 208 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
209 209 $ hg clone nbase n2
210 210 updating to branch default
211 211 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
212 212 $ hg -R n1 up -C a
213 213 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
214 214 $ echo aa > n1/a
215 215 $ hg -R n1 ci -m a1
216 216 $ hg -R n1 up -C b
217 217 2 files updated, 0 files merged, 0 files removed, 0 files unresolved
218 218 $ echo bb > n1/b
219 219 $ hg -R n1 ci -m b1
220 220 $ hg -R n2 up -C b
221 221 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
222 222 $ hg -R n2 fetch -m 'merge' n1
223 223 pulling from n1
224 224 searching for changes
225 225 adding changesets
226 226 adding manifests
227 227 adding file changes
228 228 added 2 changesets with 2 changes to 2 files
229 229 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
230 230
231 231 parent should be 4 (fast forward)
232 232
233 233 $ hg -R n2 parents --template '{rev}\n'
234 234 4
235 235 $ rm -fr n1 n2
236 236
237 237 pull changes on foreign (2 new heads) and local (1 new head) branches
238 238 with a local change
239 239
240 240 $ hg clone nbase n1
241 241 updating to branch default
242 242 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
243 243 $ hg clone nbase n2
244 244 updating to branch default
245 245 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
246 246 $ hg -R n1 up -C a
247 247 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
248 248 $ echo a1 > n1/a
249 249 $ hg -R n1 ci -m a1
250 250 $ hg -R n1 up -C b
251 251 2 files updated, 0 files merged, 0 files removed, 0 files unresolved
252 252 $ echo bb > n1/b
253 253 $ hg -R n1 ci -m b1
254 254 $ hg -R n1 up -C 1
255 255 1 files updated, 0 files merged, 1 files removed, 0 files unresolved
256 256 $ echo a2 > n1/a
257 257 $ hg -R n1 ci -m a2
258 258 created new head
259 259 $ hg -R n2 up -C b
260 260 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
261 261 $ echo change >> n2/c
262 262 $ hg -R n2 ci -A -m local
263 263 adding c
264 264 $ hg -R n2 fetch -d '0 0' -m 'merge' n1
265 265 pulling from n1
266 266 searching for changes
267 267 adding changesets
268 268 adding manifests
269 269 adding file changes
270 270 added 3 changesets with 3 changes to 2 files (+2 heads)
271 271 updating to 5:3c4a837a864f
272 272 1 files updated, 0 files merged, 1 files removed, 0 files unresolved
273 273 merging with 3:1267f84a9ea5
274 274 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
275 275 new changeset 7:2cf2a1261f21 merges remote changes with local
276 276
277 277 parent should be 7 (new merge changeset)
278 278
279 279 $ hg -R n2 parents --template '{rev}\n'
280 280 7
281 281 $ rm -fr n1 n2
282 282
283 283 pull in changes on foreign (merge of local branch) and local (2 new
284 284 heads) with a local change
285 285
286 286 $ hg clone nbase n1
287 287 updating to branch default
288 288 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
289 289 $ hg clone nbase n2
290 290 updating to branch default
291 291 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
292 292 $ hg -R n1 up -C a
293 293 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
294 294 $ hg -R n1 merge b
295 295 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
296 296 (branch merge, don't forget to commit)
297 297 $ hg -R n1 ci -m merge
298 298 $ hg -R n1 up -C 2
299 299 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
300 300 $ echo c > n1/a
301 301 $ hg -R n1 ci -m c
302 302 $ hg -R n1 up -C 2
303 303 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
304 304 $ echo cc > n1/a
305 305 $ hg -R n1 ci -m cc
306 306 created new head
307 307 $ hg -R n2 up -C b
308 308 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
309 309 $ echo change >> n2/b
310 310 $ hg -R n2 ci -A -m local
311 311 $ hg -R n2 fetch -m 'merge' n1
312 312 pulling from n1
313 313 searching for changes
314 314 adding changesets
315 315 adding manifests
316 316 adding file changes
317 317 added 3 changesets with 2 changes to 1 files (+2 heads)
318 318 not merging with 1 other new branch heads (use "hg heads ." and "hg merge" to merge them)
319 319 [1]
320 320
321 321 parent should be 3 (fetch did not merge anything)
322 322
323 323 $ hg -R n2 parents --template '{rev}\n'
324 324 3
325 325 $ rm -fr n1 n2
326 326
327 327 pull in change on different branch than dirstate
328 328
329 329 $ hg init n1
330 330 $ echo a > n1/a
331 331 $ hg -R n1 ci -Am initial
332 332 adding a
333 333 $ hg clone n1 n2
334 334 updating to branch default
335 335 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
336 336 $ echo b > n1/a
337 337 $ hg -R n1 ci -m next
338 338 $ hg -R n2 branch topic
339 339 marked working directory as branch topic
340 340 (branches are permanent and global, did you want a bookmark?)
341 341 $ hg -R n2 fetch -m merge n1
342 342 abort: working dir not at branch tip (use "hg update" to check out branch tip)
343 343 [255]
344 344
345 345 parent should be 0 (fetch did not update or merge anything)
346 346
347 347 $ hg -R n2 parents --template '{rev}\n'
348 348 0
349 349 $ rm -fr n1 n2
350 350
351 351 test fetch with inactive branches
352 352
353 353 $ hg init ib1
354 354 $ echo a > ib1/a
355 355 $ hg --cwd ib1 ci -Am base
356 356 adding a
357 357 $ hg --cwd ib1 branch second
358 358 marked working directory as branch second
359 359 (branches are permanent and global, did you want a bookmark?)
360 360 $ echo b > ib1/b
361 361 $ hg --cwd ib1 ci -Am onsecond
362 362 adding b
363 363 $ hg --cwd ib1 branch -f default
364 364 marked working directory as branch default
365 365 (branches are permanent and global, did you want a bookmark?)
366 366 $ echo c > ib1/c
367 367 $ hg --cwd ib1 ci -Am newdefault
368 368 adding c
369 369 created new head
370 370 $ hg clone ib1 ib2
371 371 updating to branch default
372 372 3 files updated, 0 files merged, 0 files removed, 0 files unresolved
373 373
374 374 fetch should succeed
375 375
376 376 $ hg --cwd ib2 fetch ../ib1
377 377 pulling from ../ib1
378 378 searching for changes
379 379 no changes found
380 380 $ rm -fr ib1 ib2
381 381
382 382 test issue1726
383 383
384 384 $ hg init i1726r1
385 385 $ echo a > i1726r1/a
386 386 $ hg --cwd i1726r1 ci -Am base
387 387 adding a
388 388 $ hg clone i1726r1 i1726r2
389 389 updating to branch default
390 390 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
391 391 $ echo b > i1726r1/a
392 392 $ hg --cwd i1726r1 ci -m second
393 393 $ echo c > i1726r2/a
394 394 $ hg --cwd i1726r2 ci -m third
395 395 $ HGMERGE=true hg --cwd i1726r2 fetch ../i1726r1
396 396 pulling from ../i1726r1
397 397 searching for changes
398 398 adding changesets
399 399 adding manifests
400 400 adding file changes
401 401 added 1 changesets with 1 changes to 1 files (+1 heads)
402 402 updating to 2:7837755a2789
403 403 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
404 404 merging with 1:d1f0c6c48ebd
405 405 merging a
406 406 0 files updated, 1 files merged, 0 files removed, 0 files unresolved
407 407 new changeset 3:* merges remote changes with local (glob)
408 408 $ hg --cwd i1726r2 heads default --template '{rev}\n'
409 409 3
410 410
411 411 test issue2047
412 412
413 413 $ hg -q init i2047a
414 414 $ cd i2047a
415 415 $ echo a > a
416 416 $ hg -q ci -Am a
417 417 $ hg -q branch stable
418 418 $ echo b > b
419 419 $ hg -q ci -Am b
420 420 $ cd ..
421 421 $ hg -q clone -r 0 i2047a i2047b
422 422 $ cd i2047b
423 423 $ hg fetch ../i2047a
424 424 pulling from ../i2047a
425 425 searching for changes
426 426 adding changesets
427 427 adding manifests
428 428 adding file changes
429 429 added 1 changesets with 1 changes to 1 files
430 430
431 431 $ cd ..
General Comments 0
You need to be logged in to leave comments. Login now