Show More
@@ -29,7 +29,7 b" testedwith = 'internal'" | |||
|
29 | 29 | _('FILE')), |
|
30 | 30 | ('s', 'source-type', '', _('source repository type'), _('TYPE')), |
|
31 | 31 | ('d', 'dest-type', '', _('destination repository type'), _('TYPE')), |
|
32 |
('r', 'rev', |
|
|
32 | ('r', 'rev', [], _('import up to source revision REV'), _('REV')), | |
|
33 | 33 | ('A', 'authormap', '', _('remap usernames using this file'), _('FILE')), |
|
34 | 34 | ('', 'filemap', '', _('remap file names using contents of file'), |
|
35 | 35 | _('FILE')), |
@@ -33,8 +33,8 b" supportedkinds = ('file', 'symlink')" | |||
|
33 | 33 | class bzr_source(converter_source): |
|
34 | 34 | """Reads Bazaar repositories by using the Bazaar Python libraries""" |
|
35 | 35 | |
|
36 | def __init__(self, ui, path, rev=None): | |
|
37 | super(bzr_source, self).__init__(ui, path, rev=rev) | |
|
36 | def __init__(self, ui, path, revs=None): | |
|
37 | super(bzr_source, self).__init__(ui, path, revs=revs) | |
|
38 | 38 | |
|
39 | 39 | if not os.path.exists(os.path.join(path, '.bzr')): |
|
40 | 40 | raise NoRepo(_('%s does not look like a Bazaar repository') |
@@ -95,20 +95,20 b' class bzr_source(converter_source):' | |||
|
95 | 95 | return self.sourcerepo.find_branches(using=True) |
|
96 | 96 | |
|
97 | 97 | def getheads(self): |
|
98 | if not self.rev: | |
|
98 | if not self.revs: | |
|
99 | 99 | # Set using=True to avoid nested repositories (see issue3254) |
|
100 | 100 | heads = sorted([b.last_revision() for b in self._bzrbranches()]) |
|
101 | 101 | else: |
|
102 | 102 | revid = None |
|
103 | 103 | for branch in self._bzrbranches(): |
|
104 | 104 | try: |
|
105 | r = RevisionSpec.from_string(self.rev) | |
|
105 | r = RevisionSpec.from_string(self.revs[0]) | |
|
106 | 106 | info = r.in_history(branch) |
|
107 | 107 | except errors.BzrError: |
|
108 | 108 | pass |
|
109 | 109 | revid = info.rev_id |
|
110 | 110 | if revid is None: |
|
111 | raise util.Abort(_('%s is not a valid revision') % self.rev) | |
|
111 | raise util.Abort(_('%s is not a valid revision') % self.revs[0]) | |
|
112 | 112 | heads = [revid] |
|
113 | 113 | # Empty repositories return 'null:', which cannot be retrieved |
|
114 | 114 | heads = [h for h in heads if h != 'null:'] |
@@ -59,12 +59,12 b' class commit(object):' | |||
|
59 | 59 | class converter_source(object): |
|
60 | 60 | """Conversion source interface""" |
|
61 | 61 | |
|
62 | def __init__(self, ui, path=None, rev=None): | |
|
62 | def __init__(self, ui, path=None, revs=None): | |
|
63 | 63 | """Initialize conversion source (or raise NoRepo("message") |
|
64 | 64 | exception if path is not a valid repository)""" |
|
65 | 65 | self.ui = ui |
|
66 | 66 | self.path = path |
|
67 | self.rev = rev | |
|
67 | self.revs = revs | |
|
68 | 68 | |
|
69 | 69 | self.encoding = 'utf-8' |
|
70 | 70 |
@@ -46,14 +46,14 b' sink_converters = [' | |||
|
46 | 46 | ('svn', svn_sink), |
|
47 | 47 | ] |
|
48 | 48 | |
|
49 | def convertsource(ui, path, type, rev): | |
|
49 | def convertsource(ui, path, type, revs): | |
|
50 | 50 | exceptions = [] |
|
51 | 51 | if type and type not in [s[0] for s in source_converters]: |
|
52 | 52 | raise util.Abort(_('%s: invalid source repository type') % type) |
|
53 | 53 | for name, source, sortmode in source_converters: |
|
54 | 54 | try: |
|
55 | 55 | if not type or name == type: |
|
56 | return source(ui, path, rev), sortmode | |
|
56 | return source(ui, path, revs), sortmode | |
|
57 | 57 | except (NoRepo, MissingTool) as inst: |
|
58 | 58 | exceptions.append(inst) |
|
59 | 59 | if not ui.quiet: |
@@ -15,8 +15,8 b' from common import makedatetimestamp' | |||
|
15 | 15 | import cvsps |
|
16 | 16 | |
|
17 | 17 | class convert_cvs(converter_source): |
|
18 | def __init__(self, ui, path, rev=None): | |
|
19 | super(convert_cvs, self).__init__(ui, path, rev=rev) | |
|
18 | def __init__(self, ui, path, revs=None): | |
|
19 | super(convert_cvs, self).__init__(ui, path, revs=revs) | |
|
20 | 20 | |
|
21 | 21 | cvs = os.path.join(path, "CVS") |
|
22 | 22 | if not os.path.exists(cvs): |
@@ -41,14 +41,17 b' class convert_cvs(converter_source):' | |||
|
41 | 41 | self.changeset = {} |
|
42 | 42 | |
|
43 | 43 | maxrev = 0 |
|
44 | if self.rev: | |
|
44 | if self.revs: | |
|
45 | if len(self.revs) > 1: | |
|
46 | raise util.Abort(_('cvs source does not support specifying ' | |
|
47 | 'multiple revs')) | |
|
45 | 48 | # TODO: handle tags |
|
46 | 49 | try: |
|
47 | 50 | # patchset number? |
|
48 | maxrev = int(self.rev) | |
|
51 | maxrev = int(self.revs[0]) | |
|
49 | 52 | except ValueError: |
|
50 | 53 | raise util.Abort(_('revision %s is not a patchset number') |
|
51 | % self.rev) | |
|
54 | % self.revs[0]) | |
|
52 | 55 | |
|
53 | 56 | d = os.getcwd() |
|
54 | 57 | try: |
@@ -27,8 +27,8 b' except ImportError:' | |||
|
27 | 27 | pass |
|
28 | 28 | |
|
29 | 29 | class darcs_source(converter_source, commandline): |
|
30 | def __init__(self, ui, path, rev=None): | |
|
31 | converter_source.__init__(self, ui, path, rev=rev) | |
|
30 | def __init__(self, ui, path, revs=None): | |
|
31 | converter_source.__init__(self, ui, path, revs=revs) | |
|
32 | 32 | commandline.__init__(self, ui, 'darcs') |
|
33 | 33 | |
|
34 | 34 | # check for _darcs, ElementTree so that we can easily skip |
@@ -86,8 +86,12 b' class convert_git(converter_source):' | |||
|
86 | 86 | data = fh.read() |
|
87 | 87 | return data, fh.close() |
|
88 | 88 | |
|
89 | def __init__(self, ui, path, rev=None): | |
|
90 | super(convert_git, self).__init__(ui, path, rev=rev) | |
|
89 | def __init__(self, ui, path, revs=None): | |
|
90 | super(convert_git, self).__init__(ui, path, revs=revs) | |
|
91 | ||
|
92 | if revs and len(revs) > 1: | |
|
93 | raise util.Abort(_("git source does not support specifying " | |
|
94 | "multiple revs")) | |
|
91 | 95 | |
|
92 | 96 | if os.path.isdir(path + "/.git"): |
|
93 | 97 | path += "/.git" |
@@ -119,11 +123,12 b' class convert_git(converter_source):' | |||
|
119 | 123 | f.close() |
|
120 | 124 | |
|
121 | 125 | def getheads(self): |
|
122 | if not self.rev: | |
|
126 | if not self.revs: | |
|
123 | 127 | heads, ret = self.gitread('git rev-parse --branches --remotes') |
|
124 | 128 | heads = heads.splitlines() |
|
125 | 129 | else: |
|
126 |
heads, ret = self.gitread("git rev-parse --verify %s" % |
|
|
130 | heads, ret = self.gitread("git rev-parse --verify %s" % | |
|
131 | self.revs[0]) | |
|
127 | 132 | heads = [heads[:-1]] |
|
128 | 133 | if ret: |
|
129 | 134 | raise util.Abort(_('cannot retrieve git heads')) |
@@ -27,8 +27,8 b' class gnuarch_source(converter_source, c' | |||
|
27 | 27 | self.ren_files = {} |
|
28 | 28 | self.ren_dirs = {} |
|
29 | 29 | |
|
30 | def __init__(self, ui, path, rev=None): | |
|
31 | super(gnuarch_source, self).__init__(ui, path, rev=rev) | |
|
30 | def __init__(self, ui, path, revs=None): | |
|
31 | super(gnuarch_source, self).__init__(ui, path, revs=revs) | |
|
32 | 32 | |
|
33 | 33 | if not os.path.exists(os.path.join(path, '{arch}')): |
|
34 | 34 | raise NoRepo(_("%s does not look like a GNU Arch repository") |
@@ -372,8 +372,11 b' class mercurial_sink(converter_sink):' | |||
|
372 | 372 | return rev in self.repo |
|
373 | 373 | |
|
374 | 374 | class mercurial_source(converter_source): |
|
375 | def __init__(self, ui, path, rev=None): | |
|
376 | converter_source.__init__(self, ui, path, rev) | |
|
375 | def __init__(self, ui, path, revs=None): | |
|
376 | converter_source.__init__(self, ui, path, revs) | |
|
377 | if revs and len(revs) > 1: | |
|
378 | raise util.Abort(_("mercurial source does not support specifying " | |
|
379 | "multiple revisions")) | |
|
377 | 380 | self.ignoreerrors = ui.configbool('convert', 'hg.ignoreerrors', False) |
|
378 | 381 | self.ignored = set() |
|
379 | 382 | self.saverev = ui.configbool('convert', 'hg.saverev', False) |
@@ -407,12 +410,12 b' class mercurial_source(converter_source)' | |||
|
407 | 410 | self.keep = children.__contains__ |
|
408 | 411 | else: |
|
409 | 412 | self.keep = util.always |
|
410 | if rev: | |
|
411 | self._heads = [self.repo[rev].node()] | |
|
413 | if revs: | |
|
414 | self._heads = [self.repo[revs[0]].node()] | |
|
412 | 415 | else: |
|
413 | 416 | self._heads = self.repo.heads() |
|
414 | 417 | else: |
|
415 | if rev or startnode is not None: | |
|
418 | if revs or startnode is not None: | |
|
416 | 419 | raise util.Abort(_('hg.revs cannot be combined with ' |
|
417 | 420 | 'hg.startrev or --rev')) |
|
418 | 421 | nodes = set() |
@@ -13,14 +13,17 b' from common import commandline' | |||
|
13 | 13 | from mercurial.i18n import _ |
|
14 | 14 | |
|
15 | 15 | class monotone_source(converter_source, commandline): |
|
16 | def __init__(self, ui, path=None, rev=None): | |
|
17 | converter_source.__init__(self, ui, path, rev) | |
|
16 | def __init__(self, ui, path=None, revs=None): | |
|
17 | converter_source.__init__(self, ui, path, revs) | |
|
18 | if revs and len(revs) > 1: | |
|
19 | raise util.Abort(_('monotone source does not support specifying ' | |
|
20 | 'multiple revs')) | |
|
18 | 21 | commandline.__init__(self, ui, 'mtn') |
|
19 | 22 | |
|
20 | 23 | self.ui = ui |
|
21 | 24 | self.path = path |
|
22 | 25 | self.automatestdio = False |
|
23 | self.rev = rev | |
|
26 | self.revs = revs | |
|
24 | 27 | |
|
25 | 28 | norepo = NoRepo(_("%s does not look like a monotone repository") |
|
26 | 29 | % path) |
@@ -219,10 +222,10 b' class monotone_source(converter_source, ' | |||
|
219 | 222 | # implement the converter_source interface: |
|
220 | 223 | |
|
221 | 224 | def getheads(self): |
|
222 | if not self.rev: | |
|
225 | if not self.revs: | |
|
223 | 226 | return self.mtnrun("leaves").splitlines() |
|
224 | 227 | else: |
|
225 |
return |
|
|
228 | return self.revs | |
|
226 | 229 | |
|
227 | 230 | def getchanges(self, rev, full): |
|
228 | 231 | if full: |
@@ -24,8 +24,8 b' def loaditer(f):' | |||
|
24 | 24 | pass |
|
25 | 25 | |
|
26 | 26 | class p4_source(converter_source): |
|
27 | def __init__(self, ui, path, rev=None): | |
|
28 | super(p4_source, self).__init__(ui, path, rev=rev) | |
|
27 | def __init__(self, ui, path, revs=None): | |
|
28 | super(p4_source, self).__init__(ui, path, revs=revs) | |
|
29 | 29 | |
|
30 | 30 | if "/" in path and not path.startswith('//'): |
|
31 | 31 | raise NoRepo(_('%s does not look like a P4 repository') % path) |
@@ -49,6 +49,9 b' class p4_source(converter_source):' | |||
|
49 | 49 | r":[^$\n]*\$") |
|
50 | 50 | self.re_keywords_old = re.compile("\$(Id|Header):[^$\n]*\$") |
|
51 | 51 | |
|
52 | if revs and len(revs) > 1: | |
|
53 | raise util.Abort(_("p4 source does not support specifying " | |
|
54 | "multiple revisions")) | |
|
52 | 55 | self._parse(ui, path) |
|
53 | 56 | |
|
54 | 57 | def _parse_view(self, path): |
@@ -99,7 +102,7 b' class p4_source(converter_source):' | |||
|
99 | 102 | startrev = self.ui.config('convert', 'p4.startrev', default=0) |
|
100 | 103 | self.p4changes = [x for x in self.p4changes |
|
101 | 104 | if ((not startrev or int(x) >= int(startrev)) and |
|
102 | (not self.rev or int(x) <= int(self.rev)))] | |
|
105 | (not self.revs or int(x) <= int(self.revs[0])))] | |
|
103 | 106 | |
|
104 | 107 | # now read the full changelists to get the list of file revisions |
|
105 | 108 | ui.status(_('collecting p4 changelists\n')) |
@@ -268,8 +268,8 b' def issvnurl(ui, url):' | |||
|
268 | 268 | # the parent module. A revision has at most one parent. |
|
269 | 269 | # |
|
270 | 270 | class svn_source(converter_source): |
|
271 | def __init__(self, ui, url, rev=None): | |
|
272 | super(svn_source, self).__init__(ui, url, rev=rev) | |
|
271 | def __init__(self, ui, url, revs=None): | |
|
272 | super(svn_source, self).__init__(ui, url, revs=revs) | |
|
273 | 273 | |
|
274 | 274 | if not (url.startswith('svn://') or url.startswith('svn+ssh://') or |
|
275 | 275 | (os.path.exists(url) and |
@@ -325,11 +325,15 b' class svn_source(converter_source):' | |||
|
325 | 325 | "to libsvn version %s") |
|
326 | 326 | % (self.url, svnversion)) |
|
327 | 327 | |
|
328 | if rev: | |
|
328 | if revs: | |
|
329 | if len(revs) > 1: | |
|
330 | raise util.Abort(_('subversion source does not support ' | |
|
331 | 'specifying multiple revisions')) | |
|
329 | 332 | try: |
|
330 | latest = int(rev) | |
|
333 | latest = int(revs[0]) | |
|
331 | 334 | except ValueError: |
|
332 |
raise util.Abort(_('svn: revision %s is not an integer') % |
|
|
335 | raise util.Abort(_('svn: revision %s is not an integer') % | |
|
336 | revs[0]) | |
|
333 | 337 | |
|
334 | 338 | self.trunkname = self.ui.config('convert', 'svn.trunk', |
|
335 | 339 | 'trunk').strip('/') |
@@ -304,11 +304,11 b'' | |||
|
304 | 304 | does not convert tags from the source repo to the target |
|
305 | 305 | repo. The default is False. |
|
306 | 306 | |
|
307 | options: | |
|
307 | options ([+] can be repeated): | |
|
308 | 308 | |
|
309 | 309 | -s --source-type TYPE source repository type |
|
310 | 310 | -d --dest-type TYPE destination repository type |
|
311 |
-r --rev REV |
|
|
311 | -r --rev REV [+] import up to source revision REV | |
|
312 | 312 | -A --authormap FILE remap usernames using this file |
|
313 | 313 | --filemap FILE remap file names using contents of file |
|
314 | 314 | --full apply filemap changes by converting all files again |
General Comments 0
You need to be logged in to leave comments.
Login now