annotate hgext/transplant.py @ 11638:79231258503b stable

transplant: crash if repo.commit() finds nothing to commit (makes issue2135, issue2264 more obvious, but does nothing to fix either one) This seems to happen in two distinct cases: * patch.patch() claims success but changes nothing (e.g. the transplanted changeset adds an empty file that already exists) * patch.patch() makes changes, but repo.status() fails to report them Both of these seem like bugs in other parts of Mercurial, so arguably it's not transplant's job to detect the failure to commit. However: * detecting the problem as soon as possible is desirable * it prevents a more obscure crash later, in transplants.write() * there might be other lurking (or future) bugs that cause repo.commit() to do nothing Also, in the case of issue2264 (source changesets silently dropped by transplant), the only way to spot the problem currently is the crash in transplants.write(). Failure to transplant a patch should abort immediately, whether it's user error (patch does not apply) or a Mercurial bug (e.g. repo.status() failing to report changes).
author Greg Ward <greg-hg@gerg.ca>
date Sun, 18 Jul 2010 21:29:29 -0400
parents 5834e79b24f7
children a4fbbe0fbc38
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
1 # Patch transplanting extension for Mercurial
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
2 #
4635
63b9d2deed48 Updated copyright notices and add "and others" to "hg version"
Thomas Arendsen Hein <thomas@intevation.de>
parents: 4516
diff changeset
3 # Copyright 2006, 2007 Brendan Cully <brendan@kublai.com>
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
4 #
8225
46293a0c7e9f updated license to be explicit about GPL version 2
Martin Geisler <mg@lazybytes.net>
parents: 8209
diff changeset
5 # This software may be used and distributed according to the terms of the
10263
25e572394f5c Update license to GPLv2+
Matt Mackall <mpm@selenic.com>
parents: 9995
diff changeset
6 # GNU General Public License version 2 or any later version.
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
7
8934
9dda4c73fc3b extensions: change descriptions for extensions providing a few commands
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 8894
diff changeset
8 '''command to transplant changesets from another branch
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
9
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
10 This extension allows you to transplant patches from another branch.
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
11
8000
83d7c9cfb065 transplant: word-wrap help texts at 70 characters
Martin Geisler <mg@daimi.au.dk>
parents: 7874
diff changeset
12 Transplanted patches are recorded in .hg/transplant/transplants, as a
83d7c9cfb065 transplant: word-wrap help texts at 70 characters
Martin Geisler <mg@daimi.au.dk>
parents: 7874
diff changeset
13 map from a changeset hash to its hash in the source repository.
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
14 '''
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
15
7629
97253bcb44a8 transplant: move docstrings before imports (see issue1466)
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 7415
diff changeset
16 from mercurial.i18n import _
97253bcb44a8 transplant: move docstrings before imports (see issue1466)
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 7415
diff changeset
17 import os, tempfile
8703
8676dd819444 transplant: use match object rather than files for commit
Matt Mackall <mpm@selenic.com>
parents: 8615
diff changeset
18 from mercurial import bundlerepo, changegroup, cmdutil, hg, merge, match
11301
3d0591a66118 move discovery methods from localrepo into new discovery module
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 11193
diff changeset
19 from mercurial import patch, revlog, util, error, discovery
7629
97253bcb44a8 transplant: move docstrings before imports (see issue1466)
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 7415
diff changeset
20
8778
c5f36402daad use new style classes
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 8706
diff changeset
21 class transplantentry(object):
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
22 def __init__(self, lnode, rnode):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
23 self.lnode = lnode
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
24 self.rnode = rnode
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
25
8778
c5f36402daad use new style classes
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 8706
diff changeset
26 class transplants(object):
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
27 def __init__(self, path=None, transplantfile=None, opener=None):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
28 self.path = path
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
29 self.transplantfile = transplantfile
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
30 self.opener = opener
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
31
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
32 if not opener:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
33 self.opener = util.opener(self.path)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
34 self.transplants = []
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
35 self.dirty = False
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
36 self.read()
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
37
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
38 def read(self):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
39 abspath = os.path.join(self.path, self.transplantfile)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
40 if self.transplantfile and os.path.exists(abspath):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
41 for line in self.opener(self.transplantfile).read().splitlines():
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
42 lnode, rnode = map(revlog.bin, line.split(':'))
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
43 self.transplants.append(transplantentry(lnode, rnode))
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
44
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
45 def write(self):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
46 if self.dirty and self.transplantfile:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
47 if not os.path.isdir(self.path):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
48 os.mkdir(self.path)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
49 fp = self.opener(self.transplantfile, 'w')
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
50 for c in self.transplants:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
51 l, r = map(revlog.hex, (c.lnode, c.rnode))
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
52 fp.write(l + ':' + r + '\n')
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
53 fp.close()
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
54 self.dirty = False
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
55
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
56 def get(self, rnode):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
57 return [t for t in self.transplants if t.rnode == rnode]
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
58
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
59 def set(self, lnode, rnode):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
60 self.transplants.append(transplantentry(lnode, rnode))
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
61 self.dirty = True
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
62
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
63 def remove(self, transplant):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
64 del self.transplants[self.transplants.index(transplant)]
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
65 self.dirty = True
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
66
8778
c5f36402daad use new style classes
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 8706
diff changeset
67 class transplanter(object):
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
68 def __init__(self, ui, repo):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
69 self.ui = ui
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
70 self.path = repo.join('transplant')
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
71 self.opener = util.opener(self.path)
7744
b44dbb95f07f transplant: wrapped long lines
Martin Geisler <mg@daimi.au.dk>
parents: 7633
diff changeset
72 self.transplants = transplants(self.path, 'transplants',
b44dbb95f07f transplant: wrapped long lines
Martin Geisler <mg@daimi.au.dk>
parents: 7633
diff changeset
73 opener=self.opener)
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
74
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
75 def applied(self, repo, node, parent):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
76 '''returns True if a node is already an ancestor of parent
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
77 or has already been transplanted'''
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
78 if hasnode(repo, node):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
79 if node in repo.changelog.reachable(parent, stop=node):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
80 return True
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
81 for t in self.transplants.get(node):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
82 # it might have been stripped
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
83 if not hasnode(repo, t.lnode):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
84 self.transplants.remove(t)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
85 return False
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
86 if t.lnode in repo.changelog.reachable(parent, stop=t.lnode):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
87 return True
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
88 return False
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
89
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
90 def apply(self, repo, source, revmap, merges, opts={}):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
91 '''apply the revisions in revmap one by one in revision order'''
8209
a1a5a57efe90 replace util.sort with sorted built-in
Matt Mackall <mpm@selenic.com>
parents: 8176
diff changeset
92 revs = sorted(revmap)
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
93 p1, p2 = repo.dirstate.parents()
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
94 pulls = []
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
95 diffopts = patch.diffopts(self.ui, opts)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
96 diffopts.git = True
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
97
4915
97b734fb9c6f Use try/finally pattern to cleanup locks and transactions
Matt Mackall <mpm@selenic.com>
parents: 4680
diff changeset
98 lock = wlock = None
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
99 try:
4915
97b734fb9c6f Use try/finally pattern to cleanup locks and transactions
Matt Mackall <mpm@selenic.com>
parents: 4680
diff changeset
100 wlock = repo.wlock()
97b734fb9c6f Use try/finally pattern to cleanup locks and transactions
Matt Mackall <mpm@selenic.com>
parents: 4680
diff changeset
101 lock = repo.lock()
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
102 for rev in revs:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
103 node = revmap[rev]
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
104 revstr = '%s:%s' % (rev, revlog.short(node))
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
105
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
106 if self.applied(repo, node, p1):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
107 self.ui.warn(_('skipping already applied revision %s\n') %
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
108 revstr)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
109 continue
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
110
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
111 parents = source.changelog.parents(node)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
112 if not opts.get('filter'):
7744
b44dbb95f07f transplant: wrapped long lines
Martin Geisler <mg@daimi.au.dk>
parents: 7633
diff changeset
113 # If the changeset parent is the same as the
b44dbb95f07f transplant: wrapped long lines
Martin Geisler <mg@daimi.au.dk>
parents: 7633
diff changeset
114 # wdir's parent, just pull it.
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
115 if parents[0] == p1:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
116 pulls.append(node)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
117 p1 = node
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
118 continue
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
119 if pulls:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
120 if source != repo:
4917
126f527b3ba3 Make repo locks recursive, eliminate all passing of lock/wlock
Matt Mackall <mpm@selenic.com>
parents: 4915
diff changeset
121 repo.pull(source, heads=pulls)
126f527b3ba3 Make repo locks recursive, eliminate all passing of lock/wlock
Matt Mackall <mpm@selenic.com>
parents: 4915
diff changeset
122 merge.update(repo, pulls[-1], False, False, None)
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
123 p1, p2 = repo.dirstate.parents()
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
124 pulls = []
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
125
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
126 domerge = False
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
127 if node in merges:
7744
b44dbb95f07f transplant: wrapped long lines
Martin Geisler <mg@daimi.au.dk>
parents: 7633
diff changeset
128 # pulling all the merge revs at once would mean we
b44dbb95f07f transplant: wrapped long lines
Martin Geisler <mg@daimi.au.dk>
parents: 7633
diff changeset
129 # couldn't transplant after the latest even if
b44dbb95f07f transplant: wrapped long lines
Martin Geisler <mg@daimi.au.dk>
parents: 7633
diff changeset
130 # transplants before them fail.
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
131 domerge = True
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
132 if not hasnode(repo, node):
4917
126f527b3ba3 Make repo locks recursive, eliminate all passing of lock/wlock
Matt Mackall <mpm@selenic.com>
parents: 4915
diff changeset
133 repo.pull(source, heads=[node])
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
134
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
135 if parents[1] != revlog.nullid:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
136 self.ui.note(_('skipping merge changeset %s:%s\n')
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
137 % (rev, revlog.short(node)))
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
138 patchfile = None
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
139 else:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
140 fd, patchfile = tempfile.mkstemp(prefix='hg-transplant-')
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
141 fp = os.fdopen(fd, 'w')
7308
b6f5490effbf patch: turn patch.diff() into a generator
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 7280
diff changeset
142 gen = patch.diff(source, parents[0], node, opts=diffopts)
b6f5490effbf patch: turn patch.diff() into a generator
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 7280
diff changeset
143 for chunk in gen:
b6f5490effbf patch: turn patch.diff() into a generator
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 7280
diff changeset
144 fp.write(chunk)
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
145 fp.close()
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
146
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
147 del revmap[rev]
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
148 if patchfile or domerge:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
149 try:
4917
126f527b3ba3 Make repo locks recursive, eliminate all passing of lock/wlock
Matt Mackall <mpm@selenic.com>
parents: 4915
diff changeset
150 n = self.applyone(repo, node,
126f527b3ba3 Make repo locks recursive, eliminate all passing of lock/wlock
Matt Mackall <mpm@selenic.com>
parents: 4915
diff changeset
151 source.changelog.read(node),
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
152 patchfile, merge=domerge,
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
153 log=opts.get('log'),
4917
126f527b3ba3 Make repo locks recursive, eliminate all passing of lock/wlock
Matt Mackall <mpm@selenic.com>
parents: 4915
diff changeset
154 filter=opts.get('filter'))
4251
e76e52145c3d transplant: fix ignoring empty changesets (eg after filter)
Brendan Cully <brendan@kublai.com>
parents: 4072
diff changeset
155 if n and domerge:
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
156 self.ui.status(_('%s merged at %s\n') % (revstr,
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
157 revlog.short(n)))
4251
e76e52145c3d transplant: fix ignoring empty changesets (eg after filter)
Brendan Cully <brendan@kublai.com>
parents: 4072
diff changeset
158 elif n:
7744
b44dbb95f07f transplant: wrapped long lines
Martin Geisler <mg@daimi.au.dk>
parents: 7633
diff changeset
159 self.ui.status(_('%s transplanted to %s\n')
b44dbb95f07f transplant: wrapped long lines
Martin Geisler <mg@daimi.au.dk>
parents: 7633
diff changeset
160 % (revlog.short(node),
b44dbb95f07f transplant: wrapped long lines
Martin Geisler <mg@daimi.au.dk>
parents: 7633
diff changeset
161 revlog.short(n)))
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
162 finally:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
163 if patchfile:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
164 os.unlink(patchfile)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
165 if pulls:
4917
126f527b3ba3 Make repo locks recursive, eliminate all passing of lock/wlock
Matt Mackall <mpm@selenic.com>
parents: 4915
diff changeset
166 repo.pull(source, heads=pulls)
126f527b3ba3 Make repo locks recursive, eliminate all passing of lock/wlock
Matt Mackall <mpm@selenic.com>
parents: 4915
diff changeset
167 merge.update(repo, pulls[-1], False, False, None)
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
168 finally:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
169 self.saveseries(revmap, merges)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
170 self.transplants.write()
8112
6ee71f78497c switch lock releasing in the extensions from gc to explicit
Ronny Pfannschmidt <Ronny.Pfannschmidt@gmx.de>
parents: 8076
diff changeset
171 lock.release()
6ee71f78497c switch lock releasing in the extensions from gc to explicit
Ronny Pfannschmidt <Ronny.Pfannschmidt@gmx.de>
parents: 8076
diff changeset
172 wlock.release()
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
173
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
174 def filter(self, filter, changelog, patchfile):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
175 '''arbitrarily rewrite changeset before applying it'''
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
176
6966
057ced2b8543 i18n: mark strings for translation in transplant extension
Martin Geisler <mg@daimi.au.dk>
parents: 6762
diff changeset
177 self.ui.status(_('filtering %s\n') % patchfile)
3759
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
178 user, date, msg = (changelog[1], changelog[2], changelog[4])
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
179
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
180 fd, headerfile = tempfile.mkstemp(prefix='hg-transplant-')
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
181 fp = os.fdopen(fd, 'w')
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
182 fp.write("# HG changeset patch\n")
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
183 fp.write("# User %s\n" % user)
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
184 fp.write("# Date %d %d\n" % date)
9433
f01a22096f1f transplant: Add trailing LF in tmp file for filtering
Mads Kiilerich <mads@kiilerich.com>
parents: 9183
diff changeset
185 fp.write(msg + '\n')
3759
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
186 fp.close()
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
187
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
188 try:
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
189 util.system('%s %s %s' % (filter, util.shellquote(headerfile),
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
190 util.shellquote(patchfile)),
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
191 environ={'HGUSER': changelog[1]},
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
192 onerr=util.Abort, errprefix=_('filter failed'))
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
193 user, date, msg = self.parselog(file(headerfile))[1:4]
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
194 finally:
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
195 os.unlink(headerfile)
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
196
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
197 return (user, date, msg)
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
198
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
199 def applyone(self, repo, node, cl, patchfile, merge=False, log=False,
4917
126f527b3ba3 Make repo locks recursive, eliminate all passing of lock/wlock
Matt Mackall <mpm@selenic.com>
parents: 4915
diff changeset
200 filter=None):
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
201 '''apply the patch in patchfile to the repository as a transplant'''
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
202 (manifest, user, (time, timezone), files, message) = cl[:5]
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
203 date = "%d %d" % (time, timezone)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
204 extra = {'transplant_source': node}
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
205 if filter:
3759
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
206 (user, date, message) = self.filter(filter, cl, patchfile)
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
207
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
208 if log:
9183
d0225fa2f6c4 do not translate commit messages
Martin Geisler <mg@lazybytes.net>
parents: 8934
diff changeset
209 # we don't translate messages inserted into commits
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
210 message += '\n(transplanted from %s)' % revlog.hex(node)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
211
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
212 self.ui.status(_('applying %s\n') % revlog.short(node))
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
213 self.ui.note('%s %s\n%s\n' % (user, date, message))
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
214
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
215 if not patchfile and not merge:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
216 raise util.Abort(_('can only omit patchfile if merging'))
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
217 if patchfile:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
218 try:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
219 files = {}
3726
752884db5037 transplant: recover added/removed files after failed application
Brendan Cully <brendan@kublai.com>
parents: 3725
diff changeset
220 try:
7874
d812029cda85 cleanup: drop variables for unused return values
Peter Arrenbrecht <peter.arrenbrecht@gmail.com>
parents: 7744
diff changeset
221 patch.patch(patchfile, self.ui, cwd=repo.root,
8811
8b35b08724eb Make mq, record and transplant honor patch.eol
Patrick Mezard <pmezard@gmail.com>
parents: 8778
diff changeset
222 files=files, eolmode=None)
3726
752884db5037 transplant: recover added/removed files after failed application
Brendan Cully <brendan@kublai.com>
parents: 3725
diff changeset
223 if not files:
7744
b44dbb95f07f transplant: wrapped long lines
Martin Geisler <mg@daimi.au.dk>
parents: 7633
diff changeset
224 self.ui.warn(_('%s: empty changeset')
b44dbb95f07f transplant: wrapped long lines
Martin Geisler <mg@daimi.au.dk>
parents: 7633
diff changeset
225 % revlog.hex(node))
4251
e76e52145c3d transplant: fix ignoring empty changesets (eg after filter)
Brendan Cully <brendan@kublai.com>
parents: 4072
diff changeset
226 return None
3726
752884db5037 transplant: recover added/removed files after failed application
Brendan Cully <brendan@kublai.com>
parents: 3725
diff changeset
227 finally:
4917
126f527b3ba3 Make repo locks recursive, eliminate all passing of lock/wlock
Matt Mackall <mpm@selenic.com>
parents: 4915
diff changeset
228 files = patch.updatedir(self.ui, repo, files)
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
229 except Exception, inst:
3757
faed44bab17b transplant: clobber old series when transplant fails
Brendan Cully <brendan@kublai.com>
parents: 3752
diff changeset
230 seriespath = os.path.join(self.path, 'series')
faed44bab17b transplant: clobber old series when transplant fails
Brendan Cully <brendan@kublai.com>
parents: 3752
diff changeset
231 if os.path.exists(seriespath):
faed44bab17b transplant: clobber old series when transplant fails
Brendan Cully <brendan@kublai.com>
parents: 3752
diff changeset
232 os.unlink(seriespath)
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
233 p1 = repo.dirstate.parents()[0]
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
234 p2 = node
3725
ccc7a9eb0e5e transplant: preserve filter changes in --continue log
Brendan Cully <brendan@kublai.com>
parents: 3724
diff changeset
235 self.log(user, date, message, p1, p2, merge=merge)
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
236 self.ui.write(str(inst) + '\n')
7744
b44dbb95f07f transplant: wrapped long lines
Martin Geisler <mg@daimi.au.dk>
parents: 7633
diff changeset
237 raise util.Abort(_('Fix up the merge and run '
b44dbb95f07f transplant: wrapped long lines
Martin Geisler <mg@daimi.au.dk>
parents: 7633
diff changeset
238 'hg transplant --continue'))
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
239 else:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
240 files = None
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
241 if merge:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
242 p1, p2 = repo.dirstate.parents()
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
243 repo.dirstate.setparents(p1, node)
8703
8676dd819444 transplant: use match object rather than files for commit
Matt Mackall <mpm@selenic.com>
parents: 8615
diff changeset
244 m = match.always(repo.root, '')
8676dd819444 transplant: use match object rather than files for commit
Matt Mackall <mpm@selenic.com>
parents: 8615
diff changeset
245 else:
8676dd819444 transplant: use match object rather than files for commit
Matt Mackall <mpm@selenic.com>
parents: 8615
diff changeset
246 m = match.exact(repo.root, '', files)
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
247
8706
25e9c71b89de commit: drop the now-unused files parameter
Matt Mackall <mpm@selenic.com>
parents: 8703
diff changeset
248 n = repo.commit(message, user, date, extra=extra, match=m)
11638
79231258503b transplant: crash if repo.commit() finds nothing to commit
Greg Ward <greg-hg@gerg.ca>
parents: 11411
diff changeset
249 if not n:
79231258503b transplant: crash if repo.commit() finds nothing to commit
Greg Ward <greg-hg@gerg.ca>
parents: 11411
diff changeset
250 # Crash here to prevent an unclear crash later, in
79231258503b transplant: crash if repo.commit() finds nothing to commit
Greg Ward <greg-hg@gerg.ca>
parents: 11411
diff changeset
251 # transplants.write(). This can happen if patch.patch()
79231258503b transplant: crash if repo.commit() finds nothing to commit
Greg Ward <greg-hg@gerg.ca>
parents: 11411
diff changeset
252 # does nothing but claims success or if repo.status() fails
79231258503b transplant: crash if repo.commit() finds nothing to commit
Greg Ward <greg-hg@gerg.ca>
parents: 11411
diff changeset
253 # to report changes done by patch.patch(). These both
79231258503b transplant: crash if repo.commit() finds nothing to commit
Greg Ward <greg-hg@gerg.ca>
parents: 11411
diff changeset
254 # appear to be bugs in other parts of Mercurial, but dying
79231258503b transplant: crash if repo.commit() finds nothing to commit
Greg Ward <greg-hg@gerg.ca>
parents: 11411
diff changeset
255 # here, as soon as we can detect the problem, is preferable
79231258503b transplant: crash if repo.commit() finds nothing to commit
Greg Ward <greg-hg@gerg.ca>
parents: 11411
diff changeset
256 # to silently dropping changesets on the floor.
79231258503b transplant: crash if repo.commit() finds nothing to commit
Greg Ward <greg-hg@gerg.ca>
parents: 11411
diff changeset
257 raise RuntimeError('nothing committed after transplant')
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
258 if not merge:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
259 self.transplants.set(n, node)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
260
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
261 return n
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
262
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
263 def resume(self, repo, source, opts=None):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
264 '''recover last transaction and apply remaining changesets'''
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
265 if os.path.exists(os.path.join(self.path, 'journal')):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
266 n, node = self.recover(repo)
3724
ea523d6f5f1a transplant: fix --continue; add --continue test
Brendan Cully <brendan@kublai.com>
parents: 3723
diff changeset
267 self.ui.status(_('%s transplanted as %s\n') % (revlog.short(node),
ea523d6f5f1a transplant: fix --continue; add --continue test
Brendan Cully <brendan@kublai.com>
parents: 3723
diff changeset
268 revlog.short(n)))
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
269 seriespath = os.path.join(self.path, 'series')
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
270 if not os.path.exists(seriespath):
3758
889f7e74a0d9 transplant: log source node when recovering too.
Brendan Cully <brendan@kublai.com>
parents: 3757
diff changeset
271 self.transplants.write()
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
272 return
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
273 nodes, merges = self.readseries()
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
274 revmap = {}
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
275 for n in nodes:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
276 revmap[source.changelog.rev(n)] = n
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
277 os.unlink(seriespath)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
278
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
279 self.apply(repo, source, revmap, merges, opts)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
280
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
281 def recover(self, repo):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
282 '''commit working directory using journal metadata'''
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
283 node, user, date, message, parents = self.readlog()
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
284 merge = len(parents) == 2
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
285
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
286 if not user or not date or not message or not parents[0]:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
287 raise util.Abort(_('transplant log file is corrupt'))
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
288
3758
889f7e74a0d9 transplant: log source node when recovering too.
Brendan Cully <brendan@kublai.com>
parents: 3757
diff changeset
289 extra = {'transplant_source': node}
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
290 wlock = repo.wlock()
4915
97b734fb9c6f Use try/finally pattern to cleanup locks and transactions
Matt Mackall <mpm@selenic.com>
parents: 4680
diff changeset
291 try:
97b734fb9c6f Use try/finally pattern to cleanup locks and transactions
Matt Mackall <mpm@selenic.com>
parents: 4680
diff changeset
292 p1, p2 = repo.dirstate.parents()
97b734fb9c6f Use try/finally pattern to cleanup locks and transactions
Matt Mackall <mpm@selenic.com>
parents: 4680
diff changeset
293 if p1 != parents[0]:
97b734fb9c6f Use try/finally pattern to cleanup locks and transactions
Matt Mackall <mpm@selenic.com>
parents: 4680
diff changeset
294 raise util.Abort(
97b734fb9c6f Use try/finally pattern to cleanup locks and transactions
Matt Mackall <mpm@selenic.com>
parents: 4680
diff changeset
295 _('working dir not at transplant parent %s') %
97b734fb9c6f Use try/finally pattern to cleanup locks and transactions
Matt Mackall <mpm@selenic.com>
parents: 4680
diff changeset
296 revlog.hex(parents[0]))
97b734fb9c6f Use try/finally pattern to cleanup locks and transactions
Matt Mackall <mpm@selenic.com>
parents: 4680
diff changeset
297 if merge:
97b734fb9c6f Use try/finally pattern to cleanup locks and transactions
Matt Mackall <mpm@selenic.com>
parents: 4680
diff changeset
298 repo.dirstate.setparents(p1, parents[1])
8706
25e9c71b89de commit: drop the now-unused files parameter
Matt Mackall <mpm@selenic.com>
parents: 8703
diff changeset
299 n = repo.commit(message, user, date, extra=extra)
4915
97b734fb9c6f Use try/finally pattern to cleanup locks and transactions
Matt Mackall <mpm@selenic.com>
parents: 4680
diff changeset
300 if not n:
97b734fb9c6f Use try/finally pattern to cleanup locks and transactions
Matt Mackall <mpm@selenic.com>
parents: 4680
diff changeset
301 raise util.Abort(_('commit failed'))
97b734fb9c6f Use try/finally pattern to cleanup locks and transactions
Matt Mackall <mpm@selenic.com>
parents: 4680
diff changeset
302 if not merge:
97b734fb9c6f Use try/finally pattern to cleanup locks and transactions
Matt Mackall <mpm@selenic.com>
parents: 4680
diff changeset
303 self.transplants.set(n, node)
97b734fb9c6f Use try/finally pattern to cleanup locks and transactions
Matt Mackall <mpm@selenic.com>
parents: 4680
diff changeset
304 self.unlog()
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
305
4915
97b734fb9c6f Use try/finally pattern to cleanup locks and transactions
Matt Mackall <mpm@selenic.com>
parents: 4680
diff changeset
306 return n, node
97b734fb9c6f Use try/finally pattern to cleanup locks and transactions
Matt Mackall <mpm@selenic.com>
parents: 4680
diff changeset
307 finally:
8112
6ee71f78497c switch lock releasing in the extensions from gc to explicit
Ronny Pfannschmidt <Ronny.Pfannschmidt@gmx.de>
parents: 8076
diff changeset
308 wlock.release()
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
309
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
310 def readseries(self):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
311 nodes = []
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
312 merges = []
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
313 cur = nodes
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
314 for line in self.opener('series').read().splitlines():
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
315 if line.startswith('# Merges'):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
316 cur = merges
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
317 continue
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
318 cur.append(revlog.bin(line))
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
319
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
320 return (nodes, merges)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
321
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
322 def saveseries(self, revmap, merges):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
323 if not revmap:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
324 return
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
325
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
326 if not os.path.isdir(self.path):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
327 os.mkdir(self.path)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
328 series = self.opener('series', 'w')
8209
a1a5a57efe90 replace util.sort with sorted built-in
Matt Mackall <mpm@selenic.com>
parents: 8176
diff changeset
329 for rev in sorted(revmap):
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
330 series.write(revlog.hex(revmap[rev]) + '\n')
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
331 if merges:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
332 series.write('# Merges\n')
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
333 for m in merges:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
334 series.write(revlog.hex(m) + '\n')
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
335 series.close()
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
336
3759
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
337 def parselog(self, fp):
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
338 parents = []
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
339 message = []
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
340 node = revlog.nullid
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
341 inmsg = False
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
342 for line in fp.read().splitlines():
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
343 if inmsg:
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
344 message.append(line)
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
345 elif line.startswith('# User '):
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
346 user = line[7:]
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
347 elif line.startswith('# Date '):
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
348 date = line[7:]
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
349 elif line.startswith('# Node ID '):
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
350 node = revlog.bin(line[10:])
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
351 elif line.startswith('# Parent '):
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
352 parents.append(revlog.bin(line[9:]))
11411
5834e79b24f7 transplant: when reading journal, treat only lines starting with "# " special like patch.extract() does
Georg Brandl <georg@python.org>
parents: 11321
diff changeset
353 elif not line.startswith('# '):
3759
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
354 inmsg = True
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
355 message.append(line)
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
356 return (node, user, date, '\n'.join(message), parents)
4516
96d8a56d4ef9 Removed trailing whitespace and tabs from python files
Thomas Arendsen Hein <thomas@intevation.de>
parents: 4251
diff changeset
357
3725
ccc7a9eb0e5e transplant: preserve filter changes in --continue log
Brendan Cully <brendan@kublai.com>
parents: 3724
diff changeset
358 def log(self, user, date, message, p1, p2, merge=False):
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
359 '''journal changelog metadata for later recover'''
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
360
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
361 if not os.path.isdir(self.path):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
362 os.mkdir(self.path)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
363 fp = self.opener('journal', 'w')
3725
ccc7a9eb0e5e transplant: preserve filter changes in --continue log
Brendan Cully <brendan@kublai.com>
parents: 3724
diff changeset
364 fp.write('# User %s\n' % user)
ccc7a9eb0e5e transplant: preserve filter changes in --continue log
Brendan Cully <brendan@kublai.com>
parents: 3724
diff changeset
365 fp.write('# Date %s\n' % date)
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
366 fp.write('# Node ID %s\n' % revlog.hex(p2))
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
367 fp.write('# Parent ' + revlog.hex(p1) + '\n')
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
368 if merge:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
369 fp.write('# Parent ' + revlog.hex(p2) + '\n')
3725
ccc7a9eb0e5e transplant: preserve filter changes in --continue log
Brendan Cully <brendan@kublai.com>
parents: 3724
diff changeset
370 fp.write(message.rstrip() + '\n')
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
371 fp.close()
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
372
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
373 def readlog(self):
3759
e96f97ca0358 transplant: split filter args into changelog entry and patch
Brendan Cully <brendan@kublai.com>
parents: 3758
diff changeset
374 return self.parselog(self.opener('journal'))
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
375
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
376 def unlog(self):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
377 '''remove changelog journal'''
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
378 absdst = os.path.join(self.path, 'journal')
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
379 if os.path.exists(absdst):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
380 os.unlink(absdst)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
381
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
382 def transplantfilter(self, repo, source, root):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
383 def matchfn(node):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
384 if self.applied(repo, node, root):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
385 return False
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
386 if source.changelog.parents(node)[1] != revlog.nullid:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
387 return False
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
388 extra = source.changelog.read(node)[5]
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
389 cnode = extra.get('transplant_source')
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
390 if cnode and self.applied(repo, cnode, root):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
391 return False
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
392 return True
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
393
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
394 return matchfn
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
395
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
396 def hasnode(repo, node):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
397 try:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
398 return repo.changelog.rev(node) != None
7633
08cabecfa8a8 errors: move revlog errors
Matt Mackall <mpm@selenic.com>
parents: 7629
diff changeset
399 except error.RevlogError:
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
400 return False
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
401
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
402 def browserevs(ui, repo, nodes, opts):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
403 '''interactively transplant changesets'''
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
404 def browsehelp(ui):
10510
f77f3383c666 i18n: mark more strings for translation
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 10394
diff changeset
405 ui.write(_('y: transplant this changeset\n'
f77f3383c666 i18n: mark more strings for translation
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 10394
diff changeset
406 'n: skip this changeset\n'
f77f3383c666 i18n: mark more strings for translation
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 10394
diff changeset
407 'm: merge at this changeset\n'
f77f3383c666 i18n: mark more strings for translation
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 10394
diff changeset
408 'p: show patch\n'
f77f3383c666 i18n: mark more strings for translation
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 10394
diff changeset
409 'c: commit selected changesets\n'
f77f3383c666 i18n: mark more strings for translation
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 10394
diff changeset
410 'q: cancel transplant\n'
f77f3383c666 i18n: mark more strings for translation
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 10394
diff changeset
411 '?: show this help\n'))
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
412
3723
c828fca6f38a transplant: show_changeset moved to cmdutil
Brendan Cully <brendan@kublai.com>
parents: 3714
diff changeset
413 displayer = cmdutil.show_changeset(ui, repo, opts)
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
414 transplants = []
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
415 merges = []
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
416 for node in nodes:
7369
87158be081b8 cmdutil: use change contexts for cset-printer and cset-templater
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 7308
diff changeset
417 displayer.show(repo[node])
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
418 action = None
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
419 while not action:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
420 action = ui.prompt(_('apply changeset? [ynmpcq?]:'))
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
421 if action == '?':
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
422 browsehelp(ui)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
423 action = None
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
424 elif action == 'p':
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
425 parent = repo.changelog.parents(node)[0]
7308
b6f5490effbf patch: turn patch.diff() into a generator
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 7280
diff changeset
426 for chunk in patch.diff(repo, parent, node):
8615
94ca38e63576 use ui instead of repo.ui when the former is in scope
Martin Geisler <mg@lazybytes.net>
parents: 8225
diff changeset
427 ui.write(chunk)
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
428 action = None
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
429 elif action not in ('y', 'n', 'm', 'c', 'q'):
10510
f77f3383c666 i18n: mark more strings for translation
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 10394
diff changeset
430 ui.write(_('no such option\n'))
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
431 action = None
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
432 if action == 'y':
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
433 transplants.append(node)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
434 elif action == 'm':
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
435 merges.append(node)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
436 elif action == 'c':
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
437 break
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
438 elif action == 'q':
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
439 transplants = ()
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
440 merges = ()
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
441 break
10152
56284451a22c Added support for templatevar "footer" to cmdutil.py
Robert Bachmann <rbachm@gmail.com>
parents: 9995
diff changeset
442 displayer.close()
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
443 return (transplants, merges)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
444
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
445 def transplant(ui, repo, *revs, **opts):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
446 '''transplant changesets from another branch
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
447
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
448 Selected changesets will be applied on top of the current working
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
449 directory with the log of the original changeset. If --log is
9274
4e61abab5f4b transplant: wrap docstrings at 70 characters
Martin Geisler <mg@lazybytes.net>
parents: 9200
diff changeset
450 specified, log messages will have a comment appended of the form::
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
451
9200
6b4c527c3d22 transplant: better reST formatting
Martin Geisler <mg@lazybytes.net>
parents: 9196
diff changeset
452 (transplanted from CHANGESETHASH)
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
453
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
454 You can rewrite the changelog message with the --filter option.
8000
83d7c9cfb065 transplant: word-wrap help texts at 70 characters
Martin Geisler <mg@daimi.au.dk>
parents: 7874
diff changeset
455 Its argument will be invoked with the current changelog message as
83d7c9cfb065 transplant: word-wrap help texts at 70 characters
Martin Geisler <mg@daimi.au.dk>
parents: 7874
diff changeset
456 $1 and the patch as $2.
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
457
8076
5ec526c1a32f help texts: write command line switches as -a/--abc
Martin Geisler <mg@lazybytes.net>
parents: 8000
diff changeset
458 If --source/-s is specified, selects changesets from the named
5ec526c1a32f help texts: write command line switches as -a/--abc
Martin Geisler <mg@lazybytes.net>
parents: 8000
diff changeset
459 repository. If --branch/-b is specified, selects changesets from
5ec526c1a32f help texts: write command line switches as -a/--abc
Martin Geisler <mg@lazybytes.net>
parents: 8000
diff changeset
460 the branch holding the named revision, up to that revision. If
5ec526c1a32f help texts: write command line switches as -a/--abc
Martin Geisler <mg@lazybytes.net>
parents: 8000
diff changeset
461 --all/-a is specified, all changesets on the branch will be
5ec526c1a32f help texts: write command line switches as -a/--abc
Martin Geisler <mg@lazybytes.net>
parents: 8000
diff changeset
462 transplanted, otherwise you will be prompted to select the
5ec526c1a32f help texts: write command line switches as -a/--abc
Martin Geisler <mg@lazybytes.net>
parents: 8000
diff changeset
463 changesets you want.
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
464
11193
687c7d395f20 Use our custom hg reStructuredText role some more
Martin Geisler <mg@aragost.com>
parents: 10510
diff changeset
465 :hg:`transplant --branch REVISION --all` will rebase the selected
8000
83d7c9cfb065 transplant: word-wrap help texts at 70 characters
Martin Geisler <mg@daimi.au.dk>
parents: 7874
diff changeset
466 branch (up to the named revision) onto your current working
83d7c9cfb065 transplant: word-wrap help texts at 70 characters
Martin Geisler <mg@daimi.au.dk>
parents: 7874
diff changeset
467 directory.
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
468
8000
83d7c9cfb065 transplant: word-wrap help texts at 70 characters
Martin Geisler <mg@daimi.au.dk>
parents: 7874
diff changeset
469 You can optionally mark selected transplanted changesets as merge
83d7c9cfb065 transplant: word-wrap help texts at 70 characters
Martin Geisler <mg@daimi.au.dk>
parents: 7874
diff changeset
470 changesets. You will not be prompted to transplant any ancestors
83d7c9cfb065 transplant: word-wrap help texts at 70 characters
Martin Geisler <mg@daimi.au.dk>
parents: 7874
diff changeset
471 of a merged transplant, and you can merge descendants of them
83d7c9cfb065 transplant: word-wrap help texts at 70 characters
Martin Geisler <mg@daimi.au.dk>
parents: 7874
diff changeset
472 normally instead of transplanting them.
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
473
11193
687c7d395f20 Use our custom hg reStructuredText role some more
Martin Geisler <mg@aragost.com>
parents: 10510
diff changeset
474 If no merges or revisions are provided, :hg:`transplant` will
687c7d395f20 Use our custom hg reStructuredText role some more
Martin Geisler <mg@aragost.com>
parents: 10510
diff changeset
475 start an interactive changeset browser.
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
476
8000
83d7c9cfb065 transplant: word-wrap help texts at 70 characters
Martin Geisler <mg@daimi.au.dk>
parents: 7874
diff changeset
477 If a changeset application fails, you can fix the merge by hand
11193
687c7d395f20 Use our custom hg reStructuredText role some more
Martin Geisler <mg@aragost.com>
parents: 10510
diff changeset
478 and then resume where you left off by calling :hg:`transplant
687c7d395f20 Use our custom hg reStructuredText role some more
Martin Geisler <mg@aragost.com>
parents: 10510
diff changeset
479 --continue/-c`.
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
480 '''
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
481 def getremotechanges(repo, url):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
482 sourcerepo = ui.expandpath(url)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
483 source = hg.repository(ui, sourcerepo)
11301
3d0591a66118 move discovery methods from localrepo into new discovery module
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 11193
diff changeset
484 tmp = discovery.findcommonincoming(repo, source, force=True)
3d0591a66118 move discovery methods from localrepo into new discovery module
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 11193
diff changeset
485 common, incoming, rheads = tmp
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
486 if not incoming:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
487 return (source, None, None)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
488
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
489 bundle = None
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
490 if not source.local():
7415
6163ef936a00 protocol: use changegroupsubset() if possible (issue1389)
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 7369
diff changeset
491 if source.capable('changegroupsubset'):
6163ef936a00 protocol: use changegroupsubset() if possible (issue1389)
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 7369
diff changeset
492 cg = source.changegroupsubset(incoming, rheads, 'incoming')
6163ef936a00 protocol: use changegroupsubset() if possible (issue1389)
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 7369
diff changeset
493 else:
6163ef936a00 protocol: use changegroupsubset() if possible (issue1389)
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 7369
diff changeset
494 cg = source.changegroup(incoming, 'incoming')
4049
863465381028 transplant: update to current writebundle API
Brendan Cully <brendan@kublai.com>
parents: 4035
diff changeset
495 bundle = changegroup.writebundle(cg, None, 'HG10UN')
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
496 source = bundlerepo.bundlerepository(ui, repo.root, bundle)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
497
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
498 return (source, incoming, bundle)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
499
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
500 def incwalk(repo, incoming, branches, match=util.always):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
501 if not branches:
10282
08a0f04b56bd many, many trivial check-code fixups
Matt Mackall <mpm@selenic.com>
parents: 10264
diff changeset
502 branches = None
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
503 for node in repo.changelog.nodesbetween(incoming, branches)[0]:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
504 if match(node):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
505 yield node
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
506
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
507 def transplantwalk(repo, root, branches, match=util.always):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
508 if not branches:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
509 branches = repo.heads()
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
510 ancestors = []
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
511 for branch in branches:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
512 ancestors.append(repo.changelog.ancestor(root, branch))
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
513 for node in repo.changelog.nodesbetween(ancestors, branches)[0]:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
514 if match(node):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
515 yield node
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
516
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
517 def checkopts(opts, revs):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
518 if opts.get('continue'):
10282
08a0f04b56bd many, many trivial check-code fixups
Matt Mackall <mpm@selenic.com>
parents: 10264
diff changeset
519 if opts.get('branch') or opts.get('all') or opts.get('merge'):
7744
b44dbb95f07f transplant: wrapped long lines
Martin Geisler <mg@daimi.au.dk>
parents: 7633
diff changeset
520 raise util.Abort(_('--continue is incompatible with '
b44dbb95f07f transplant: wrapped long lines
Martin Geisler <mg@daimi.au.dk>
parents: 7633
diff changeset
521 'branch, all or merge'))
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
522 return
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
523 if not (opts.get('source') or revs or
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
524 opts.get('merge') or opts.get('branch')):
7744
b44dbb95f07f transplant: wrapped long lines
Martin Geisler <mg@daimi.au.dk>
parents: 7633
diff changeset
525 raise util.Abort(_('no source URL, branch tag or revision '
b44dbb95f07f transplant: wrapped long lines
Martin Geisler <mg@daimi.au.dk>
parents: 7633
diff changeset
526 'list provided'))
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
527 if opts.get('all'):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
528 if not opts.get('branch'):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
529 raise util.Abort(_('--all requires a branch revision'))
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
530 if revs:
7744
b44dbb95f07f transplant: wrapped long lines
Martin Geisler <mg@daimi.au.dk>
parents: 7633
diff changeset
531 raise util.Abort(_('--all is incompatible with a '
b44dbb95f07f transplant: wrapped long lines
Martin Geisler <mg@daimi.au.dk>
parents: 7633
diff changeset
532 'revision list'))
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
533
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
534 checkopts(opts, revs)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
535
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
536 if not opts.get('log'):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
537 opts['log'] = ui.config('transplant', 'log')
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
538 if not opts.get('filter'):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
539 opts['filter'] = ui.config('transplant', 'filter')
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
540
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
541 tp = transplanter(ui, repo)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
542
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
543 p1, p2 = repo.dirstate.parents()
8176
2660e7002413 transplant: forbid transplant to nonempty repositories with no working directory.
Brendan Cully <brendan@kublai.com>
parents: 8173
diff changeset
544 if len(repo) > 0 and p1 == revlog.nullid:
2660e7002413 transplant: forbid transplant to nonempty repositories with no working directory.
Brendan Cully <brendan@kublai.com>
parents: 8173
diff changeset
545 raise util.Abort(_('no revision checked out'))
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
546 if not opts.get('continue'):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
547 if p2 != revlog.nullid:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
548 raise util.Abort(_('outstanding uncommitted merges'))
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
549 m, a, r, d = repo.status()[:4]
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
550 if m or a or r or d:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
551 raise util.Abort(_('outstanding local changes'))
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
552
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
553 bundle = None
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
554 source = opts.get('source')
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
555 if source:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
556 (source, incoming, bundle) = getremotechanges(repo, source)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
557 else:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
558 source = repo
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
559
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
560 try:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
561 if opts.get('continue'):
3724
ea523d6f5f1a transplant: fix --continue; add --continue test
Brendan Cully <brendan@kublai.com>
parents: 3723
diff changeset
562 tp.resume(repo, source, opts)
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
563 return
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
564
10394
4612cded5176 fix coding style (reported by pylint)
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 10282
diff changeset
565 tf = tp.transplantfilter(repo, source, p1)
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
566 if opts.get('prune'):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
567 prune = [source.lookup(r)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
568 for r in cmdutil.revrange(source, opts.get('prune'))]
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
569 matchfn = lambda x: tf(x) and x not in prune
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
570 else:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
571 matchfn = tf
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
572 branches = map(source.lookup, opts.get('branch', ()))
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
573 merges = map(source.lookup, opts.get('merge', ()))
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
574 revmap = {}
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
575 if revs:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
576 for r in cmdutil.revrange(source, revs):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
577 revmap[int(r)] = source.lookup(r)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
578 elif opts.get('all') or not merges:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
579 if source != repo:
7744
b44dbb95f07f transplant: wrapped long lines
Martin Geisler <mg@daimi.au.dk>
parents: 7633
diff changeset
580 alltransplants = incwalk(source, incoming, branches,
b44dbb95f07f transplant: wrapped long lines
Martin Geisler <mg@daimi.au.dk>
parents: 7633
diff changeset
581 match=matchfn)
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
582 else:
7744
b44dbb95f07f transplant: wrapped long lines
Martin Geisler <mg@daimi.au.dk>
parents: 7633
diff changeset
583 alltransplants = transplantwalk(source, p1, branches,
b44dbb95f07f transplant: wrapped long lines
Martin Geisler <mg@daimi.au.dk>
parents: 7633
diff changeset
584 match=matchfn)
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
585 if opts.get('all'):
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
586 revs = alltransplants
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
587 else:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
588 revs, newmerges = browserevs(ui, source, alltransplants, opts)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
589 merges.extend(newmerges)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
590 for r in revs:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
591 revmap[source.changelog.rev(r)] = r
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
592 for r in merges:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
593 revmap[source.changelog.rev(r)] = r
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
594
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
595 tp.apply(repo, source, revmap, merges, opts)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
596 finally:
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
597 if bundle:
4072
e916bc0dfdd6 transplant: remote bundle source was not closed before deleting the fetched bundle.
Patrick Mezard <pmezard@gmail.com>
parents: 4049
diff changeset
598 source.close()
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
599 os.unlink(bundle)
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
600
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
601 cmdtable = {
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
602 "transplant":
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
603 (transplant,
11321
40c06bbf58be help: show value requirement and multiple occurrence of options
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 11301
diff changeset
604 [('s', 'source', '',
40c06bbf58be help: show value requirement and multiple occurrence of options
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 11301
diff changeset
605 _('pull patches from REPO'), _('REPO')),
40c06bbf58be help: show value requirement and multiple occurrence of options
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 11301
diff changeset
606 ('b', 'branch', [],
40c06bbf58be help: show value requirement and multiple occurrence of options
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 11301
diff changeset
607 _('pull patches from branch BRANCH'), _('BRANCH')),
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
608 ('a', 'all', None, _('pull all changesets up to BRANCH')),
11321
40c06bbf58be help: show value requirement and multiple occurrence of options
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 11301
diff changeset
609 ('p', 'prune', [],
40c06bbf58be help: show value requirement and multiple occurrence of options
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 11301
diff changeset
610 _('skip over REV'), _('REV')),
40c06bbf58be help: show value requirement and multiple occurrence of options
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 11301
diff changeset
611 ('m', 'merge', [],
40c06bbf58be help: show value requirement and multiple occurrence of options
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 11301
diff changeset
612 _('merge at REV'), _('REV')),
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
613 ('', 'log', None, _('append transplant info to log message')),
7744
b44dbb95f07f transplant: wrapped long lines
Martin Geisler <mg@daimi.au.dk>
parents: 7633
diff changeset
614 ('c', 'continue', None, _('continue last transplant session '
b44dbb95f07f transplant: wrapped long lines
Martin Geisler <mg@daimi.au.dk>
parents: 7633
diff changeset
615 'after repair')),
11321
40c06bbf58be help: show value requirement and multiple occurrence of options
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 11301
diff changeset
616 ('', 'filter', '',
40c06bbf58be help: show value requirement and multiple occurrence of options
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 11301
diff changeset
617 _('filter changesets through command'), _('CMD'))],
40c06bbf58be help: show value requirement and multiple occurrence of options
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 11301
diff changeset
618 _('hg transplant [-s REPO] [-b BRANCH [-a]] [-p REV] '
7744
b44dbb95f07f transplant: wrapped long lines
Martin Geisler <mg@daimi.au.dk>
parents: 7633
diff changeset
619 '[-m REV] [REV]...'))
3714
198173f3957c Add transplant extension
Brendan Cully <brendan@kublai.com>
parents:
diff changeset
620 }