##// END OF EJS Templates
rebase: do not add second parent to rebased changeset (drop detach option) (BC)...
Pierre-Yves David -
r17005:50f43451 default
parent child Browse files
Show More
@@ -48,8 +48,7 b" testedwith = 'internal'"
48 _('read collapse commit message from file'), _('FILE')),
48 _('read collapse commit message from file'), _('FILE')),
49 ('', 'keep', False, _('keep original changesets')),
49 ('', 'keep', False, _('keep original changesets')),
50 ('', 'keepbranches', False, _('keep original branch names')),
50 ('', 'keepbranches', False, _('keep original branch names')),
51 ('D', 'detach', False, _('force detaching of source from its original '
51 ('D', 'detach', False, _('(DEPRECATED)')),
52 'branch')),
53 ('t', 'tool', '', _('specify merge tool')),
52 ('t', 'tool', '', _('specify merge tool')),
54 ('c', 'continue', False, _('continue an interrupted rebase')),
53 ('c', 'continue', False, _('continue an interrupted rebase')),
55 ('a', 'abort', False, _('abort an interrupted rebase'))] +
54 ('a', 'abort', False, _('abort an interrupted rebase'))] +
@@ -131,7 +130,6 b' def rebase(ui, repo, **opts):'
131 extrafn = opts.get('extrafn') # internal, used by e.g. hgsubversion
130 extrafn = opts.get('extrafn') # internal, used by e.g. hgsubversion
132 keepf = opts.get('keep', False)
131 keepf = opts.get('keep', False)
133 keepbranchesf = opts.get('keepbranches', False)
132 keepbranchesf = opts.get('keepbranches', False)
134 detachf = opts.get('detach', False)
135 # keepopen is not meant for use on the command line, but by
133 # keepopen is not meant for use on the command line, but by
136 # other extensions
134 # other extensions
137 keepopen = opts.get('keepopen', False)
135 keepopen = opts.get('keepopen', False)
@@ -146,8 +144,6 b' def rebase(ui, repo, **opts):'
146 if collapsef:
144 if collapsef:
147 raise util.Abort(
145 raise util.Abort(
148 _('cannot use collapse with continue or abort'))
146 _('cannot use collapse with continue or abort'))
149 if detachf:
150 raise util.Abort(_('cannot use detach with continue or abort'))
151 if srcf or basef or destf:
147 if srcf or basef or destf:
152 raise util.Abort(
148 raise util.Abort(
153 _('abort and continue do not allow specifying revisions'))
149 _('abort and continue do not allow specifying revisions'))
@@ -168,12 +164,6 b' def rebase(ui, repo, **opts):'
168 if revf and srcf:
164 if revf and srcf:
169 raise util.Abort(_('cannot specify both a '
165 raise util.Abort(_('cannot specify both a '
170 'revision and a source'))
166 'revision and a source'))
171 if detachf:
172 if not (srcf or revf):
173 raise util.Abort(
174 _('detach requires a revision to be specified'))
175 if basef:
176 raise util.Abort(_('cannot specify a base with detach'))
177
167
178 cmdutil.bailifchanged(repo)
168 cmdutil.bailifchanged(repo)
179
169
@@ -215,7 +205,7 b' def rebase(ui, repo, **opts):'
215 % repo[root],
205 % repo[root],
216 hint=_('see hg help phases for details'))
206 hint=_('see hg help phases for details'))
217 else:
207 else:
218 result = buildstate(repo, dest, rebaseset, detachf, collapsef)
208 result = buildstate(repo, dest, rebaseset, collapsef)
219
209
220 if not result:
210 if not result:
221 # Empty state built, nothing to rebase
211 # Empty state built, nothing to rebase
@@ -592,13 +582,13 b' def abort(repo, originalwd, target, stat'
592 repo.ui.warn(_('rebase aborted\n'))
582 repo.ui.warn(_('rebase aborted\n'))
593 return 0
583 return 0
594
584
595 def buildstate(repo, dest, rebaseset, detach, collapse):
585 def buildstate(repo, dest, rebaseset, collapse):
596 '''Define which revisions are going to be rebased and where
586 '''Define which revisions are going to be rebased and where
597
587
598 repo: repo
588 repo: repo
599 dest: context
589 dest: context
600 rebaseset: set of rev
590 rebaseset: set of rev
601 detach: boolean'''
591 '''
602
592
603 # This check isn't strictly necessary, since mq detects commits over an
593 # This check isn't strictly necessary, since mq detects commits over an
604 # applied patch. But it prevents messing up the working directory when
594 # applied patch. But it prevents messing up the working directory when
@@ -607,7 +597,6 b' def buildstate(repo, dest, rebaseset, de'
607 [s.node for s in repo.mq.applied]):
597 [s.node for s in repo.mq.applied]):
608 raise util.Abort(_('cannot rebase onto an applied mq patch'))
598 raise util.Abort(_('cannot rebase onto an applied mq patch'))
609
599
610 detachset = set()
611 roots = list(repo.set('roots(%ld)', rebaseset))
600 roots = list(repo.set('roots(%ld)', rebaseset))
612 if not roots:
601 if not roots:
613 raise util.Abort(_('no matching revisions'))
602 raise util.Abort(_('no matching revisions'))
@@ -623,14 +612,50 b' def buildstate(repo, dest, rebaseset, de'
623 if not collapse and samebranch and root in dest.children():
612 if not collapse and samebranch and root in dest.children():
624 repo.ui.debug('source is a child of destination\n')
613 repo.ui.debug('source is a child of destination\n')
625 return None
614 return None
626 # rebase on ancestor, force detach
627 detach = True
628 if detach:
629 detachset = repo.revs('::%d - ::%d - %d', root, commonbase, root)
630
615
631 repo.ui.debug('rebase onto %d starting from %d\n' % (dest, root))
616 repo.ui.debug('rebase onto %d starting from %d\n' % (dest, root))
632 state = dict.fromkeys(rebaseset, nullrev)
617 state = dict.fromkeys(rebaseset, nullrev)
633 state.update(dict.fromkeys(detachset, nullmerge))
618 # Rebase tries to turn <dest> into a parent of <root> while
619 # preserving the number of parents of rebased changesets:
620 #
621 # - A changeset with a single parent will always be rebased as a
622 # changeset with a single parent.
623 #
624 # - A merge will be rebased as merge unless its parents are both
625 # ancestors of <dest> or are themselves in the rebased set and
626 # pruned while rebased.
627 #
628 # If one parent of <root> is an ancestor of <dest>, the rebased
629 # version of this parent will be <dest>. This is always true with
630 # --base option.
631 #
632 # Otherwise, we need to *replace* the original parents with
633 # <dest>. This "detaches" the rebased set from its former location
634 # and rebases it onto <dest>. Changes introduced by ancestors of
635 # <root> not common with <dest> (the detachset, marked as
636 # nullmerge) are "removed" from the rebased changesets.
637 #
638 # - If <root> has a single parent, set it to <dest>.
639 #
640 # - If <root> is a merge, we cannot decide which parent to
641 # replace, the rebase operation is not clearly defined.
642 #
643 # The table below sums up this behavior:
644 #
645 # +--------------------+----------------------+-------------------------+
646 # | | one parent | merge |
647 # +--------------------+----------------------+-------------------------+
648 # | parent in ::<dest> | new parent is <dest> | parents in ::<dest> are |
649 # | | | remapped to <dest> |
650 # +--------------------+----------------------+-------------------------+
651 # | unrelated source | new parent is <dest> | ambiguous, abort |
652 # +--------------------+----------------------+-------------------------+
653 #
654 # The actual abort is handled by `defineparents`
655 if len(root.parents()) <= 1:
656 # (strict) ancestors of <root> not ancestors of <dest>
657 detachset = repo.revs('::%d - ::%d - %d', root, commonbase, root)
658 state.update(dict.fromkeys(detachset, nullmerge))
634 return repo['.'].rev(), dest.rev(), state
659 return repo['.'].rev(), dest.rev(), state
635
660
636 def pullrebase(orig, ui, repo, *args, **opts):
661 def pullrebase(orig, ui, repo, *args, **opts):
@@ -39,11 +39,10 b' rebase'
39 saved backup bundle to $TESTTMP/.hg/strip-backup/*-backup.hg (glob)
39 saved backup bundle to $TESTTMP/.hg/strip-backup/*-backup.hg (glob)
40
40
41 $ hg log
41 $ hg log
42 changeset: 3:9163974d1cb5
42 changeset: 3:42e5ed2cdcf4
43 bookmark: two
43 bookmark: two
44 tag: tip
44 tag: tip
45 parent: 1:925d80f479bb
45 parent: 1:925d80f479bb
46 parent: 2:db815d6d32e6
47 user: test
46 user: test
48 date: Thu Jan 01 00:00:00 1970 +0000
47 date: Thu Jan 01 00:00:00 1970 +0000
49 summary: 3
48 summary: 3
@@ -54,7 +54,7 b' Move only rebased bookmarks'
54 $ cd a1
54 $ cd a1
55 $ hg up -q Z
55 $ hg up -q Z
56
56
57 $ hg rebase --detach -s Y -d 3
57 $ hg rebase -s Y -d 3
58 saved backup bundle to $TESTTMP/a1/.hg/strip-backup/*-backup.hg (glob)
58 saved backup bundle to $TESTTMP/a1/.hg/strip-backup/*-backup.hg (glob)
59
59
60 $ hg tglog
60 $ hg tglog
@@ -104,7 +104,7 b' Rebase part of branch2 (5-6) onto branch'
104 2: 'B' branch1
104 2: 'B' branch1
105 0: 'A'
105 0: 'A'
106
106
107 $ hg rebase --detach -s 5 -d 8
107 $ hg rebase -s 5 -d 8
108 saved backup bundle to $TESTTMP/a1/.hg/strip-backup/*-backup.hg (glob)
108 saved backup bundle to $TESTTMP/a1/.hg/strip-backup/*-backup.hg (glob)
109
109
110 $ hg branches
110 $ hg branches
@@ -165,7 +165,7 b' Rebase head of branch3 (8) onto branch2 '
165 |/
165 |/
166 o 0: 'A'
166 o 0: 'A'
167
167
168 $ hg rebase --detach -s 8 -d 6
168 $ hg rebase -s 8 -d 6
169 saved backup bundle to $TESTTMP/a2/.hg/strip-backup/*-backup.hg (glob)
169 saved backup bundle to $TESTTMP/a2/.hg/strip-backup/*-backup.hg (glob)
170
170
171 $ hg branches
171 $ hg branches
@@ -229,7 +229,7 b' Rebase entire branch3 (7-8) onto branch2'
229 |/
229 |/
230 o 0: 'A'
230 o 0: 'A'
231
231
232 $ hg rebase --detach -s 7 -d 6
232 $ hg rebase -s 7 -d 6
233 saved backup bundle to $TESTTMP/a3/.hg/strip-backup/*-backup.hg (glob)
233 saved backup bundle to $TESTTMP/a3/.hg/strip-backup/*-backup.hg (glob)
234
234
235 $ hg branches
235 $ hg branches
@@ -230,7 +230,7 b' Rebase and collapse - more than one exte'
230
230
231 Rebase and collapse - E onto H:
231 Rebase and collapse - E onto H:
232
232
233 $ hg rebase -s 4 --collapse
233 $ hg rebase -s 4 --collapse # root (4) is not a merge
234 saved backup bundle to $TESTTMP/b1/.hg/strip-backup/*-backup.hg (glob)
234 saved backup bundle to $TESTTMP/b1/.hg/strip-backup/*-backup.hg (glob)
235
235
236 $ hg tglog
236 $ hg tglog
@@ -250,7 +250,6 b' Rebase and collapse - E onto H:'
250
250
251 $ hg manifest
251 $ hg manifest
252 A
252 A
253 B
254 C
253 C
255 D
254 D
256 E
255 E
@@ -340,7 +339,7 b' Rebase and collapse - E onto I:'
340 $ hg clone -q -u . c c1
339 $ hg clone -q -u . c c1
341 $ cd c1
340 $ cd c1
342
341
343 $ hg rebase -s 4 --collapse
342 $ hg rebase -s 4 --collapse # root (4) is not a merge
344 merging E
343 merging E
345 saved backup bundle to $TESTTMP/c1/.hg/strip-backup/*-backup.hg (glob)
344 saved backup bundle to $TESTTMP/c1/.hg/strip-backup/*-backup.hg (glob)
346
345
@@ -362,7 +361,6 b' Rebase and collapse - E onto I:'
362
361
363 $ hg manifest
362 $ hg manifest
364 A
363 A
365 B
366 C
364 C
367 D
365 D
368 E
366 E
@@ -48,7 +48,7 b' Rebasing D onto H detaching from C:'
48 o 0: 'A'
48 o 0: 'A'
49
49
50 $ hg phase --force --secret 3
50 $ hg phase --force --secret 3
51 $ hg rebase --detach -s 3 -d 7
51 $ hg rebase -s 3 -d 7
52 saved backup bundle to $TESTTMP/a1/.hg/strip-backup/*-backup.hg (glob)
52 saved backup bundle to $TESTTMP/a1/.hg/strip-backup/*-backup.hg (glob)
53
53
54 $ hg log -G --template "{rev}:{phase} '{desc}' {branches}\n"
54 $ hg log -G --template "{rev}:{phase} '{desc}' {branches}\n"
@@ -99,7 +99,7 b' Rebasing C onto H detaching from B:'
99 |/
99 |/
100 o 0: 'A'
100 o 0: 'A'
101
101
102 $ hg rebase --detach -s 2 -d 7
102 $ hg rebase -s 2 -d 7
103 saved backup bundle to $TESTTMP/a2/.hg/strip-backup/*-backup.hg (glob)
103 saved backup bundle to $TESTTMP/a2/.hg/strip-backup/*-backup.hg (glob)
104
104
105 $ hg tglog
105 $ hg tglog
@@ -151,7 +151,7 b' Rebasing B onto H using detach (same as '
151 |/
151 |/
152 o 0: 'A'
152 o 0: 'A'
153
153
154 $ hg rebase --detach -s 1 -d 7
154 $ hg rebase -s 1 -d 7
155 saved backup bundle to $TESTTMP/a3/.hg/strip-backup/*-backup.hg (glob)
155 saved backup bundle to $TESTTMP/a3/.hg/strip-backup/*-backup.hg (glob)
156
156
157 $ hg tglog
157 $ hg tglog
@@ -205,7 +205,7 b' Rebasing C onto H detaching from B and c'
205 |/
205 |/
206 o 0: 'A'
206 o 0: 'A'
207
207
208 $ hg rebase --detach --collapse -s 2 -d 7
208 $ hg rebase --collapse -s 2 -d 7
209 saved backup bundle to $TESTTMP/a4/.hg/strip-backup/*-backup.hg (glob)
209 saved backup bundle to $TESTTMP/a4/.hg/strip-backup/*-backup.hg (glob)
210
210
211 $ hg log -G --template "{rev}:{phase} '{desc}' {branches}\n"
211 $ hg log -G --template "{rev}:{phase} '{desc}' {branches}\n"
@@ -264,7 +264,7 b' Rebasing across null as ancestor'
264 |/
264 |/
265 o 0: 'A'
265 o 0: 'A'
266
266
267 $ hg rebase --detach -s 1 -d tip
267 $ hg rebase -s 1 -d tip
268 saved backup bundle to $TESTTMP/a5/.hg/strip-backup/*-backup.hg (glob)
268 saved backup bundle to $TESTTMP/a5/.hg/strip-backup/*-backup.hg (glob)
269
269
270 $ hg tglog
270 $ hg tglog
@@ -325,7 +325,7 b' Verify that target is not selected as ex'
325 $ echo "J" >> F
325 $ echo "J" >> F
326 $ hg ci -m "J"
326 $ hg ci -m "J"
327
327
328 $ hg rebase -s 8 -d 7 --collapse --detach --config ui.merge=internal:other
328 $ hg rebase -s 8 -d 7 --collapse --config ui.merge=internal:other
329 remote changed E which local deleted
329 remote changed E which local deleted
330 use (c)hanged version or leave (d)eleted? c
330 use (c)hanged version or leave (d)eleted? c
331 saved backup bundle to $TESTTMP/a6/.hg/strip-backup/*-backup.hg (glob)
331 saved backup bundle to $TESTTMP/a6/.hg/strip-backup/*-backup.hg (glob)
@@ -370,7 +370,7 b' Ensure --continue restores a correct sta'
370 $ hg ci -A -m 'H2'
370 $ hg ci -A -m 'H2'
371 adding H
371 adding H
372 $ hg phase --force --secret 8
372 $ hg phase --force --secret 8
373 $ hg rebase -s 8 -d 7 --detach --config ui.merge=internal:fail
373 $ hg rebase -s 8 -d 7 --config ui.merge=internal:fail
374 merging H
374 merging H
375 warning: conflicts during merge.
375 warning: conflicts during merge.
376 merging H incomplete! (edit conflicts, then use 'hg resolve --mark')
376 merging H incomplete! (edit conflicts, then use 'hg resolve --mark')
@@ -199,19 +199,19 b' Specify only source (from 2 onto 8):'
199 $ hg tglog
199 $ hg tglog
200 @ 8: 'D'
200 @ 8: 'D'
201 |
201 |
202 o 7: 'C'
202 o 7: 'C'
203 |\
203 |
204 | o 6: 'I'
204 o 6: 'I'
205 | |
205 |
206 | o 5: 'H'
206 o 5: 'H'
207 |
208 | o 4: 'G'
209 |/|
210 o | 3: 'F'
207 | |
211 | |
208 | | o 4: 'G'
212 | o 2: 'E'
209 | |/|
213 |/
210 | o | 3: 'F'
214 | o 1: 'B'
211 | | |
212 | | o 2: 'E'
213 | |/
214 o | 1: 'B'
215 |/
215 |/
216 o 0: 'A'
216 o 0: 'A'
217
217
@@ -283,7 +283,7 b' Specify source and dest (from 2 onto 7):'
283 $ hg clone -q -u . a a7
283 $ hg clone -q -u . a a7
284 $ cd a7
284 $ cd a7
285
285
286 $ hg rebase --detach --source 2 --dest 7
286 $ hg rebase --source 2 --dest 7
287 saved backup bundle to $TESTTMP/a7/.hg/strip-backup/*-backup.hg (glob)
287 saved backup bundle to $TESTTMP/a7/.hg/strip-backup/*-backup.hg (glob)
288
288
289 $ hg tglog
289 $ hg tglog
@@ -349,19 +349,19 b' Specify only revs (from 2 onto 8)'
349 $ hg tglog
349 $ hg tglog
350 @ 8: 'D'
350 @ 8: 'D'
351 |
351 |
352 o 7: 'C'
352 o 7: 'C'
353 |\
353 |
354 | o 6: 'I'
354 o 6: 'I'
355 | |
355 |
356 | o 5: 'H'
356 o 5: 'H'
357 |
358 | o 4: 'G'
359 |/|
360 o | 3: 'F'
357 | |
361 | |
358 | | o 4: 'G'
362 | o 2: 'E'
359 | |/|
363 |/
360 | o | 3: 'F'
364 | o 1: 'B'
361 | | |
362 | | o 2: 'E'
363 | |/
364 o | 1: 'B'
365 |/
365 |/
366 o 0: 'A'
366 o 0: 'A'
367
367
@@ -52,19 +52,19 b' D onto H - simple rebase:'
52 saved backup bundle to $TESTTMP/a1/.hg/strip-backup/*-backup.hg (glob)
52 saved backup bundle to $TESTTMP/a1/.hg/strip-backup/*-backup.hg (glob)
53
53
54 $ hg tglog
54 $ hg tglog
55 @ 7: 'D'
55 @ 7: 'D'
56 |\
56 |
57 | o 6: 'H'
57 o 6: 'H'
58 |
59 | o 5: 'G'
60 |/|
61 o | 4: 'F'
58 | |
62 | |
59 | | o 5: 'G'
63 | o 3: 'E'
60 | |/|
64 |/
61 | o | 4: 'F'
65 | o 2: 'C'
62 | | |
63 | | o 3: 'E'
64 | |/
65 o | 2: 'C'
66 | |
66 | |
67 o | 1: 'B'
67 | o 1: 'B'
68 |/
68 |/
69 o 0: 'A'
69 o 0: 'A'
70
70
@@ -80,19 +80,19 b' D onto F - intermediate point:'
80 saved backup bundle to $TESTTMP/a2/.hg/strip-backup/*-backup.hg (glob)
80 saved backup bundle to $TESTTMP/a2/.hg/strip-backup/*-backup.hg (glob)
81
81
82 $ hg tglog
82 $ hg tglog
83 @ 7: 'D'
83 @ 7: 'D'
84 |\
84 |
85 | | o 6: 'H'
85 | o 6: 'H'
86 | |/
86 |/
87 | | o 5: 'G'
87 | o 5: 'G'
88 | |/|
88 |/|
89 | o | 4: 'F'
89 o | 4: 'F'
90 | | |
91 | | o 3: 'E'
92 | |/
93 o | 2: 'C'
94 | |
90 | |
95 o | 1: 'B'
91 | o 3: 'E'
92 |/
93 | o 2: 'C'
94 | |
95 | o 1: 'B'
96 |/
96 |/
97 o 0: 'A'
97 o 0: 'A'
98
98
@@ -303,9 +303,9 b' Source phase greater or equal to destina'
303 $ hg log --template "{phase}\n" -r 9
303 $ hg log --template "{phase}\n" -r 9
304 secret
304 secret
305 Source phase lower than destination phase: new changeset get the phase of destination:
305 Source phase lower than destination phase: new changeset get the phase of destination:
306 $ hg rebase -s7 -d9
306 $ hg rebase -s8 -d9
307 saved backup bundle to $TESTTMP/a7/.hg/strip-backup/c9659aac0000-backup.hg (glob)
307 saved backup bundle to $TESTTMP/a7/.hg/strip-backup/6d4f22462821-backup.hg
308 $ hg log --template "{phase}\n" -r 9
308 $ hg log --template "{phase}\n" -r 'rev(9)'
309 secret
309 secret
310
310
311 $ cd ..
311 $ cd ..
@@ -404,20 +404,20 b' Base on have one descendant heads we ask'
404 |
404 |
405 o 10: 'G'
405 o 10: 'G'
406 |
406 |
407 o 9: 'D'
407 o 9: 'D'
408 |\
408 |
409 | | o 8: 'I'
409 | o 8: 'I'
410 | | |
410 | |
411 | | o 7: 'H'
411 | o 7: 'H'
412 | |
413 | o 6: 'G'
414 | |
415 | | o 5: 'F'
412 | | |
416 | | |
413 | | o 6: 'G'
417 | | o 4: 'E'
414 | | |
415 | | | o 5: 'F'
416 | | | |
417 | | | o 4: 'E'
418 | | |/
419 | | o 3: 'D'
420 | |/
418 | |/
419 | o 3: 'D'
420 | |
421 | o 2: 'C'
421 | o 2: 'C'
422 | |
422 | |
423 o | 1: 'B'
423 o | 1: 'B'
@@ -441,20 +441,20 b' rebase subset'
441 |
441 |
442 o 10: 'G'
442 o 10: 'G'
443 |
443 |
444 o 9: 'D'
444 o 9: 'D'
445 |\
445 |
446 | | o 8: 'I'
446 | o 8: 'I'
447 | | |
447 | |
448 | | o 7: 'H'
448 | o 7: 'H'
449 | |
450 | o 6: 'G'
451 | |
452 | | o 5: 'F'
449 | | |
453 | | |
450 | | o 6: 'G'
454 | | o 4: 'E'
451 | | |
452 | | | o 5: 'F'
453 | | | |
454 | | | o 4: 'E'
455 | | |/
456 | | o 3: 'D'
457 | |/
455 | |/
456 | o 3: 'D'
457 | |
458 | o 2: 'C'
458 | o 2: 'C'
459 | |
459 | |
460 o | 1: 'B'
460 o | 1: 'B'
@@ -482,20 +482,20 b' rebase subset with multiple head'
482 | |
482 | |
483 | o 10: 'E'
483 | o 10: 'E'
484 |/
484 |/
485 o 9: 'D'
485 o 9: 'D'
486 |\
486 |
487 | | o 8: 'I'
487 | o 8: 'I'
488 | | |
488 | |
489 | | o 7: 'H'
489 | o 7: 'H'
490 | |
491 | o 6: 'G'
492 | |
493 | | o 5: 'F'
490 | | |
494 | | |
491 | | o 6: 'G'
495 | | o 4: 'E'
492 | | |
493 | | | o 5: 'F'
494 | | | |
495 | | | o 4: 'E'
496 | | |/
497 | | o 3: 'D'
498 | |/
496 | |/
497 | o 3: 'D'
498 | |
499 | o 2: 'C'
499 | o 2: 'C'
500 | |
500 | |
501 o | 1: 'B'
501 o | 1: 'B'
General Comments 0
You need to be logged in to leave comments. Login now