annotate contrib/convert-repo @ 1705:4b5725a4a0a6

add changenav at bottom of page if one reads through the changelog and wants to go to the previous or next page one needs the navigation links at the bottom, not at the top of the page
author Johannes Stezenbach <js@linuxtv.org>
date Tue, 07 Feb 2006 23:01:11 -0600
parents 14d73fff4c45
children 40346aa66b0f
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
316
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
1 #!/usr/bin/env python
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
2 #
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
3 # This is a generalized framework for converting between SCM
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
4 # repository formats.
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
5 #
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
6 # In its current form, it's hardcoded to convert incrementally between
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
7 # git and Mercurial.
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
8 #
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
9 # To use, you must first import the first git version into Mercurial,
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
10 # and establish a mapping between the git commit hash and the hash in
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
11 # Mercurial for that version. This mapping is kept in a simple text
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
12 # file with lines like so:
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
13 #
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
14 # <git hash> <mercurial hash>
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
15 #
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
16 # To convert the rest of the repo, run:
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
17 #
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
18 # convert-repo <git-dir> <hg-dir> <mapfile>
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
19 #
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
20 # This updates the mapfile on each commit copied, so it can be
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
21 # interrupted and can be run repeatedly to copy new commits.
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
22
694
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
23 import sys, os, zlib, sha, time
1656
14d73fff4c45 convert-repo: use commit rather than rawcommit
Matt Mackall <mpm@selenic.com>
parents: 1655
diff changeset
24 from mercurial import hg, ui, util, commands
316
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
25
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
26 class convert_git:
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
27 def __init__(self, path):
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
28 self.path = path
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
29
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
30 def getheads(self):
1335
bea6356b8bca git -> hg conversion script
Florian La Roche <laroche@redhat.com>
parents: 1237
diff changeset
31 return [file(self.path + "/HEAD").read()[:-1]]
316
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
32
692
695dd9a491da convert-repo: deal with packed git and other fixes
mpm@selenic.com
parents: 450
diff changeset
33 def catfile(self, rev, type):
695dd9a491da convert-repo: deal with packed git and other fixes
mpm@selenic.com
parents: 450
diff changeset
34 if rev == "0" * 40: raise IOError()
1335
bea6356b8bca git -> hg conversion script
Florian La Roche <laroche@redhat.com>
parents: 1237
diff changeset
35 fh = os.popen("GIT_DIR=%s git-cat-file %s %s 2>/dev/null" % (self.path, type, rev))
692
695dd9a491da convert-repo: deal with packed git and other fixes
mpm@selenic.com
parents: 450
diff changeset
36 return fh.read()
695dd9a491da convert-repo: deal with packed git and other fixes
mpm@selenic.com
parents: 450
diff changeset
37
316
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
38 def getfile(self, name, rev):
692
695dd9a491da convert-repo: deal with packed git and other fixes
mpm@selenic.com
parents: 450
diff changeset
39 return self.catfile(rev, "blob")
316
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
40
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
41 def getchanges(self, version):
1335
bea6356b8bca git -> hg conversion script
Florian La Roche <laroche@redhat.com>
parents: 1237
diff changeset
42 fh = os.popen("GIT_DIR=%s git-diff-tree --root -m -r %s" % (self.path, version))
316
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
43 changes = []
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
44 for l in fh:
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
45 if "\t" not in l: continue
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
46 m, f = l[:-1].split("\t")
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
47 m = m.split()
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
48 h = m[3]
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
49 p = (m[1] == "100755")
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
50 changes.append((f, h, p))
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
51 return changes
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
52
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
53 def getcommit(self, version):
692
695dd9a491da convert-repo: deal with packed git and other fixes
mpm@selenic.com
parents: 450
diff changeset
54 c = self.catfile(version, "commit") # read the commit hash
316
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
55 end = c.find("\n\n")
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
56 message = c[end+2:]
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
57 l = c[:end].splitlines()
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
58 manifest = l[0].split()[1]
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
59 parents = []
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
60 for e in l[1:]:
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
61 n,v = e.split(" ", 1)
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
62 if n == "author":
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
63 p = v.split()
1385
adb3de56635b convert-repo: Fix timezone handling
Matt Mackall <mpm@selenic.com>
parents: 1335
diff changeset
64 tm, tz = p[-2:]
316
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
65 author = " ".join(p[:-2])
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
66 if author[0] == "<": author = author[1:-1]
692
695dd9a491da convert-repo: deal with packed git and other fixes
mpm@selenic.com
parents: 450
diff changeset
67 if n == "committer":
431
dfc44f3f587c convert-repo fixups
mpm@selenic.com
parents: 316
diff changeset
68 p = v.split()
1385
adb3de56635b convert-repo: Fix timezone handling
Matt Mackall <mpm@selenic.com>
parents: 1335
diff changeset
69 tm, tz = p[-2:]
431
dfc44f3f587c convert-repo fixups
mpm@selenic.com
parents: 316
diff changeset
70 committer = " ".join(p[:-2])
dfc44f3f587c convert-repo fixups
mpm@selenic.com
parents: 316
diff changeset
71 if committer[0] == "<": committer = committer[1:-1]
1385
adb3de56635b convert-repo: Fix timezone handling
Matt Mackall <mpm@selenic.com>
parents: 1335
diff changeset
72 message += "\ncommitter: %s\n" % v
316
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
73 if n == "parent": parents.append(v)
1385
adb3de56635b convert-repo: Fix timezone handling
Matt Mackall <mpm@selenic.com>
parents: 1335
diff changeset
74
adb3de56635b convert-repo: Fix timezone handling
Matt Mackall <mpm@selenic.com>
parents: 1335
diff changeset
75 tzs, tzh, tzm = tz[-5:-4] + "1", tz[-4:-2], tz[-2:]
adb3de56635b convert-repo: Fix timezone handling
Matt Mackall <mpm@selenic.com>
parents: 1335
diff changeset
76 tz = int(tzs) * (int(tzh) * 3600 + int(tzm))
adb3de56635b convert-repo: Fix timezone handling
Matt Mackall <mpm@selenic.com>
parents: 1335
diff changeset
77 date = tm + " " + str(tz)
316
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
78 return (parents, author, date, message)
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
79
694
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
80 def gettags(self):
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
81 tags = {}
1335
bea6356b8bca git -> hg conversion script
Florian La Roche <laroche@redhat.com>
parents: 1237
diff changeset
82 for f in os.listdir(self.path + "/refs/tags"):
694
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
83 try:
1335
bea6356b8bca git -> hg conversion script
Florian La Roche <laroche@redhat.com>
parents: 1237
diff changeset
84 h = file(self.path + "/refs/tags/" + f).read().strip()
1386
a1040345fdda convert-repo: retrieve the commit hash from the tag object for tag import
Matt Mackall <mpm@selenic.com>
parents: 1385
diff changeset
85 c = self.catfile(h, "tag") # read the commit hash
a1040345fdda convert-repo: retrieve the commit hash from the tag object for tag import
Matt Mackall <mpm@selenic.com>
parents: 1385
diff changeset
86 h = c.splitlines()[0].split()[1]
1237
227cfbe34109 Fix off by one in convert-repo tags
mason@suse.com
parents: 705
diff changeset
87 tags[f] = h
694
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
88 except:
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
89 pass
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
90 return tags
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
91
316
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
92 class convert_mercurial:
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
93 def __init__(self, path):
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
94 self.path = path
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
95 u = ui.ui()
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
96 self.repo = hg.repository(u, path)
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
97
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
98 def getheads(self):
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
99 h = self.repo.changelog.heads()
1335
bea6356b8bca git -> hg conversion script
Florian La Roche <laroche@redhat.com>
parents: 1237
diff changeset
100 return [ hg.hex(x) for x in h ]
692
695dd9a491da convert-repo: deal with packed git and other fixes
mpm@selenic.com
parents: 450
diff changeset
101
316
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
102 def putfile(self, f, e, data):
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
103 self.repo.wfile(f, "w").write(data)
692
695dd9a491da convert-repo: deal with packed git and other fixes
mpm@selenic.com
parents: 450
diff changeset
104 if self.repo.dirstate.state(f) == '?':
695dd9a491da convert-repo: deal with packed git and other fixes
mpm@selenic.com
parents: 450
diff changeset
105 self.repo.dirstate.update([f], "a")
695dd9a491da convert-repo: deal with packed git and other fixes
mpm@selenic.com
parents: 450
diff changeset
106
450
9d785fd7deec Get set_exec from util in convert_repo
mpm@selenic.com
parents: 431
diff changeset
107 util.set_exec(self.repo.wjoin(f), e)
316
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
108
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
109 def delfile(self, f):
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
110 try:
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
111 os.unlink(self.repo.wjoin(f))
692
695dd9a491da convert-repo: deal with packed git and other fixes
mpm@selenic.com
parents: 450
diff changeset
112 #self.repo.remove([f])
316
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
113 except:
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
114 pass
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
115
1656
14d73fff4c45 convert-repo: use commit rather than rawcommit
Matt Mackall <mpm@selenic.com>
parents: 1655
diff changeset
116 def putcommit(self, files, parents, author, date, text):
431
dfc44f3f587c convert-repo fixups
mpm@selenic.com
parents: 316
diff changeset
117 seen = {}
dfc44f3f587c convert-repo fixups
mpm@selenic.com
parents: 316
diff changeset
118 pl = []
dfc44f3f587c convert-repo fixups
mpm@selenic.com
parents: 316
diff changeset
119 for p in parents:
dfc44f3f587c convert-repo fixups
mpm@selenic.com
parents: 316
diff changeset
120 if p not in seen:
dfc44f3f587c convert-repo fixups
mpm@selenic.com
parents: 316
diff changeset
121 pl.append(p)
dfc44f3f587c convert-repo fixups
mpm@selenic.com
parents: 316
diff changeset
122 seen[p] = 1
dfc44f3f587c convert-repo fixups
mpm@selenic.com
parents: 316
diff changeset
123 parents = pl
316
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
124
692
695dd9a491da convert-repo: deal with packed git and other fixes
mpm@selenic.com
parents: 450
diff changeset
125 if len(parents) < 2: parents.append("0" * 40)
695dd9a491da convert-repo: deal with packed git and other fixes
mpm@selenic.com
parents: 450
diff changeset
126 if len(parents) < 2: parents.append("0" * 40)
431
dfc44f3f587c convert-repo fixups
mpm@selenic.com
parents: 316
diff changeset
127 p2 = parents.pop(0)
692
695dd9a491da convert-repo: deal with packed git and other fixes
mpm@selenic.com
parents: 450
diff changeset
128
431
dfc44f3f587c convert-repo fixups
mpm@selenic.com
parents: 316
diff changeset
129 while parents:
dfc44f3f587c convert-repo fixups
mpm@selenic.com
parents: 316
diff changeset
130 p1 = p2
dfc44f3f587c convert-repo fixups
mpm@selenic.com
parents: 316
diff changeset
131 p2 = parents.pop(0)
1656
14d73fff4c45 convert-repo: use commit rather than rawcommit
Matt Mackall <mpm@selenic.com>
parents: 1655
diff changeset
132 self.repo.dirstate.setparents(hg.bin(p1), hg.bin(p2))
14d73fff4c45 convert-repo: use commit rather than rawcommit
Matt Mackall <mpm@selenic.com>
parents: 1655
diff changeset
133 if len(files) > 0:
14d73fff4c45 convert-repo: use commit rather than rawcommit
Matt Mackall <mpm@selenic.com>
parents: 1655
diff changeset
134 olddir = os.getcwd()
14d73fff4c45 convert-repo: use commit rather than rawcommit
Matt Mackall <mpm@selenic.com>
parents: 1655
diff changeset
135 os.chdir(self.path)
14d73fff4c45 convert-repo: use commit rather than rawcommit
Matt Mackall <mpm@selenic.com>
parents: 1655
diff changeset
136 commands.addremove(self.repo.ui, self.repo, *files)
14d73fff4c45 convert-repo: use commit rather than rawcommit
Matt Mackall <mpm@selenic.com>
parents: 1655
diff changeset
137 os.chdir(olddir)
14d73fff4c45 convert-repo: use commit rather than rawcommit
Matt Mackall <mpm@selenic.com>
parents: 1655
diff changeset
138 self.repo.commit(files, text, author, date)
431
dfc44f3f587c convert-repo fixups
mpm@selenic.com
parents: 316
diff changeset
139 text = "(octopus merge fixup)\n"
1389
9b3ef6f3cef5 convert-repo: fix up octopus merge conversion
Matt Mackall <mpm@selenic.com>
parents: 1388
diff changeset
140 p2 = hg.hex(self.repo.changelog.tip())
431
dfc44f3f587c convert-repo fixups
mpm@selenic.com
parents: 316
diff changeset
141
1389
9b3ef6f3cef5 convert-repo: fix up octopus merge conversion
Matt Mackall <mpm@selenic.com>
parents: 1388
diff changeset
142 return p2
316
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
143
694
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
144 def puttags(self, tags):
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
145 try:
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
146 old = self.repo.wfile(".hgtags").read()
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
147 oldlines = old.splitlines(1)
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
148 oldlines.sort()
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
149 except:
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
150 oldlines = []
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
151
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
152 k = tags.keys()
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
153 k.sort()
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
154 newlines = []
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
155 for tag in k:
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
156 newlines.append("%s %s\n" % (tags[tag], tag))
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
157
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
158 newlines.sort()
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
159
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
160 if newlines != oldlines:
1335
bea6356b8bca git -> hg conversion script
Florian La Roche <laroche@redhat.com>
parents: 1237
diff changeset
161 #print "updating tags"
694
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
162 f = self.repo.wfile(".hgtags", "w")
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
163 f.write("".join(newlines))
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
164 f.close()
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
165 if not oldlines: self.repo.add([".hgtags"])
1335
bea6356b8bca git -> hg conversion script
Florian La Roche <laroche@redhat.com>
parents: 1237
diff changeset
166 date = "%s 0" % int(time.mktime(time.gmtime()))
694
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
167 self.repo.rawcommit([".hgtags"], "update tags", "convert-repo",
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
168 date, self.repo.changelog.tip(), hg.nullid)
1387
0c7e8d345564 convert-repo: linearize the tag commit
Matt Mackall <mpm@selenic.com>
parents: 1386
diff changeset
169 return hg.hex(self.repo.changelog.tip())
694
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
170
316
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
171 class convert:
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
172 def __init__(self, source, dest, mapfile):
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
173 self.source = source
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
174 self.dest = dest
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
175 self.mapfile = mapfile
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
176 self.commitcache = {}
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
177
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
178 self.map = {}
1655
7bfd4724932a convert-repo: automatically create empty map file
Matt Mackall <mpm@selenic.com>
parents: 1389
diff changeset
179 try:
7bfd4724932a convert-repo: automatically create empty map file
Matt Mackall <mpm@selenic.com>
parents: 1389
diff changeset
180 for l in file(self.mapfile):
7bfd4724932a convert-repo: automatically create empty map file
Matt Mackall <mpm@selenic.com>
parents: 1389
diff changeset
181 sv, dv = l[:-1].split()
7bfd4724932a convert-repo: automatically create empty map file
Matt Mackall <mpm@selenic.com>
parents: 1389
diff changeset
182 self.map[sv] = dv
7bfd4724932a convert-repo: automatically create empty map file
Matt Mackall <mpm@selenic.com>
parents: 1389
diff changeset
183 except IOError:
7bfd4724932a convert-repo: automatically create empty map file
Matt Mackall <mpm@selenic.com>
parents: 1389
diff changeset
184 pass
316
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
185
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
186 def walktree(self, heads):
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
187 visit = heads
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
188 known = {}
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
189 parents = {}
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
190 while visit:
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
191 n = visit.pop(0)
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
192 if n in known or n in self.map: continue
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
193 known[n] = 1
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
194 self.commitcache[n] = self.source.getcommit(n)
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
195 cp = self.commitcache[n][0]
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
196 for p in cp:
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
197 parents.setdefault(n, []).append(p)
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
198 visit.append(p)
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
199
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
200 return parents
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
201
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
202 def toposort(self, parents):
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
203 visit = parents.keys()
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
204 seen = {}
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
205 children = {}
692
695dd9a491da convert-repo: deal with packed git and other fixes
mpm@selenic.com
parents: 450
diff changeset
206
316
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
207 while visit:
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
208 n = visit.pop(0)
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
209 if n in seen: continue
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
210 seen[n] = 1
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
211 pc = 0
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
212 if n in parents:
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
213 for p in parents[n]:
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
214 if p not in self.map: pc += 1
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
215 visit.append(p)
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
216 children.setdefault(p, []).append(n)
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
217 if not pc: root = n
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
218
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
219 s = []
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
220 removed = {}
692
695dd9a491da convert-repo: deal with packed git and other fixes
mpm@selenic.com
parents: 450
diff changeset
221 visit = children.keys()
316
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
222 while visit:
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
223 n = visit.pop(0)
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
224 if n in removed: continue
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
225 dep = 0
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
226 if n in parents:
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
227 for p in parents[n]:
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
228 if p in self.map: continue
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
229 if p not in removed:
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
230 # we're still dependent
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
231 visit.append(n)
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
232 dep = 1
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
233 break
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
234
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
235 if not dep:
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
236 # all n's parents are in the list
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
237 removed[n] = 1
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
238 s.append(n)
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
239 if n in children:
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
240 for c in children[n]:
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
241 visit.insert(0, c)
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
242
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
243 return s
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
244
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
245 def copy(self, rev):
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
246 p, a, d, t = self.commitcache[rev]
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
247 files = self.source.getchanges(rev)
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
248
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
249 for f,v,e in files:
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
250 try:
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
251 data = self.source.getfile(f, v)
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
252 except IOError, inst:
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
253 self.dest.delfile(f)
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
254 else:
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
255 self.dest.putfile(f, e, data)
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
256
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
257 r = [self.map[v] for v in p]
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
258 f = [f for f,v,e in files]
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
259 self.map[rev] = self.dest.putcommit(f, r, a, d, t)
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
260 file(self.mapfile, "a").write("%s %s\n" % (rev, self.map[rev]))
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
261
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
262 def convert(self):
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
263 heads = self.source.getheads()
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
264 parents = self.walktree(heads)
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
265 t = self.toposort(parents)
1388
5eb2d3c54165 convert-repo: change duplicate elimination
Matt Mackall <mpm@selenic.com>
parents: 1387
diff changeset
266 t = [n for n in t if n not in self.map]
316
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
267 num = len(t)
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
268
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
269 for c in t:
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
270 num -= 1
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
271 desc = self.commitcache[c][3].splitlines()[0]
1335
bea6356b8bca git -> hg conversion script
Florian La Roche <laroche@redhat.com>
parents: 1237
diff changeset
272 #print num, desc
316
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
273 self.copy(c)
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
274
694
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
275 tags = self.source.gettags()
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
276 ctags = {}
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
277 for k in tags:
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
278 v = tags[k]
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
279 if v in self.map:
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
280 ctags[k] = self.map[v]
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
281
1387
0c7e8d345564 convert-repo: linearize the tag commit
Matt Mackall <mpm@selenic.com>
parents: 1386
diff changeset
282 if ctags:
0c7e8d345564 convert-repo: linearize the tag commit
Matt Mackall <mpm@selenic.com>
parents: 1386
diff changeset
283 nrev = self.dest.puttags(ctags)
0c7e8d345564 convert-repo: linearize the tag commit
Matt Mackall <mpm@selenic.com>
parents: 1386
diff changeset
284 # write another hash correspondence to override the previous
0c7e8d345564 convert-repo: linearize the tag commit
Matt Mackall <mpm@selenic.com>
parents: 1386
diff changeset
285 # one so we don't end up with extra tag heads
0c7e8d345564 convert-repo: linearize the tag commit
Matt Mackall <mpm@selenic.com>
parents: 1386
diff changeset
286 file(self.mapfile, "a").write("%s %s\n" % (c, nrev))
694
51eb248d3348 Teach convert-repo about tags
mpm@selenic.com
parents: 692
diff changeset
287
316
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
288 gitpath, hgpath, mapfile = sys.argv[1:]
1335
bea6356b8bca git -> hg conversion script
Florian La Roche <laroche@redhat.com>
parents: 1237
diff changeset
289 if os.path.isdir(gitpath + "/.git"):
bea6356b8bca git -> hg conversion script
Florian La Roche <laroche@redhat.com>
parents: 1237
diff changeset
290 gitpath += "/.git"
316
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
291
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
292 c = convert(convert_git(gitpath), convert_mercurial(hgpath), mapfile)
c48d069163d6 Add new convert-repo script
mpm@selenic.com
parents:
diff changeset
293 c.convert()