##// END OF EJS Templates
changelog: fix readpending if no pending data exist (issue4609)...
Pierre-Yves David -
r24822:8678b1ea stable
parent child Browse files
Show More
@@ -1,385 +1,387 b''
1 # changelog.py - changelog class for mercurial
1 # changelog.py - changelog class for mercurial
2 #
2 #
3 # Copyright 2005-2007 Matt Mackall <mpm@selenic.com>
3 # Copyright 2005-2007 Matt Mackall <mpm@selenic.com>
4 #
4 #
5 # This software may be used and distributed according to the terms of the
5 # This software may be used and distributed according to the terms of the
6 # GNU General Public License version 2 or any later version.
6 # GNU General Public License version 2 or any later version.
7
7
8 from node import bin, hex, nullid
8 from node import bin, hex, nullid
9 from i18n import _
9 from i18n import _
10 import util, error, revlog, encoding
10 import util, error, revlog, encoding
11
11
12 _defaultextra = {'branch': 'default'}
12 _defaultextra = {'branch': 'default'}
13
13
14 def _string_escape(text):
14 def _string_escape(text):
15 """
15 """
16 >>> d = {'nl': chr(10), 'bs': chr(92), 'cr': chr(13), 'nul': chr(0)}
16 >>> d = {'nl': chr(10), 'bs': chr(92), 'cr': chr(13), 'nul': chr(0)}
17 >>> s = "ab%(nl)scd%(bs)s%(bs)sn%(nul)sab%(cr)scd%(bs)s%(nl)s" % d
17 >>> s = "ab%(nl)scd%(bs)s%(bs)sn%(nul)sab%(cr)scd%(bs)s%(nl)s" % d
18 >>> s
18 >>> s
19 'ab\\ncd\\\\\\\\n\\x00ab\\rcd\\\\\\n'
19 'ab\\ncd\\\\\\\\n\\x00ab\\rcd\\\\\\n'
20 >>> res = _string_escape(s)
20 >>> res = _string_escape(s)
21 >>> s == res.decode('string_escape')
21 >>> s == res.decode('string_escape')
22 True
22 True
23 """
23 """
24 # subset of the string_escape codec
24 # subset of the string_escape codec
25 text = text.replace('\\', '\\\\').replace('\n', '\\n').replace('\r', '\\r')
25 text = text.replace('\\', '\\\\').replace('\n', '\\n').replace('\r', '\\r')
26 return text.replace('\0', '\\0')
26 return text.replace('\0', '\\0')
27
27
28 def decodeextra(text):
28 def decodeextra(text):
29 """
29 """
30 >>> sorted(decodeextra(encodeextra({'foo': 'bar', 'baz': chr(0) + '2'})
30 >>> sorted(decodeextra(encodeextra({'foo': 'bar', 'baz': chr(0) + '2'})
31 ... ).iteritems())
31 ... ).iteritems())
32 [('baz', '\\x002'), ('branch', 'default'), ('foo', 'bar')]
32 [('baz', '\\x002'), ('branch', 'default'), ('foo', 'bar')]
33 >>> sorted(decodeextra(encodeextra({'foo': 'bar',
33 >>> sorted(decodeextra(encodeextra({'foo': 'bar',
34 ... 'baz': chr(92) + chr(0) + '2'})
34 ... 'baz': chr(92) + chr(0) + '2'})
35 ... ).iteritems())
35 ... ).iteritems())
36 [('baz', '\\\\\\x002'), ('branch', 'default'), ('foo', 'bar')]
36 [('baz', '\\\\\\x002'), ('branch', 'default'), ('foo', 'bar')]
37 """
37 """
38 extra = _defaultextra.copy()
38 extra = _defaultextra.copy()
39 for l in text.split('\0'):
39 for l in text.split('\0'):
40 if l:
40 if l:
41 if '\\0' in l:
41 if '\\0' in l:
42 # fix up \0 without getting into trouble with \\0
42 # fix up \0 without getting into trouble with \\0
43 l = l.replace('\\\\', '\\\\\n')
43 l = l.replace('\\\\', '\\\\\n')
44 l = l.replace('\\0', '\0')
44 l = l.replace('\\0', '\0')
45 l = l.replace('\n', '')
45 l = l.replace('\n', '')
46 k, v = l.decode('string_escape').split(':', 1)
46 k, v = l.decode('string_escape').split(':', 1)
47 extra[k] = v
47 extra[k] = v
48 return extra
48 return extra
49
49
50 def encodeextra(d):
50 def encodeextra(d):
51 # keys must be sorted to produce a deterministic changelog entry
51 # keys must be sorted to produce a deterministic changelog entry
52 items = [_string_escape('%s:%s' % (k, d[k])) for k in sorted(d)]
52 items = [_string_escape('%s:%s' % (k, d[k])) for k in sorted(d)]
53 return "\0".join(items)
53 return "\0".join(items)
54
54
55 def stripdesc(desc):
55 def stripdesc(desc):
56 """strip trailing whitespace and leading and trailing empty lines"""
56 """strip trailing whitespace and leading and trailing empty lines"""
57 return '\n'.join([l.rstrip() for l in desc.splitlines()]).strip('\n')
57 return '\n'.join([l.rstrip() for l in desc.splitlines()]).strip('\n')
58
58
59 class appender(object):
59 class appender(object):
60 '''the changelog index must be updated last on disk, so we use this class
60 '''the changelog index must be updated last on disk, so we use this class
61 to delay writes to it'''
61 to delay writes to it'''
62 def __init__(self, vfs, name, mode, buf):
62 def __init__(self, vfs, name, mode, buf):
63 self.data = buf
63 self.data = buf
64 fp = vfs(name, mode)
64 fp = vfs(name, mode)
65 self.fp = fp
65 self.fp = fp
66 self.offset = fp.tell()
66 self.offset = fp.tell()
67 self.size = vfs.fstat(fp).st_size
67 self.size = vfs.fstat(fp).st_size
68
68
69 def end(self):
69 def end(self):
70 return self.size + len("".join(self.data))
70 return self.size + len("".join(self.data))
71 def tell(self):
71 def tell(self):
72 return self.offset
72 return self.offset
73 def flush(self):
73 def flush(self):
74 pass
74 pass
75 def close(self):
75 def close(self):
76 self.fp.close()
76 self.fp.close()
77
77
78 def seek(self, offset, whence=0):
78 def seek(self, offset, whence=0):
79 '''virtual file offset spans real file and data'''
79 '''virtual file offset spans real file and data'''
80 if whence == 0:
80 if whence == 0:
81 self.offset = offset
81 self.offset = offset
82 elif whence == 1:
82 elif whence == 1:
83 self.offset += offset
83 self.offset += offset
84 elif whence == 2:
84 elif whence == 2:
85 self.offset = self.end() + offset
85 self.offset = self.end() + offset
86 if self.offset < self.size:
86 if self.offset < self.size:
87 self.fp.seek(self.offset)
87 self.fp.seek(self.offset)
88
88
89 def read(self, count=-1):
89 def read(self, count=-1):
90 '''only trick here is reads that span real file and data'''
90 '''only trick here is reads that span real file and data'''
91 ret = ""
91 ret = ""
92 if self.offset < self.size:
92 if self.offset < self.size:
93 s = self.fp.read(count)
93 s = self.fp.read(count)
94 ret = s
94 ret = s
95 self.offset += len(s)
95 self.offset += len(s)
96 if count > 0:
96 if count > 0:
97 count -= len(s)
97 count -= len(s)
98 if count != 0:
98 if count != 0:
99 doff = self.offset - self.size
99 doff = self.offset - self.size
100 self.data.insert(0, "".join(self.data))
100 self.data.insert(0, "".join(self.data))
101 del self.data[1:]
101 del self.data[1:]
102 s = self.data[0][doff:doff + count]
102 s = self.data[0][doff:doff + count]
103 self.offset += len(s)
103 self.offset += len(s)
104 ret += s
104 ret += s
105 return ret
105 return ret
106
106
107 def write(self, s):
107 def write(self, s):
108 self.data.append(str(s))
108 self.data.append(str(s))
109 self.offset += len(s)
109 self.offset += len(s)
110
110
111 def _divertopener(opener, target):
111 def _divertopener(opener, target):
112 """build an opener that writes in 'target.a' instead of 'target'"""
112 """build an opener that writes in 'target.a' instead of 'target'"""
113 def _divert(name, mode='r'):
113 def _divert(name, mode='r'):
114 if name != target:
114 if name != target:
115 return opener(name, mode)
115 return opener(name, mode)
116 return opener(name + ".a", mode)
116 return opener(name + ".a", mode)
117 return _divert
117 return _divert
118
118
119 def _delayopener(opener, target, buf):
119 def _delayopener(opener, target, buf):
120 """build an opener that stores chunks in 'buf' instead of 'target'"""
120 """build an opener that stores chunks in 'buf' instead of 'target'"""
121 def _delay(name, mode='r'):
121 def _delay(name, mode='r'):
122 if name != target:
122 if name != target:
123 return opener(name, mode)
123 return opener(name, mode)
124 return appender(opener, name, mode, buf)
124 return appender(opener, name, mode, buf)
125 return _delay
125 return _delay
126
126
127 class changelog(revlog.revlog):
127 class changelog(revlog.revlog):
128 def __init__(self, opener):
128 def __init__(self, opener):
129 revlog.revlog.__init__(self, opener, "00changelog.i")
129 revlog.revlog.__init__(self, opener, "00changelog.i")
130 if self._initempty:
130 if self._initempty:
131 # changelogs don't benefit from generaldelta
131 # changelogs don't benefit from generaldelta
132 self.version &= ~revlog.REVLOGGENERALDELTA
132 self.version &= ~revlog.REVLOGGENERALDELTA
133 self._generaldelta = False
133 self._generaldelta = False
134 self._realopener = opener
134 self._realopener = opener
135 self._delayed = False
135 self._delayed = False
136 self._delaybuf = None
136 self._delaybuf = None
137 self._divert = False
137 self._divert = False
138 self.filteredrevs = frozenset()
138 self.filteredrevs = frozenset()
139
139
140 def tip(self):
140 def tip(self):
141 """filtered version of revlog.tip"""
141 """filtered version of revlog.tip"""
142 for i in xrange(len(self) -1, -2, -1):
142 for i in xrange(len(self) -1, -2, -1):
143 if i not in self.filteredrevs:
143 if i not in self.filteredrevs:
144 return self.node(i)
144 return self.node(i)
145
145
146 def __contains__(self, rev):
146 def __contains__(self, rev):
147 """filtered version of revlog.__contains__"""
147 """filtered version of revlog.__contains__"""
148 return (0 <= rev < len(self)
148 return (0 <= rev < len(self)
149 and rev not in self.filteredrevs)
149 and rev not in self.filteredrevs)
150
150
151 def __iter__(self):
151 def __iter__(self):
152 """filtered version of revlog.__iter__"""
152 """filtered version of revlog.__iter__"""
153 if len(self.filteredrevs) == 0:
153 if len(self.filteredrevs) == 0:
154 return revlog.revlog.__iter__(self)
154 return revlog.revlog.__iter__(self)
155
155
156 def filterediter():
156 def filterediter():
157 for i in xrange(len(self)):
157 for i in xrange(len(self)):
158 if i not in self.filteredrevs:
158 if i not in self.filteredrevs:
159 yield i
159 yield i
160
160
161 return filterediter()
161 return filterediter()
162
162
163 def revs(self, start=0, stop=None):
163 def revs(self, start=0, stop=None):
164 """filtered version of revlog.revs"""
164 """filtered version of revlog.revs"""
165 for i in super(changelog, self).revs(start, stop):
165 for i in super(changelog, self).revs(start, stop):
166 if i not in self.filteredrevs:
166 if i not in self.filteredrevs:
167 yield i
167 yield i
168
168
169 @util.propertycache
169 @util.propertycache
170 def nodemap(self):
170 def nodemap(self):
171 # XXX need filtering too
171 # XXX need filtering too
172 self.rev(self.node(0))
172 self.rev(self.node(0))
173 return self._nodecache
173 return self._nodecache
174
174
175 def hasnode(self, node):
175 def hasnode(self, node):
176 """filtered version of revlog.hasnode"""
176 """filtered version of revlog.hasnode"""
177 try:
177 try:
178 i = self.rev(node)
178 i = self.rev(node)
179 return i not in self.filteredrevs
179 return i not in self.filteredrevs
180 except KeyError:
180 except KeyError:
181 return False
181 return False
182
182
183 def headrevs(self):
183 def headrevs(self):
184 if self.filteredrevs:
184 if self.filteredrevs:
185 try:
185 try:
186 return self.index.headrevsfiltered(self.filteredrevs)
186 return self.index.headrevsfiltered(self.filteredrevs)
187 # AttributeError covers non-c-extension environments and
187 # AttributeError covers non-c-extension environments and
188 # old c extensions without filter handling.
188 # old c extensions without filter handling.
189 except AttributeError:
189 except AttributeError:
190 return self._headrevs()
190 return self._headrevs()
191
191
192 return super(changelog, self).headrevs()
192 return super(changelog, self).headrevs()
193
193
194 def strip(self, *args, **kwargs):
194 def strip(self, *args, **kwargs):
195 # XXX make something better than assert
195 # XXX make something better than assert
196 # We can't expect proper strip behavior if we are filtered.
196 # We can't expect proper strip behavior if we are filtered.
197 assert not self.filteredrevs
197 assert not self.filteredrevs
198 super(changelog, self).strip(*args, **kwargs)
198 super(changelog, self).strip(*args, **kwargs)
199
199
200 def rev(self, node):
200 def rev(self, node):
201 """filtered version of revlog.rev"""
201 """filtered version of revlog.rev"""
202 r = super(changelog, self).rev(node)
202 r = super(changelog, self).rev(node)
203 if r in self.filteredrevs:
203 if r in self.filteredrevs:
204 raise error.FilteredLookupError(hex(node), self.indexfile,
204 raise error.FilteredLookupError(hex(node), self.indexfile,
205 _('filtered node'))
205 _('filtered node'))
206 return r
206 return r
207
207
208 def node(self, rev):
208 def node(self, rev):
209 """filtered version of revlog.node"""
209 """filtered version of revlog.node"""
210 if rev in self.filteredrevs:
210 if rev in self.filteredrevs:
211 raise error.FilteredIndexError(rev)
211 raise error.FilteredIndexError(rev)
212 return super(changelog, self).node(rev)
212 return super(changelog, self).node(rev)
213
213
214 def linkrev(self, rev):
214 def linkrev(self, rev):
215 """filtered version of revlog.linkrev"""
215 """filtered version of revlog.linkrev"""
216 if rev in self.filteredrevs:
216 if rev in self.filteredrevs:
217 raise error.FilteredIndexError(rev)
217 raise error.FilteredIndexError(rev)
218 return super(changelog, self).linkrev(rev)
218 return super(changelog, self).linkrev(rev)
219
219
220 def parentrevs(self, rev):
220 def parentrevs(self, rev):
221 """filtered version of revlog.parentrevs"""
221 """filtered version of revlog.parentrevs"""
222 if rev in self.filteredrevs:
222 if rev in self.filteredrevs:
223 raise error.FilteredIndexError(rev)
223 raise error.FilteredIndexError(rev)
224 return super(changelog, self).parentrevs(rev)
224 return super(changelog, self).parentrevs(rev)
225
225
226 def flags(self, rev):
226 def flags(self, rev):
227 """filtered version of revlog.flags"""
227 """filtered version of revlog.flags"""
228 if rev in self.filteredrevs:
228 if rev in self.filteredrevs:
229 raise error.FilteredIndexError(rev)
229 raise error.FilteredIndexError(rev)
230 return super(changelog, self).flags(rev)
230 return super(changelog, self).flags(rev)
231
231
232 def delayupdate(self, tr):
232 def delayupdate(self, tr):
233 "delay visibility of index updates to other readers"
233 "delay visibility of index updates to other readers"
234
234
235 if not self._delayed:
235 if not self._delayed:
236 if len(self) == 0:
236 if len(self) == 0:
237 self._divert = True
237 self._divert = True
238 if self._realopener.exists(self.indexfile + '.a'):
238 if self._realopener.exists(self.indexfile + '.a'):
239 self._realopener.unlink(self.indexfile + '.a')
239 self._realopener.unlink(self.indexfile + '.a')
240 self.opener = _divertopener(self._realopener, self.indexfile)
240 self.opener = _divertopener(self._realopener, self.indexfile)
241 else:
241 else:
242 self._delaybuf = []
242 self._delaybuf = []
243 self.opener = _delayopener(self._realopener, self.indexfile,
243 self.opener = _delayopener(self._realopener, self.indexfile,
244 self._delaybuf)
244 self._delaybuf)
245 self._delayed = True
245 self._delayed = True
246 tr.addpending('cl-%i' % id(self), self._writepending)
246 tr.addpending('cl-%i' % id(self), self._writepending)
247 tr.addfinalize('cl-%i' % id(self), self._finalize)
247 tr.addfinalize('cl-%i' % id(self), self._finalize)
248
248
249 def _finalize(self, tr):
249 def _finalize(self, tr):
250 "finalize index updates"
250 "finalize index updates"
251 self._delayed = False
251 self._delayed = False
252 self.opener = self._realopener
252 self.opener = self._realopener
253 # move redirected index data back into place
253 # move redirected index data back into place
254 if self._divert:
254 if self._divert:
255 assert not self._delaybuf
255 assert not self._delaybuf
256 tmpname = self.indexfile + ".a"
256 tmpname = self.indexfile + ".a"
257 nfile = self.opener.open(tmpname)
257 nfile = self.opener.open(tmpname)
258 nfile.close()
258 nfile.close()
259 self.opener.rename(tmpname, self.indexfile)
259 self.opener.rename(tmpname, self.indexfile)
260 elif self._delaybuf:
260 elif self._delaybuf:
261 fp = self.opener(self.indexfile, 'a')
261 fp = self.opener(self.indexfile, 'a')
262 fp.write("".join(self._delaybuf))
262 fp.write("".join(self._delaybuf))
263 fp.close()
263 fp.close()
264 self._delaybuf = None
264 self._delaybuf = None
265 self._divert = False
265 self._divert = False
266 # split when we're done
266 # split when we're done
267 self.checkinlinesize(tr)
267 self.checkinlinesize(tr)
268
268
269 def readpending(self, file):
269 def readpending(self, file):
270 if not self.opener.exists(file):
271 return # no pending data for changelog
270 r = revlog.revlog(self.opener, file)
272 r = revlog.revlog(self.opener, file)
271 self.index = r.index
273 self.index = r.index
272 self.nodemap = r.nodemap
274 self.nodemap = r.nodemap
273 self._nodecache = r._nodecache
275 self._nodecache = r._nodecache
274 self._chunkcache = r._chunkcache
276 self._chunkcache = r._chunkcache
275
277
276 def _writepending(self, tr):
278 def _writepending(self, tr):
277 "create a file containing the unfinalized state for pretxnchangegroup"
279 "create a file containing the unfinalized state for pretxnchangegroup"
278 if self._delaybuf:
280 if self._delaybuf:
279 # make a temporary copy of the index
281 # make a temporary copy of the index
280 fp1 = self._realopener(self.indexfile)
282 fp1 = self._realopener(self.indexfile)
281 pendingfilename = self.indexfile + ".a"
283 pendingfilename = self.indexfile + ".a"
282 # register as a temp file to ensure cleanup on failure
284 # register as a temp file to ensure cleanup on failure
283 tr.registertmp(pendingfilename)
285 tr.registertmp(pendingfilename)
284 # write existing data
286 # write existing data
285 fp2 = self._realopener(pendingfilename, "w")
287 fp2 = self._realopener(pendingfilename, "w")
286 fp2.write(fp1.read())
288 fp2.write(fp1.read())
287 # add pending data
289 # add pending data
288 fp2.write("".join(self._delaybuf))
290 fp2.write("".join(self._delaybuf))
289 fp2.close()
291 fp2.close()
290 # switch modes so finalize can simply rename
292 # switch modes so finalize can simply rename
291 self._delaybuf = None
293 self._delaybuf = None
292 self._divert = True
294 self._divert = True
293 self.opener = _divertopener(self._realopener, self.indexfile)
295 self.opener = _divertopener(self._realopener, self.indexfile)
294
296
295 if self._divert:
297 if self._divert:
296 return True
298 return True
297
299
298 return False
300 return False
299
301
300 def checkinlinesize(self, tr, fp=None):
302 def checkinlinesize(self, tr, fp=None):
301 if not self._delayed:
303 if not self._delayed:
302 revlog.revlog.checkinlinesize(self, tr, fp)
304 revlog.revlog.checkinlinesize(self, tr, fp)
303
305
304 def read(self, node):
306 def read(self, node):
305 """
307 """
306 format used:
308 format used:
307 nodeid\n : manifest node in ascii
309 nodeid\n : manifest node in ascii
308 user\n : user, no \n or \r allowed
310 user\n : user, no \n or \r allowed
309 time tz extra\n : date (time is int or float, timezone is int)
311 time tz extra\n : date (time is int or float, timezone is int)
310 : extra is metadata, encoded and separated by '\0'
312 : extra is metadata, encoded and separated by '\0'
311 : older versions ignore it
313 : older versions ignore it
312 files\n\n : files modified by the cset, no \n or \r allowed
314 files\n\n : files modified by the cset, no \n or \r allowed
313 (.*) : comment (free text, ideally utf-8)
315 (.*) : comment (free text, ideally utf-8)
314
316
315 changelog v0 doesn't use extra
317 changelog v0 doesn't use extra
316 """
318 """
317 text = self.revision(node)
319 text = self.revision(node)
318 if not text:
320 if not text:
319 return (nullid, "", (0, 0), [], "", _defaultextra)
321 return (nullid, "", (0, 0), [], "", _defaultextra)
320 last = text.index("\n\n")
322 last = text.index("\n\n")
321 desc = encoding.tolocal(text[last + 2:])
323 desc = encoding.tolocal(text[last + 2:])
322 l = text[:last].split('\n')
324 l = text[:last].split('\n')
323 manifest = bin(l[0])
325 manifest = bin(l[0])
324 user = encoding.tolocal(l[1])
326 user = encoding.tolocal(l[1])
325
327
326 tdata = l[2].split(' ', 2)
328 tdata = l[2].split(' ', 2)
327 if len(tdata) != 3:
329 if len(tdata) != 3:
328 time = float(tdata[0])
330 time = float(tdata[0])
329 try:
331 try:
330 # various tools did silly things with the time zone field.
332 # various tools did silly things with the time zone field.
331 timezone = int(tdata[1])
333 timezone = int(tdata[1])
332 except ValueError:
334 except ValueError:
333 timezone = 0
335 timezone = 0
334 extra = _defaultextra
336 extra = _defaultextra
335 else:
337 else:
336 time, timezone = float(tdata[0]), int(tdata[1])
338 time, timezone = float(tdata[0]), int(tdata[1])
337 extra = decodeextra(tdata[2])
339 extra = decodeextra(tdata[2])
338
340
339 files = l[3:]
341 files = l[3:]
340 return (manifest, user, (time, timezone), files, desc, extra)
342 return (manifest, user, (time, timezone), files, desc, extra)
341
343
342 def add(self, manifest, files, desc, transaction, p1, p2,
344 def add(self, manifest, files, desc, transaction, p1, p2,
343 user, date=None, extra=None):
345 user, date=None, extra=None):
344 # Convert to UTF-8 encoded bytestrings as the very first
346 # Convert to UTF-8 encoded bytestrings as the very first
345 # thing: calling any method on a localstr object will turn it
347 # thing: calling any method on a localstr object will turn it
346 # into a str object and the cached UTF-8 string is thus lost.
348 # into a str object and the cached UTF-8 string is thus lost.
347 user, desc = encoding.fromlocal(user), encoding.fromlocal(desc)
349 user, desc = encoding.fromlocal(user), encoding.fromlocal(desc)
348
350
349 user = user.strip()
351 user = user.strip()
350 # An empty username or a username with a "\n" will make the
352 # An empty username or a username with a "\n" will make the
351 # revision text contain two "\n\n" sequences -> corrupt
353 # revision text contain two "\n\n" sequences -> corrupt
352 # repository since read cannot unpack the revision.
354 # repository since read cannot unpack the revision.
353 if not user:
355 if not user:
354 raise error.RevlogError(_("empty username"))
356 raise error.RevlogError(_("empty username"))
355 if "\n" in user:
357 if "\n" in user:
356 raise error.RevlogError(_("username %s contains a newline")
358 raise error.RevlogError(_("username %s contains a newline")
357 % repr(user))
359 % repr(user))
358
360
359 desc = stripdesc(desc)
361 desc = stripdesc(desc)
360
362
361 if date:
363 if date:
362 parseddate = "%d %d" % util.parsedate(date)
364 parseddate = "%d %d" % util.parsedate(date)
363 else:
365 else:
364 parseddate = "%d %d" % util.makedate()
366 parseddate = "%d %d" % util.makedate()
365 if extra:
367 if extra:
366 branch = extra.get("branch")
368 branch = extra.get("branch")
367 if branch in ("default", ""):
369 if branch in ("default", ""):
368 del extra["branch"]
370 del extra["branch"]
369 elif branch in (".", "null", "tip"):
371 elif branch in (".", "null", "tip"):
370 raise error.RevlogError(_('the name \'%s\' is reserved')
372 raise error.RevlogError(_('the name \'%s\' is reserved')
371 % branch)
373 % branch)
372 if extra:
374 if extra:
373 extra = encodeextra(extra)
375 extra = encodeextra(extra)
374 parseddate = "%s %s" % (parseddate, extra)
376 parseddate = "%s %s" % (parseddate, extra)
375 l = [hex(manifest), user, parseddate] + sorted(files) + ["", desc]
377 l = [hex(manifest), user, parseddate] + sorted(files) + ["", desc]
376 text = "\n".join(l)
378 text = "\n".join(l)
377 return self.addrevision(text, transaction, len(self), p1, p2)
379 return self.addrevision(text, transaction, len(self), p1, p2)
378
380
379 def branchinfo(self, rev):
381 def branchinfo(self, rev):
380 """return the branch name and open/close state of a revision
382 """return the branch name and open/close state of a revision
381
383
382 This function exists because creating a changectx object
384 This function exists because creating a changectx object
383 just to access this is costly."""
385 just to access this is costly."""
384 extra = self.read(rev)[5]
386 extra = self.read(rev)[5]
385 return encoding.tolocal(extra.get("branch")), 'close' in extra
387 return encoding.tolocal(extra.get("branch")), 'close' in extra
@@ -1,602 +1,602 b''
1 Test exchange of common information using bundle2
1 Test exchange of common information using bundle2
2
2
3
3
4 $ getmainid() {
4 $ getmainid() {
5 > hg -R main log --template '{node}\n' --rev "$1"
5 > hg -R main log --template '{node}\n' --rev "$1"
6 > }
6 > }
7
7
8 enable obsolescence
8 enable obsolescence
9
9
10 $ cat > $TESTTMP/bundle2-pushkey-hook.sh << EOF
10 $ cat > $TESTTMP/bundle2-pushkey-hook.sh << EOF
11 > echo pushkey: lock state after \"\$HG_NAMESPACE\"
11 > echo pushkey: lock state after \"\$HG_NAMESPACE\"
12 > hg debuglock
12 > hg debuglock
13 > EOF
13 > EOF
14
14
15 $ cat >> $HGRCPATH << EOF
15 $ cat >> $HGRCPATH << EOF
16 > [experimental]
16 > [experimental]
17 > evolution=createmarkers,exchange
17 > evolution=createmarkers,exchange
18 > bundle2-exp=True
18 > bundle2-exp=True
19 > [ui]
19 > [ui]
20 > ssh=python "$TESTDIR/dummyssh"
20 > ssh=python "$TESTDIR/dummyssh"
21 > logtemplate={rev}:{node|short} {phase} {author} {bookmarks} {desc|firstline}
21 > logtemplate={rev}:{node|short} {phase} {author} {bookmarks} {desc|firstline}
22 > [web]
22 > [web]
23 > push_ssl = false
23 > push_ssl = false
24 > allow_push = *
24 > allow_push = *
25 > [phases]
25 > [phases]
26 > publish=False
26 > publish=False
27 > [hooks]
27 > [hooks]
28 > pretxnclose.tip = hg log -r tip -T "pre-close-tip:{node|short} {phase} {bookmarks}\n"
28 > pretxnclose.tip = hg log -r tip -T "pre-close-tip:{node|short} {phase} {bookmarks}\n"
29 > txnclose.tip = hg log -r tip -T "postclose-tip:{node|short} {phase} {bookmarks}\n"
29 > txnclose.tip = hg log -r tip -T "postclose-tip:{node|short} {phase} {bookmarks}\n"
30 > txnclose.env = sh -c "HG_LOCAL= python \"$TESTDIR/printenv.py\" txnclose"
30 > txnclose.env = sh -c "HG_LOCAL= python \"$TESTDIR/printenv.py\" txnclose"
31 > pushkey= sh "$TESTTMP/bundle2-pushkey-hook.sh"
31 > pushkey= sh "$TESTTMP/bundle2-pushkey-hook.sh"
32 > EOF
32 > EOF
33
33
34 The extension requires a repo (currently unused)
34 The extension requires a repo (currently unused)
35
35
36 $ hg init main
36 $ hg init main
37 $ cd main
37 $ cd main
38 $ touch a
38 $ touch a
39 $ hg add a
39 $ hg add a
40 $ hg commit -m 'a'
40 $ hg commit -m 'a'
41 pre-close-tip:3903775176ed draft
41 pre-close-tip:3903775176ed draft
42 postclose-tip:3903775176ed draft
42 postclose-tip:3903775176ed draft
43 txnclose hook: HG_PHASES_MOVED=1 HG_TXNID=TXN:* HG_TXNNAME=commit (glob)
43 txnclose hook: HG_PHASES_MOVED=1 HG_TXNID=TXN:* HG_TXNNAME=commit (glob)
44
44
45 $ hg unbundle $TESTDIR/bundles/rebase.hg
45 $ hg unbundle $TESTDIR/bundles/rebase.hg
46 adding changesets
46 adding changesets
47 adding manifests
47 adding manifests
48 adding file changes
48 adding file changes
49 added 8 changesets with 7 changes to 7 files (+3 heads)
49 added 8 changesets with 7 changes to 7 files (+3 heads)
50 pre-close-tip:02de42196ebe draft
50 pre-close-tip:02de42196ebe draft
51 postclose-tip:02de42196ebe draft
51 postclose-tip:02de42196ebe draft
52 txnclose hook: HG_NODE=cd010b8cd998f3981a5a8115f94f8da4ab506089 HG_PHASES_MOVED=1 HG_SOURCE=unbundle HG_TXNID=TXN:* HG_TXNNAME=unbundle (glob)
52 txnclose hook: HG_NODE=cd010b8cd998f3981a5a8115f94f8da4ab506089 HG_PHASES_MOVED=1 HG_SOURCE=unbundle HG_TXNID=TXN:* HG_TXNNAME=unbundle (glob)
53 bundle:*/tests/bundles/rebase.hg HG_URL=bundle:*/tests/bundles/rebase.hg (glob)
53 bundle:*/tests/bundles/rebase.hg HG_URL=bundle:*/tests/bundles/rebase.hg (glob)
54 (run 'hg heads' to see heads, 'hg merge' to merge)
54 (run 'hg heads' to see heads, 'hg merge' to merge)
55
55
56 $ cd ..
56 $ cd ..
57
57
58 Real world exchange
58 Real world exchange
59 =====================
59 =====================
60
60
61 Add more obsolescence information
61 Add more obsolescence information
62
62
63 $ hg -R main debugobsolete -d '0 0' 1111111111111111111111111111111111111111 `getmainid 9520eea781bc`
63 $ hg -R main debugobsolete -d '0 0' 1111111111111111111111111111111111111111 `getmainid 9520eea781bc`
64 pre-close-tip:02de42196ebe draft
64 pre-close-tip:02de42196ebe draft
65 postclose-tip:02de42196ebe draft
65 postclose-tip:02de42196ebe draft
66 txnclose hook: HG_NEW_OBSMARKERS=1 HG_TXNID=TXN:* HG_TXNNAME=debugobsolete (glob)
66 txnclose hook: HG_NEW_OBSMARKERS=1 HG_TXNID=TXN:* HG_TXNNAME=debugobsolete (glob)
67 $ hg -R main debugobsolete -d '0 0' 2222222222222222222222222222222222222222 `getmainid 24b6387c8c8c`
67 $ hg -R main debugobsolete -d '0 0' 2222222222222222222222222222222222222222 `getmainid 24b6387c8c8c`
68 pre-close-tip:02de42196ebe draft
68 pre-close-tip:02de42196ebe draft
69 postclose-tip:02de42196ebe draft
69 postclose-tip:02de42196ebe draft
70 txnclose hook: HG_NEW_OBSMARKERS=1 HG_TXNID=TXN:* HG_TXNNAME=debugobsolete (glob)
70 txnclose hook: HG_NEW_OBSMARKERS=1 HG_TXNID=TXN:* HG_TXNNAME=debugobsolete (glob)
71
71
72 clone --pull
72 clone --pull
73
73
74 $ hg -R main phase --public cd010b8cd998
74 $ hg -R main phase --public cd010b8cd998
75 pre-close-tip:000000000000 public
75 pre-close-tip:02de42196ebe draft
76 postclose-tip:02de42196ebe draft
76 postclose-tip:02de42196ebe draft
77 txnclose hook: HG_PHASES_MOVED=1 HG_TXNID=TXN:* HG_TXNNAME=phase (glob)
77 txnclose hook: HG_PHASES_MOVED=1 HG_TXNID=TXN:* HG_TXNNAME=phase (glob)
78 $ hg clone main other --pull --rev 9520eea781bc
78 $ hg clone main other --pull --rev 9520eea781bc
79 adding changesets
79 adding changesets
80 adding manifests
80 adding manifests
81 adding file changes
81 adding file changes
82 added 2 changesets with 2 changes to 2 files
82 added 2 changesets with 2 changes to 2 files
83 1 new obsolescence markers
83 1 new obsolescence markers
84 pre-close-tip:9520eea781bc draft
84 pre-close-tip:9520eea781bc draft
85 postclose-tip:9520eea781bc draft
85 postclose-tip:9520eea781bc draft
86 txnclose hook: HG_NEW_OBSMARKERS=1 HG_NODE=cd010b8cd998f3981a5a8115f94f8da4ab506089 HG_PHASES_MOVED=1 HG_SOURCE=pull HG_TXNID=TXN:* HG_TXNNAME=pull (glob)
86 txnclose hook: HG_NEW_OBSMARKERS=1 HG_NODE=cd010b8cd998f3981a5a8115f94f8da4ab506089 HG_PHASES_MOVED=1 HG_SOURCE=pull HG_TXNID=TXN:* HG_TXNNAME=pull (glob)
87 file:/*/$TESTTMP/main HG_URL=file:$TESTTMP/main (glob)
87 file:/*/$TESTTMP/main HG_URL=file:$TESTTMP/main (glob)
88 updating to branch default
88 updating to branch default
89 2 files updated, 0 files merged, 0 files removed, 0 files unresolved
89 2 files updated, 0 files merged, 0 files removed, 0 files unresolved
90 $ hg -R other log -G
90 $ hg -R other log -G
91 @ 1:9520eea781bc draft Nicolas Dumazet <nicdumz.commits@gmail.com> E
91 @ 1:9520eea781bc draft Nicolas Dumazet <nicdumz.commits@gmail.com> E
92 |
92 |
93 o 0:cd010b8cd998 public Nicolas Dumazet <nicdumz.commits@gmail.com> A
93 o 0:cd010b8cd998 public Nicolas Dumazet <nicdumz.commits@gmail.com> A
94
94
95 $ hg -R other debugobsolete
95 $ hg -R other debugobsolete
96 1111111111111111111111111111111111111111 9520eea781bcca16c1e15acc0ba14335a0e8e5ba 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
96 1111111111111111111111111111111111111111 9520eea781bcca16c1e15acc0ba14335a0e8e5ba 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
97
97
98 pull
98 pull
99
99
100 $ hg -R main phase --public 9520eea781bc
100 $ hg -R main phase --public 9520eea781bc
101 pre-close-tip:000000000000 public
101 pre-close-tip:02de42196ebe draft
102 postclose-tip:02de42196ebe draft
102 postclose-tip:02de42196ebe draft
103 txnclose hook: HG_PHASES_MOVED=1 HG_TXNID=TXN:* HG_TXNNAME=phase (glob)
103 txnclose hook: HG_PHASES_MOVED=1 HG_TXNID=TXN:* HG_TXNNAME=phase (glob)
104 $ hg -R other pull -r 24b6387c8c8c
104 $ hg -R other pull -r 24b6387c8c8c
105 pulling from $TESTTMP/main (glob)
105 pulling from $TESTTMP/main (glob)
106 searching for changes
106 searching for changes
107 adding changesets
107 adding changesets
108 adding manifests
108 adding manifests
109 adding file changes
109 adding file changes
110 added 1 changesets with 1 changes to 1 files (+1 heads)
110 added 1 changesets with 1 changes to 1 files (+1 heads)
111 1 new obsolescence markers
111 1 new obsolescence markers
112 pre-close-tip:24b6387c8c8c draft
112 pre-close-tip:24b6387c8c8c draft
113 postclose-tip:24b6387c8c8c draft
113 postclose-tip:24b6387c8c8c draft
114 txnclose hook: HG_NEW_OBSMARKERS=1 HG_NODE=24b6387c8c8cae37178880f3fa95ded3cb1cf785 HG_PHASES_MOVED=1 HG_SOURCE=pull HG_TXNID=TXN:* HG_TXNNAME=pull (glob)
114 txnclose hook: HG_NEW_OBSMARKERS=1 HG_NODE=24b6387c8c8cae37178880f3fa95ded3cb1cf785 HG_PHASES_MOVED=1 HG_SOURCE=pull HG_TXNID=TXN:* HG_TXNNAME=pull (glob)
115 file:/*/$TESTTMP/main HG_URL=file:$TESTTMP/main (glob)
115 file:/*/$TESTTMP/main HG_URL=file:$TESTTMP/main (glob)
116 (run 'hg heads' to see heads, 'hg merge' to merge)
116 (run 'hg heads' to see heads, 'hg merge' to merge)
117 $ hg -R other log -G
117 $ hg -R other log -G
118 o 2:24b6387c8c8c draft Nicolas Dumazet <nicdumz.commits@gmail.com> F
118 o 2:24b6387c8c8c draft Nicolas Dumazet <nicdumz.commits@gmail.com> F
119 |
119 |
120 | @ 1:9520eea781bc draft Nicolas Dumazet <nicdumz.commits@gmail.com> E
120 | @ 1:9520eea781bc draft Nicolas Dumazet <nicdumz.commits@gmail.com> E
121 |/
121 |/
122 o 0:cd010b8cd998 public Nicolas Dumazet <nicdumz.commits@gmail.com> A
122 o 0:cd010b8cd998 public Nicolas Dumazet <nicdumz.commits@gmail.com> A
123
123
124 $ hg -R other debugobsolete
124 $ hg -R other debugobsolete
125 1111111111111111111111111111111111111111 9520eea781bcca16c1e15acc0ba14335a0e8e5ba 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
125 1111111111111111111111111111111111111111 9520eea781bcca16c1e15acc0ba14335a0e8e5ba 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
126 2222222222222222222222222222222222222222 24b6387c8c8cae37178880f3fa95ded3cb1cf785 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
126 2222222222222222222222222222222222222222 24b6387c8c8cae37178880f3fa95ded3cb1cf785 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
127
127
128 pull empty (with phase movement)
128 pull empty (with phase movement)
129
129
130 $ hg -R main phase --public 24b6387c8c8c
130 $ hg -R main phase --public 24b6387c8c8c
131 pre-close-tip:000000000000 public
131 pre-close-tip:02de42196ebe draft
132 postclose-tip:02de42196ebe draft
132 postclose-tip:02de42196ebe draft
133 txnclose hook: HG_PHASES_MOVED=1 HG_TXNID=TXN:* HG_TXNNAME=phase (glob)
133 txnclose hook: HG_PHASES_MOVED=1 HG_TXNID=TXN:* HG_TXNNAME=phase (glob)
134 $ hg -R other pull -r 24b6387c8c8c
134 $ hg -R other pull -r 24b6387c8c8c
135 pulling from $TESTTMP/main (glob)
135 pulling from $TESTTMP/main (glob)
136 no changes found
136 no changes found
137 pre-close-tip:000000000000 public
137 pre-close-tip:24b6387c8c8c public
138 postclose-tip:24b6387c8c8c public
138 postclose-tip:24b6387c8c8c public
139 txnclose hook: HG_NEW_OBSMARKERS=0 HG_PHASES_MOVED=1 HG_SOURCE=pull HG_TXNID=TXN:* HG_TXNNAME=pull (glob)
139 txnclose hook: HG_NEW_OBSMARKERS=0 HG_PHASES_MOVED=1 HG_SOURCE=pull HG_TXNID=TXN:* HG_TXNNAME=pull (glob)
140 file:/*/$TESTTMP/main HG_URL=file:$TESTTMP/main (glob)
140 file:/*/$TESTTMP/main HG_URL=file:$TESTTMP/main (glob)
141 $ hg -R other log -G
141 $ hg -R other log -G
142 o 2:24b6387c8c8c public Nicolas Dumazet <nicdumz.commits@gmail.com> F
142 o 2:24b6387c8c8c public Nicolas Dumazet <nicdumz.commits@gmail.com> F
143 |
143 |
144 | @ 1:9520eea781bc draft Nicolas Dumazet <nicdumz.commits@gmail.com> E
144 | @ 1:9520eea781bc draft Nicolas Dumazet <nicdumz.commits@gmail.com> E
145 |/
145 |/
146 o 0:cd010b8cd998 public Nicolas Dumazet <nicdumz.commits@gmail.com> A
146 o 0:cd010b8cd998 public Nicolas Dumazet <nicdumz.commits@gmail.com> A
147
147
148 $ hg -R other debugobsolete
148 $ hg -R other debugobsolete
149 1111111111111111111111111111111111111111 9520eea781bcca16c1e15acc0ba14335a0e8e5ba 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
149 1111111111111111111111111111111111111111 9520eea781bcca16c1e15acc0ba14335a0e8e5ba 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
150 2222222222222222222222222222222222222222 24b6387c8c8cae37178880f3fa95ded3cb1cf785 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
150 2222222222222222222222222222222222222222 24b6387c8c8cae37178880f3fa95ded3cb1cf785 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
151
151
152 pull empty
152 pull empty
153
153
154 $ hg -R other pull -r 24b6387c8c8c
154 $ hg -R other pull -r 24b6387c8c8c
155 pulling from $TESTTMP/main (glob)
155 pulling from $TESTTMP/main (glob)
156 no changes found
156 no changes found
157 pre-close-tip:24b6387c8c8c public
157 pre-close-tip:24b6387c8c8c public
158 postclose-tip:24b6387c8c8c public
158 postclose-tip:24b6387c8c8c public
159 txnclose hook: HG_NEW_OBSMARKERS=0 HG_SOURCE=pull HG_TXNID=TXN:* HG_TXNNAME=pull (glob)
159 txnclose hook: HG_NEW_OBSMARKERS=0 HG_SOURCE=pull HG_TXNID=TXN:* HG_TXNNAME=pull (glob)
160 file:/*/$TESTTMP/main HG_URL=file:$TESTTMP/main (glob)
160 file:/*/$TESTTMP/main HG_URL=file:$TESTTMP/main (glob)
161 $ hg -R other log -G
161 $ hg -R other log -G
162 o 2:24b6387c8c8c public Nicolas Dumazet <nicdumz.commits@gmail.com> F
162 o 2:24b6387c8c8c public Nicolas Dumazet <nicdumz.commits@gmail.com> F
163 |
163 |
164 | @ 1:9520eea781bc draft Nicolas Dumazet <nicdumz.commits@gmail.com> E
164 | @ 1:9520eea781bc draft Nicolas Dumazet <nicdumz.commits@gmail.com> E
165 |/
165 |/
166 o 0:cd010b8cd998 public Nicolas Dumazet <nicdumz.commits@gmail.com> A
166 o 0:cd010b8cd998 public Nicolas Dumazet <nicdumz.commits@gmail.com> A
167
167
168 $ hg -R other debugobsolete
168 $ hg -R other debugobsolete
169 1111111111111111111111111111111111111111 9520eea781bcca16c1e15acc0ba14335a0e8e5ba 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
169 1111111111111111111111111111111111111111 9520eea781bcca16c1e15acc0ba14335a0e8e5ba 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
170 2222222222222222222222222222222222222222 24b6387c8c8cae37178880f3fa95ded3cb1cf785 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
170 2222222222222222222222222222222222222222 24b6387c8c8cae37178880f3fa95ded3cb1cf785 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
171
171
172 add extra data to test their exchange during push
172 add extra data to test their exchange during push
173
173
174 $ hg -R main bookmark --rev eea13746799a book_eea1
174 $ hg -R main bookmark --rev eea13746799a book_eea1
175 $ hg -R main debugobsolete -d '0 0' 3333333333333333333333333333333333333333 `getmainid eea13746799a`
175 $ hg -R main debugobsolete -d '0 0' 3333333333333333333333333333333333333333 `getmainid eea13746799a`
176 pre-close-tip:02de42196ebe draft
176 pre-close-tip:02de42196ebe draft
177 postclose-tip:02de42196ebe draft
177 postclose-tip:02de42196ebe draft
178 txnclose hook: HG_NEW_OBSMARKERS=1 HG_TXNID=TXN:* HG_TXNNAME=debugobsolete (glob)
178 txnclose hook: HG_NEW_OBSMARKERS=1 HG_TXNID=TXN:* HG_TXNNAME=debugobsolete (glob)
179 $ hg -R main bookmark --rev 02de42196ebe book_02de
179 $ hg -R main bookmark --rev 02de42196ebe book_02de
180 $ hg -R main debugobsolete -d '0 0' 4444444444444444444444444444444444444444 `getmainid 02de42196ebe`
180 $ hg -R main debugobsolete -d '0 0' 4444444444444444444444444444444444444444 `getmainid 02de42196ebe`
181 pre-close-tip:02de42196ebe draft book_02de
181 pre-close-tip:02de42196ebe draft book_02de
182 postclose-tip:02de42196ebe draft book_02de
182 postclose-tip:02de42196ebe draft book_02de
183 txnclose hook: HG_NEW_OBSMARKERS=1 HG_TXNID=TXN:* HG_TXNNAME=debugobsolete (glob)
183 txnclose hook: HG_NEW_OBSMARKERS=1 HG_TXNID=TXN:* HG_TXNNAME=debugobsolete (glob)
184 $ hg -R main bookmark --rev 42ccdea3bb16 book_42cc
184 $ hg -R main bookmark --rev 42ccdea3bb16 book_42cc
185 $ hg -R main debugobsolete -d '0 0' 5555555555555555555555555555555555555555 `getmainid 42ccdea3bb16`
185 $ hg -R main debugobsolete -d '0 0' 5555555555555555555555555555555555555555 `getmainid 42ccdea3bb16`
186 pre-close-tip:02de42196ebe draft book_02de
186 pre-close-tip:02de42196ebe draft book_02de
187 postclose-tip:02de42196ebe draft book_02de
187 postclose-tip:02de42196ebe draft book_02de
188 txnclose hook: HG_NEW_OBSMARKERS=1 HG_TXNID=TXN:* HG_TXNNAME=debugobsolete (glob)
188 txnclose hook: HG_NEW_OBSMARKERS=1 HG_TXNID=TXN:* HG_TXNNAME=debugobsolete (glob)
189 $ hg -R main bookmark --rev 5fddd98957c8 book_5fdd
189 $ hg -R main bookmark --rev 5fddd98957c8 book_5fdd
190 $ hg -R main debugobsolete -d '0 0' 6666666666666666666666666666666666666666 `getmainid 5fddd98957c8`
190 $ hg -R main debugobsolete -d '0 0' 6666666666666666666666666666666666666666 `getmainid 5fddd98957c8`
191 pre-close-tip:02de42196ebe draft book_02de
191 pre-close-tip:02de42196ebe draft book_02de
192 postclose-tip:02de42196ebe draft book_02de
192 postclose-tip:02de42196ebe draft book_02de
193 txnclose hook: HG_NEW_OBSMARKERS=1 HG_TXNID=TXN:* HG_TXNNAME=debugobsolete (glob)
193 txnclose hook: HG_NEW_OBSMARKERS=1 HG_TXNID=TXN:* HG_TXNNAME=debugobsolete (glob)
194 $ hg -R main bookmark --rev 32af7686d403 book_32af
194 $ hg -R main bookmark --rev 32af7686d403 book_32af
195 $ hg -R main debugobsolete -d '0 0' 7777777777777777777777777777777777777777 `getmainid 32af7686d403`
195 $ hg -R main debugobsolete -d '0 0' 7777777777777777777777777777777777777777 `getmainid 32af7686d403`
196 pre-close-tip:02de42196ebe draft book_02de
196 pre-close-tip:02de42196ebe draft book_02de
197 postclose-tip:02de42196ebe draft book_02de
197 postclose-tip:02de42196ebe draft book_02de
198 txnclose hook: HG_NEW_OBSMARKERS=1 HG_TXNID=TXN:* HG_TXNNAME=debugobsolete (glob)
198 txnclose hook: HG_NEW_OBSMARKERS=1 HG_TXNID=TXN:* HG_TXNNAME=debugobsolete (glob)
199
199
200 $ hg -R other bookmark --rev cd010b8cd998 book_eea1
200 $ hg -R other bookmark --rev cd010b8cd998 book_eea1
201 $ hg -R other bookmark --rev cd010b8cd998 book_02de
201 $ hg -R other bookmark --rev cd010b8cd998 book_02de
202 $ hg -R other bookmark --rev cd010b8cd998 book_42cc
202 $ hg -R other bookmark --rev cd010b8cd998 book_42cc
203 $ hg -R other bookmark --rev cd010b8cd998 book_5fdd
203 $ hg -R other bookmark --rev cd010b8cd998 book_5fdd
204 $ hg -R other bookmark --rev cd010b8cd998 book_32af
204 $ hg -R other bookmark --rev cd010b8cd998 book_32af
205
205
206 $ hg -R main phase --public eea13746799a
206 $ hg -R main phase --public eea13746799a
207 pre-close-tip:000000000000 public
207 pre-close-tip:02de42196ebe draft book_02de
208 postclose-tip:02de42196ebe draft book_02de
208 postclose-tip:02de42196ebe draft book_02de
209 txnclose hook: HG_PHASES_MOVED=1 HG_TXNID=TXN:* HG_TXNNAME=phase (glob)
209 txnclose hook: HG_PHASES_MOVED=1 HG_TXNID=TXN:* HG_TXNNAME=phase (glob)
210
210
211 push
211 push
212 $ hg -R main push other --rev eea13746799a --bookmark book_eea1
212 $ hg -R main push other --rev eea13746799a --bookmark book_eea1
213 pushing to other
213 pushing to other
214 searching for changes
214 searching for changes
215 pre-close-tip:eea13746799a public book_eea1
215 pre-close-tip:eea13746799a public book_eea1
216 pushkey: lock state after "phases"
216 pushkey: lock state after "phases"
217 lock: free
217 lock: free
218 wlock: free
218 wlock: free
219 pushkey: lock state after "bookmarks"
219 pushkey: lock state after "bookmarks"
220 lock: free
220 lock: free
221 wlock: free
221 wlock: free
222 postclose-tip:eea13746799a public book_eea1
222 postclose-tip:eea13746799a public book_eea1
223 txnclose hook: HG_BOOKMARK_MOVED=1 HG_BUNDLE2=1 HG_NEW_OBSMARKERS=1 HG_NODE=eea13746799a9e0bfd88f29d3c2e9dc9389f524f HG_PHASES_MOVED=1 HG_SOURCE=push HG_TXNID=TXN:* HG_TXNNAME=push HG_URL=push (glob)
223 txnclose hook: HG_BOOKMARK_MOVED=1 HG_BUNDLE2=1 HG_NEW_OBSMARKERS=1 HG_NODE=eea13746799a9e0bfd88f29d3c2e9dc9389f524f HG_PHASES_MOVED=1 HG_SOURCE=push HG_TXNID=TXN:* HG_TXNNAME=push HG_URL=push (glob)
224 remote: adding changesets
224 remote: adding changesets
225 remote: adding manifests
225 remote: adding manifests
226 remote: adding file changes
226 remote: adding file changes
227 remote: added 1 changesets with 0 changes to 0 files (-1 heads)
227 remote: added 1 changesets with 0 changes to 0 files (-1 heads)
228 remote: 1 new obsolescence markers
228 remote: 1 new obsolescence markers
229 updating bookmark book_eea1
229 updating bookmark book_eea1
230 pre-close-tip:02de42196ebe draft book_02de
230 pre-close-tip:02de42196ebe draft book_02de
231 postclose-tip:02de42196ebe draft book_02de
231 postclose-tip:02de42196ebe draft book_02de
232 txnclose hook: HG_SOURCE=push-response HG_TXNID=TXN:* HG_TXNNAME=push-response (glob)
232 txnclose hook: HG_SOURCE=push-response HG_TXNID=TXN:* HG_TXNNAME=push-response (glob)
233 file:/*/$TESTTMP/other HG_URL=file:$TESTTMP/other (glob)
233 file:/*/$TESTTMP/other HG_URL=file:$TESTTMP/other (glob)
234 $ hg -R other log -G
234 $ hg -R other log -G
235 o 3:eea13746799a public Nicolas Dumazet <nicdumz.commits@gmail.com> book_eea1 G
235 o 3:eea13746799a public Nicolas Dumazet <nicdumz.commits@gmail.com> book_eea1 G
236 |\
236 |\
237 | o 2:24b6387c8c8c public Nicolas Dumazet <nicdumz.commits@gmail.com> F
237 | o 2:24b6387c8c8c public Nicolas Dumazet <nicdumz.commits@gmail.com> F
238 | |
238 | |
239 @ | 1:9520eea781bc public Nicolas Dumazet <nicdumz.commits@gmail.com> E
239 @ | 1:9520eea781bc public Nicolas Dumazet <nicdumz.commits@gmail.com> E
240 |/
240 |/
241 o 0:cd010b8cd998 public Nicolas Dumazet <nicdumz.commits@gmail.com> book_02de book_32af book_42cc book_5fdd A
241 o 0:cd010b8cd998 public Nicolas Dumazet <nicdumz.commits@gmail.com> book_02de book_32af book_42cc book_5fdd A
242
242
243 $ hg -R other debugobsolete
243 $ hg -R other debugobsolete
244 1111111111111111111111111111111111111111 9520eea781bcca16c1e15acc0ba14335a0e8e5ba 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
244 1111111111111111111111111111111111111111 9520eea781bcca16c1e15acc0ba14335a0e8e5ba 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
245 2222222222222222222222222222222222222222 24b6387c8c8cae37178880f3fa95ded3cb1cf785 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
245 2222222222222222222222222222222222222222 24b6387c8c8cae37178880f3fa95ded3cb1cf785 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
246 3333333333333333333333333333333333333333 eea13746799a9e0bfd88f29d3c2e9dc9389f524f 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
246 3333333333333333333333333333333333333333 eea13746799a9e0bfd88f29d3c2e9dc9389f524f 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
247
247
248 pull over ssh
248 pull over ssh
249
249
250 $ hg -R other pull ssh://user@dummy/main -r 02de42196ebe --bookmark book_02de
250 $ hg -R other pull ssh://user@dummy/main -r 02de42196ebe --bookmark book_02de
251 pulling from ssh://user@dummy/main
251 pulling from ssh://user@dummy/main
252 searching for changes
252 searching for changes
253 adding changesets
253 adding changesets
254 adding manifests
254 adding manifests
255 adding file changes
255 adding file changes
256 added 1 changesets with 1 changes to 1 files (+1 heads)
256 added 1 changesets with 1 changes to 1 files (+1 heads)
257 1 new obsolescence markers
257 1 new obsolescence markers
258 updating bookmark book_02de
258 updating bookmark book_02de
259 pre-close-tip:02de42196ebe draft book_02de
259 pre-close-tip:02de42196ebe draft book_02de
260 postclose-tip:02de42196ebe draft book_02de
260 postclose-tip:02de42196ebe draft book_02de
261 txnclose hook: HG_BOOKMARK_MOVED=1 HG_NEW_OBSMARKERS=1 HG_NODE=02de42196ebee42ef284b6780a87cdc96e8eaab6 HG_PHASES_MOVED=1 HG_SOURCE=pull HG_TXNID=TXN:* HG_TXNNAME=pull (glob)
261 txnclose hook: HG_BOOKMARK_MOVED=1 HG_NEW_OBSMARKERS=1 HG_NODE=02de42196ebee42ef284b6780a87cdc96e8eaab6 HG_PHASES_MOVED=1 HG_SOURCE=pull HG_TXNID=TXN:* HG_TXNNAME=pull (glob)
262 ssh://user@dummy/main HG_URL=ssh://user@dummy/main
262 ssh://user@dummy/main HG_URL=ssh://user@dummy/main
263 (run 'hg heads' to see heads, 'hg merge' to merge)
263 (run 'hg heads' to see heads, 'hg merge' to merge)
264 $ hg -R other debugobsolete
264 $ hg -R other debugobsolete
265 1111111111111111111111111111111111111111 9520eea781bcca16c1e15acc0ba14335a0e8e5ba 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
265 1111111111111111111111111111111111111111 9520eea781bcca16c1e15acc0ba14335a0e8e5ba 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
266 2222222222222222222222222222222222222222 24b6387c8c8cae37178880f3fa95ded3cb1cf785 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
266 2222222222222222222222222222222222222222 24b6387c8c8cae37178880f3fa95ded3cb1cf785 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
267 3333333333333333333333333333333333333333 eea13746799a9e0bfd88f29d3c2e9dc9389f524f 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
267 3333333333333333333333333333333333333333 eea13746799a9e0bfd88f29d3c2e9dc9389f524f 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
268 4444444444444444444444444444444444444444 02de42196ebee42ef284b6780a87cdc96e8eaab6 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
268 4444444444444444444444444444444444444444 02de42196ebee42ef284b6780a87cdc96e8eaab6 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
269
269
270 pull over http
270 pull over http
271
271
272 $ hg -R main serve -p $HGPORT -d --pid-file=main.pid -E main-error.log
272 $ hg -R main serve -p $HGPORT -d --pid-file=main.pid -E main-error.log
273 $ cat main.pid >> $DAEMON_PIDS
273 $ cat main.pid >> $DAEMON_PIDS
274
274
275 $ hg -R other pull http://localhost:$HGPORT/ -r 42ccdea3bb16 --bookmark book_42cc
275 $ hg -R other pull http://localhost:$HGPORT/ -r 42ccdea3bb16 --bookmark book_42cc
276 pulling from http://localhost:$HGPORT/
276 pulling from http://localhost:$HGPORT/
277 searching for changes
277 searching for changes
278 adding changesets
278 adding changesets
279 adding manifests
279 adding manifests
280 adding file changes
280 adding file changes
281 added 1 changesets with 1 changes to 1 files (+1 heads)
281 added 1 changesets with 1 changes to 1 files (+1 heads)
282 1 new obsolescence markers
282 1 new obsolescence markers
283 updating bookmark book_42cc
283 updating bookmark book_42cc
284 pre-close-tip:42ccdea3bb16 draft book_42cc
284 pre-close-tip:42ccdea3bb16 draft book_42cc
285 postclose-tip:42ccdea3bb16 draft book_42cc
285 postclose-tip:42ccdea3bb16 draft book_42cc
286 txnclose hook: HG_BOOKMARK_MOVED=1 HG_NEW_OBSMARKERS=1 HG_NODE=42ccdea3bb16d28e1848c95fe2e44c000f3f21b1 HG_PHASES_MOVED=1 HG_SOURCE=pull HG_TXNID=TXN:* HG_TXNNAME=pull (glob)
286 txnclose hook: HG_BOOKMARK_MOVED=1 HG_NEW_OBSMARKERS=1 HG_NODE=42ccdea3bb16d28e1848c95fe2e44c000f3f21b1 HG_PHASES_MOVED=1 HG_SOURCE=pull HG_TXNID=TXN:* HG_TXNNAME=pull (glob)
287 http://localhost:$HGPORT/ HG_URL=http://localhost:$HGPORT/
287 http://localhost:$HGPORT/ HG_URL=http://localhost:$HGPORT/
288 (run 'hg heads .' to see heads, 'hg merge' to merge)
288 (run 'hg heads .' to see heads, 'hg merge' to merge)
289 $ cat main-error.log
289 $ cat main-error.log
290 $ hg -R other debugobsolete
290 $ hg -R other debugobsolete
291 1111111111111111111111111111111111111111 9520eea781bcca16c1e15acc0ba14335a0e8e5ba 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
291 1111111111111111111111111111111111111111 9520eea781bcca16c1e15acc0ba14335a0e8e5ba 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
292 2222222222222222222222222222222222222222 24b6387c8c8cae37178880f3fa95ded3cb1cf785 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
292 2222222222222222222222222222222222222222 24b6387c8c8cae37178880f3fa95ded3cb1cf785 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
293 3333333333333333333333333333333333333333 eea13746799a9e0bfd88f29d3c2e9dc9389f524f 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
293 3333333333333333333333333333333333333333 eea13746799a9e0bfd88f29d3c2e9dc9389f524f 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
294 4444444444444444444444444444444444444444 02de42196ebee42ef284b6780a87cdc96e8eaab6 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
294 4444444444444444444444444444444444444444 02de42196ebee42ef284b6780a87cdc96e8eaab6 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
295 5555555555555555555555555555555555555555 42ccdea3bb16d28e1848c95fe2e44c000f3f21b1 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
295 5555555555555555555555555555555555555555 42ccdea3bb16d28e1848c95fe2e44c000f3f21b1 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
296
296
297 push over ssh
297 push over ssh
298
298
299 $ hg -R main push ssh://user@dummy/other -r 5fddd98957c8 --bookmark book_5fdd
299 $ hg -R main push ssh://user@dummy/other -r 5fddd98957c8 --bookmark book_5fdd
300 pushing to ssh://user@dummy/other
300 pushing to ssh://user@dummy/other
301 searching for changes
301 searching for changes
302 remote: adding changesets
302 remote: adding changesets
303 remote: adding manifests
303 remote: adding manifests
304 remote: adding file changes
304 remote: adding file changes
305 remote: added 1 changesets with 1 changes to 1 files
305 remote: added 1 changesets with 1 changes to 1 files
306 remote: 1 new obsolescence markers
306 remote: 1 new obsolescence markers
307 updating bookmark book_5fdd
307 updating bookmark book_5fdd
308 remote: pre-close-tip:5fddd98957c8 draft book_5fdd
308 remote: pre-close-tip:5fddd98957c8 draft book_5fdd
309 remote: pushkey: lock state after "bookmarks"
309 remote: pushkey: lock state after "bookmarks"
310 remote: lock: free
310 remote: lock: free
311 remote: wlock: free
311 remote: wlock: free
312 remote: postclose-tip:5fddd98957c8 draft book_5fdd
312 remote: postclose-tip:5fddd98957c8 draft book_5fdd
313 remote: txnclose hook: HG_BOOKMARK_MOVED=1 HG_BUNDLE2=1 HG_NEW_OBSMARKERS=1 HG_NODE=5fddd98957c8a54a4d436dfe1da9d87f21a1b97b HG_SOURCE=serve HG_TXNID=TXN:* HG_TXNNAME=serve HG_URL=remote:ssh:127.0.0.1 (glob)
313 remote: txnclose hook: HG_BOOKMARK_MOVED=1 HG_BUNDLE2=1 HG_NEW_OBSMARKERS=1 HG_NODE=5fddd98957c8a54a4d436dfe1da9d87f21a1b97b HG_SOURCE=serve HG_TXNID=TXN:* HG_TXNNAME=serve HG_URL=remote:ssh:127.0.0.1 (glob)
314 pre-close-tip:02de42196ebe draft book_02de
314 pre-close-tip:02de42196ebe draft book_02de
315 postclose-tip:02de42196ebe draft book_02de
315 postclose-tip:02de42196ebe draft book_02de
316 txnclose hook: HG_SOURCE=push-response HG_TXNID=TXN:* HG_TXNNAME=push-response (glob)
316 txnclose hook: HG_SOURCE=push-response HG_TXNID=TXN:* HG_TXNNAME=push-response (glob)
317 ssh://user@dummy/other HG_URL=ssh://user@dummy/other
317 ssh://user@dummy/other HG_URL=ssh://user@dummy/other
318 $ hg -R other log -G
318 $ hg -R other log -G
319 o 6:5fddd98957c8 draft Nicolas Dumazet <nicdumz.commits@gmail.com> book_5fdd C
319 o 6:5fddd98957c8 draft Nicolas Dumazet <nicdumz.commits@gmail.com> book_5fdd C
320 |
320 |
321 o 5:42ccdea3bb16 draft Nicolas Dumazet <nicdumz.commits@gmail.com> book_42cc B
321 o 5:42ccdea3bb16 draft Nicolas Dumazet <nicdumz.commits@gmail.com> book_42cc B
322 |
322 |
323 | o 4:02de42196ebe draft Nicolas Dumazet <nicdumz.commits@gmail.com> book_02de H
323 | o 4:02de42196ebe draft Nicolas Dumazet <nicdumz.commits@gmail.com> book_02de H
324 | |
324 | |
325 | | o 3:eea13746799a public Nicolas Dumazet <nicdumz.commits@gmail.com> book_eea1 G
325 | | o 3:eea13746799a public Nicolas Dumazet <nicdumz.commits@gmail.com> book_eea1 G
326 | |/|
326 | |/|
327 | o | 2:24b6387c8c8c public Nicolas Dumazet <nicdumz.commits@gmail.com> F
327 | o | 2:24b6387c8c8c public Nicolas Dumazet <nicdumz.commits@gmail.com> F
328 |/ /
328 |/ /
329 | @ 1:9520eea781bc public Nicolas Dumazet <nicdumz.commits@gmail.com> E
329 | @ 1:9520eea781bc public Nicolas Dumazet <nicdumz.commits@gmail.com> E
330 |/
330 |/
331 o 0:cd010b8cd998 public Nicolas Dumazet <nicdumz.commits@gmail.com> book_32af A
331 o 0:cd010b8cd998 public Nicolas Dumazet <nicdumz.commits@gmail.com> book_32af A
332
332
333 $ hg -R other debugobsolete
333 $ hg -R other debugobsolete
334 1111111111111111111111111111111111111111 9520eea781bcca16c1e15acc0ba14335a0e8e5ba 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
334 1111111111111111111111111111111111111111 9520eea781bcca16c1e15acc0ba14335a0e8e5ba 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
335 2222222222222222222222222222222222222222 24b6387c8c8cae37178880f3fa95ded3cb1cf785 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
335 2222222222222222222222222222222222222222 24b6387c8c8cae37178880f3fa95ded3cb1cf785 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
336 3333333333333333333333333333333333333333 eea13746799a9e0bfd88f29d3c2e9dc9389f524f 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
336 3333333333333333333333333333333333333333 eea13746799a9e0bfd88f29d3c2e9dc9389f524f 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
337 4444444444444444444444444444444444444444 02de42196ebee42ef284b6780a87cdc96e8eaab6 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
337 4444444444444444444444444444444444444444 02de42196ebee42ef284b6780a87cdc96e8eaab6 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
338 5555555555555555555555555555555555555555 42ccdea3bb16d28e1848c95fe2e44c000f3f21b1 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
338 5555555555555555555555555555555555555555 42ccdea3bb16d28e1848c95fe2e44c000f3f21b1 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
339 6666666666666666666666666666666666666666 5fddd98957c8a54a4d436dfe1da9d87f21a1b97b 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
339 6666666666666666666666666666666666666666 5fddd98957c8a54a4d436dfe1da9d87f21a1b97b 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
340
340
341 push over http
341 push over http
342
342
343 $ hg -R other serve -p $HGPORT2 -d --pid-file=other.pid -E other-error.log
343 $ hg -R other serve -p $HGPORT2 -d --pid-file=other.pid -E other-error.log
344 $ cat other.pid >> $DAEMON_PIDS
344 $ cat other.pid >> $DAEMON_PIDS
345
345
346 $ hg -R main phase --public 32af7686d403
346 $ hg -R main phase --public 32af7686d403
347 pre-close-tip:000000000000 public
347 pre-close-tip:02de42196ebe draft book_02de
348 postclose-tip:02de42196ebe draft book_02de
348 postclose-tip:02de42196ebe draft book_02de
349 txnclose hook: HG_PHASES_MOVED=1 HG_TXNID=TXN:* HG_TXNNAME=phase (glob)
349 txnclose hook: HG_PHASES_MOVED=1 HG_TXNID=TXN:* HG_TXNNAME=phase (glob)
350 $ hg -R main push http://localhost:$HGPORT2/ -r 32af7686d403 --bookmark book_32af
350 $ hg -R main push http://localhost:$HGPORT2/ -r 32af7686d403 --bookmark book_32af
351 pushing to http://localhost:$HGPORT2/
351 pushing to http://localhost:$HGPORT2/
352 searching for changes
352 searching for changes
353 remote: adding changesets
353 remote: adding changesets
354 remote: adding manifests
354 remote: adding manifests
355 remote: adding file changes
355 remote: adding file changes
356 remote: added 1 changesets with 1 changes to 1 files
356 remote: added 1 changesets with 1 changes to 1 files
357 remote: 1 new obsolescence markers
357 remote: 1 new obsolescence markers
358 updating bookmark book_32af
358 updating bookmark book_32af
359 pre-close-tip:02de42196ebe draft book_02de
359 pre-close-tip:02de42196ebe draft book_02de
360 postclose-tip:02de42196ebe draft book_02de
360 postclose-tip:02de42196ebe draft book_02de
361 txnclose hook: HG_SOURCE=push-response HG_TXNID=TXN:* HG_TXNNAME=push-response (glob)
361 txnclose hook: HG_SOURCE=push-response HG_TXNID=TXN:* HG_TXNNAME=push-response (glob)
362 http://localhost:$HGPORT2/ HG_URL=http://localhost:$HGPORT2/
362 http://localhost:$HGPORT2/ HG_URL=http://localhost:$HGPORT2/
363 $ cat other-error.log
363 $ cat other-error.log
364
364
365 Check final content.
365 Check final content.
366
366
367 $ hg -R other log -G
367 $ hg -R other log -G
368 o 7:32af7686d403 public Nicolas Dumazet <nicdumz.commits@gmail.com> book_32af D
368 o 7:32af7686d403 public Nicolas Dumazet <nicdumz.commits@gmail.com> book_32af D
369 |
369 |
370 o 6:5fddd98957c8 public Nicolas Dumazet <nicdumz.commits@gmail.com> book_5fdd C
370 o 6:5fddd98957c8 public Nicolas Dumazet <nicdumz.commits@gmail.com> book_5fdd C
371 |
371 |
372 o 5:42ccdea3bb16 public Nicolas Dumazet <nicdumz.commits@gmail.com> book_42cc B
372 o 5:42ccdea3bb16 public Nicolas Dumazet <nicdumz.commits@gmail.com> book_42cc B
373 |
373 |
374 | o 4:02de42196ebe draft Nicolas Dumazet <nicdumz.commits@gmail.com> book_02de H
374 | o 4:02de42196ebe draft Nicolas Dumazet <nicdumz.commits@gmail.com> book_02de H
375 | |
375 | |
376 | | o 3:eea13746799a public Nicolas Dumazet <nicdumz.commits@gmail.com> book_eea1 G
376 | | o 3:eea13746799a public Nicolas Dumazet <nicdumz.commits@gmail.com> book_eea1 G
377 | |/|
377 | |/|
378 | o | 2:24b6387c8c8c public Nicolas Dumazet <nicdumz.commits@gmail.com> F
378 | o | 2:24b6387c8c8c public Nicolas Dumazet <nicdumz.commits@gmail.com> F
379 |/ /
379 |/ /
380 | @ 1:9520eea781bc public Nicolas Dumazet <nicdumz.commits@gmail.com> E
380 | @ 1:9520eea781bc public Nicolas Dumazet <nicdumz.commits@gmail.com> E
381 |/
381 |/
382 o 0:cd010b8cd998 public Nicolas Dumazet <nicdumz.commits@gmail.com> A
382 o 0:cd010b8cd998 public Nicolas Dumazet <nicdumz.commits@gmail.com> A
383
383
384 $ hg -R other debugobsolete
384 $ hg -R other debugobsolete
385 1111111111111111111111111111111111111111 9520eea781bcca16c1e15acc0ba14335a0e8e5ba 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
385 1111111111111111111111111111111111111111 9520eea781bcca16c1e15acc0ba14335a0e8e5ba 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
386 2222222222222222222222222222222222222222 24b6387c8c8cae37178880f3fa95ded3cb1cf785 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
386 2222222222222222222222222222222222222222 24b6387c8c8cae37178880f3fa95ded3cb1cf785 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
387 3333333333333333333333333333333333333333 eea13746799a9e0bfd88f29d3c2e9dc9389f524f 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
387 3333333333333333333333333333333333333333 eea13746799a9e0bfd88f29d3c2e9dc9389f524f 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
388 4444444444444444444444444444444444444444 02de42196ebee42ef284b6780a87cdc96e8eaab6 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
388 4444444444444444444444444444444444444444 02de42196ebee42ef284b6780a87cdc96e8eaab6 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
389 5555555555555555555555555555555555555555 42ccdea3bb16d28e1848c95fe2e44c000f3f21b1 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
389 5555555555555555555555555555555555555555 42ccdea3bb16d28e1848c95fe2e44c000f3f21b1 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
390 6666666666666666666666666666666666666666 5fddd98957c8a54a4d436dfe1da9d87f21a1b97b 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
390 6666666666666666666666666666666666666666 5fddd98957c8a54a4d436dfe1da9d87f21a1b97b 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
391 7777777777777777777777777777777777777777 32af7686d403cf45b5d95f2d70cebea587ac806a 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
391 7777777777777777777777777777777777777777 32af7686d403cf45b5d95f2d70cebea587ac806a 0 (Thu Jan 01 00:00:00 1970 +0000) {'user': 'test'}
392
392
393 (check that no 'pending' files remain)
393 (check that no 'pending' files remain)
394
394
395 $ ls -1 other/.hg/bookmarks*
395 $ ls -1 other/.hg/bookmarks*
396 other/.hg/bookmarks
396 other/.hg/bookmarks
397 $ ls -1 other/.hg/store/phaseroots*
397 $ ls -1 other/.hg/store/phaseroots*
398 other/.hg/store/phaseroots
398 other/.hg/store/phaseroots
399 $ ls -1 other/.hg/store/00changelog.i*
399 $ ls -1 other/.hg/store/00changelog.i*
400 other/.hg/store/00changelog.i
400 other/.hg/store/00changelog.i
401
401
402 Error Handling
402 Error Handling
403 ==============
403 ==============
404
404
405 Check that errors are properly returned to the client during push.
405 Check that errors are properly returned to the client during push.
406
406
407 Setting up
407 Setting up
408
408
409 $ cat > failpush.py << EOF
409 $ cat > failpush.py << EOF
410 > """A small extension that makes push fails when using bundle2
410 > """A small extension that makes push fails when using bundle2
411 >
411 >
412 > used to test error handling in bundle2
412 > used to test error handling in bundle2
413 > """
413 > """
414 >
414 >
415 > from mercurial import util
415 > from mercurial import util
416 > from mercurial import bundle2
416 > from mercurial import bundle2
417 > from mercurial import exchange
417 > from mercurial import exchange
418 > from mercurial import extensions
418 > from mercurial import extensions
419 >
419 >
420 > def _pushbundle2failpart(pushop, bundler):
420 > def _pushbundle2failpart(pushop, bundler):
421 > reason = pushop.ui.config('failpush', 'reason', None)
421 > reason = pushop.ui.config('failpush', 'reason', None)
422 > part = None
422 > part = None
423 > if reason == 'abort':
423 > if reason == 'abort':
424 > bundler.newpart('test:abort')
424 > bundler.newpart('test:abort')
425 > if reason == 'unknown':
425 > if reason == 'unknown':
426 > bundler.newpart('test:unknown')
426 > bundler.newpart('test:unknown')
427 > if reason == 'race':
427 > if reason == 'race':
428 > # 20 Bytes of crap
428 > # 20 Bytes of crap
429 > bundler.newpart('check:heads', data='01234567890123456789')
429 > bundler.newpart('check:heads', data='01234567890123456789')
430 >
430 >
431 > @bundle2.parthandler("test:abort")
431 > @bundle2.parthandler("test:abort")
432 > def handleabort(op, part):
432 > def handleabort(op, part):
433 > raise util.Abort('Abandon ship!', hint="don't panic")
433 > raise util.Abort('Abandon ship!', hint="don't panic")
434 >
434 >
435 > def uisetup(ui):
435 > def uisetup(ui):
436 > exchange.b2partsgenmapping['failpart'] = _pushbundle2failpart
436 > exchange.b2partsgenmapping['failpart'] = _pushbundle2failpart
437 > exchange.b2partsgenorder.insert(0, 'failpart')
437 > exchange.b2partsgenorder.insert(0, 'failpart')
438 >
438 >
439 > EOF
439 > EOF
440
440
441 $ cd main
441 $ cd main
442 $ hg up tip
442 $ hg up tip
443 3 files updated, 0 files merged, 1 files removed, 0 files unresolved
443 3 files updated, 0 files merged, 1 files removed, 0 files unresolved
444 $ echo 'I' > I
444 $ echo 'I' > I
445 $ hg add I
445 $ hg add I
446 $ hg ci -m 'I'
446 $ hg ci -m 'I'
447 pre-close-tip:e7ec4e813ba6 draft
447 pre-close-tip:e7ec4e813ba6 draft
448 postclose-tip:e7ec4e813ba6 draft
448 postclose-tip:e7ec4e813ba6 draft
449 txnclose hook: HG_TXNID=TXN:* HG_TXNNAME=commit (glob)
449 txnclose hook: HG_TXNID=TXN:* HG_TXNNAME=commit (glob)
450 $ hg id
450 $ hg id
451 e7ec4e813ba6 tip
451 e7ec4e813ba6 tip
452 $ cd ..
452 $ cd ..
453
453
454 $ cat << EOF >> $HGRCPATH
454 $ cat << EOF >> $HGRCPATH
455 > [extensions]
455 > [extensions]
456 > failpush=$TESTTMP/failpush.py
456 > failpush=$TESTTMP/failpush.py
457 > EOF
457 > EOF
458
458
459 $ "$TESTDIR/killdaemons.py" $DAEMON_PIDS
459 $ "$TESTDIR/killdaemons.py" $DAEMON_PIDS
460 $ hg -R other serve -p $HGPORT2 -d --pid-file=other.pid -E other-error.log
460 $ hg -R other serve -p $HGPORT2 -d --pid-file=other.pid -E other-error.log
461 $ cat other.pid >> $DAEMON_PIDS
461 $ cat other.pid >> $DAEMON_PIDS
462
462
463 Doing the actual push: Abort error
463 Doing the actual push: Abort error
464
464
465 $ cat << EOF >> $HGRCPATH
465 $ cat << EOF >> $HGRCPATH
466 > [failpush]
466 > [failpush]
467 > reason = abort
467 > reason = abort
468 > EOF
468 > EOF
469
469
470 $ hg -R main push other -r e7ec4e813ba6
470 $ hg -R main push other -r e7ec4e813ba6
471 pushing to other
471 pushing to other
472 searching for changes
472 searching for changes
473 abort: Abandon ship!
473 abort: Abandon ship!
474 (don't panic)
474 (don't panic)
475 [255]
475 [255]
476
476
477 $ hg -R main push ssh://user@dummy/other -r e7ec4e813ba6
477 $ hg -R main push ssh://user@dummy/other -r e7ec4e813ba6
478 pushing to ssh://user@dummy/other
478 pushing to ssh://user@dummy/other
479 searching for changes
479 searching for changes
480 abort: Abandon ship!
480 abort: Abandon ship!
481 (don't panic)
481 (don't panic)
482 [255]
482 [255]
483
483
484 $ hg -R main push http://localhost:$HGPORT2/ -r e7ec4e813ba6
484 $ hg -R main push http://localhost:$HGPORT2/ -r e7ec4e813ba6
485 pushing to http://localhost:$HGPORT2/
485 pushing to http://localhost:$HGPORT2/
486 searching for changes
486 searching for changes
487 abort: Abandon ship!
487 abort: Abandon ship!
488 (don't panic)
488 (don't panic)
489 [255]
489 [255]
490
490
491
491
492 Doing the actual push: unknown mandatory parts
492 Doing the actual push: unknown mandatory parts
493
493
494 $ cat << EOF >> $HGRCPATH
494 $ cat << EOF >> $HGRCPATH
495 > [failpush]
495 > [failpush]
496 > reason = unknown
496 > reason = unknown
497 > EOF
497 > EOF
498
498
499 $ hg -R main push other -r e7ec4e813ba6
499 $ hg -R main push other -r e7ec4e813ba6
500 pushing to other
500 pushing to other
501 searching for changes
501 searching for changes
502 abort: missing support for test:unknown
502 abort: missing support for test:unknown
503 [255]
503 [255]
504
504
505 $ hg -R main push ssh://user@dummy/other -r e7ec4e813ba6
505 $ hg -R main push ssh://user@dummy/other -r e7ec4e813ba6
506 pushing to ssh://user@dummy/other
506 pushing to ssh://user@dummy/other
507 searching for changes
507 searching for changes
508 abort: missing support for test:unknown
508 abort: missing support for test:unknown
509 [255]
509 [255]
510
510
511 $ hg -R main push http://localhost:$HGPORT2/ -r e7ec4e813ba6
511 $ hg -R main push http://localhost:$HGPORT2/ -r e7ec4e813ba6
512 pushing to http://localhost:$HGPORT2/
512 pushing to http://localhost:$HGPORT2/
513 searching for changes
513 searching for changes
514 abort: missing support for test:unknown
514 abort: missing support for test:unknown
515 [255]
515 [255]
516
516
517 Doing the actual push: race
517 Doing the actual push: race
518
518
519 $ cat << EOF >> $HGRCPATH
519 $ cat << EOF >> $HGRCPATH
520 > [failpush]
520 > [failpush]
521 > reason = race
521 > reason = race
522 > EOF
522 > EOF
523
523
524 $ hg -R main push other -r e7ec4e813ba6
524 $ hg -R main push other -r e7ec4e813ba6
525 pushing to other
525 pushing to other
526 searching for changes
526 searching for changes
527 abort: push failed:
527 abort: push failed:
528 'repository changed while pushing - please try again'
528 'repository changed while pushing - please try again'
529 [255]
529 [255]
530
530
531 $ hg -R main push ssh://user@dummy/other -r e7ec4e813ba6
531 $ hg -R main push ssh://user@dummy/other -r e7ec4e813ba6
532 pushing to ssh://user@dummy/other
532 pushing to ssh://user@dummy/other
533 searching for changes
533 searching for changes
534 abort: push failed:
534 abort: push failed:
535 'repository changed while pushing - please try again'
535 'repository changed while pushing - please try again'
536 [255]
536 [255]
537
537
538 $ hg -R main push http://localhost:$HGPORT2/ -r e7ec4e813ba6
538 $ hg -R main push http://localhost:$HGPORT2/ -r e7ec4e813ba6
539 pushing to http://localhost:$HGPORT2/
539 pushing to http://localhost:$HGPORT2/
540 searching for changes
540 searching for changes
541 abort: push failed:
541 abort: push failed:
542 'repository changed while pushing - please try again'
542 'repository changed while pushing - please try again'
543 [255]
543 [255]
544
544
545 Doing the actual push: hook abort
545 Doing the actual push: hook abort
546
546
547 $ cat << EOF >> $HGRCPATH
547 $ cat << EOF >> $HGRCPATH
548 > [failpush]
548 > [failpush]
549 > reason =
549 > reason =
550 > [hooks]
550 > [hooks]
551 > pretxnclose.failpush = false
551 > pretxnclose.failpush = false
552 > EOF
552 > EOF
553
553
554 $ "$TESTDIR/killdaemons.py" $DAEMON_PIDS
554 $ "$TESTDIR/killdaemons.py" $DAEMON_PIDS
555 $ hg -R other serve -p $HGPORT2 -d --pid-file=other.pid -E other-error.log
555 $ hg -R other serve -p $HGPORT2 -d --pid-file=other.pid -E other-error.log
556 $ cat other.pid >> $DAEMON_PIDS
556 $ cat other.pid >> $DAEMON_PIDS
557
557
558 $ hg -R main push other -r e7ec4e813ba6
558 $ hg -R main push other -r e7ec4e813ba6
559 pushing to other
559 pushing to other
560 searching for changes
560 searching for changes
561 pre-close-tip:e7ec4e813ba6 draft
561 pre-close-tip:e7ec4e813ba6 draft
562 transaction abort!
562 transaction abort!
563 rollback completed
563 rollback completed
564 remote: adding changesets
564 remote: adding changesets
565 remote: adding manifests
565 remote: adding manifests
566 remote: adding file changes
566 remote: adding file changes
567 remote: added 1 changesets with 1 changes to 1 files
567 remote: added 1 changesets with 1 changes to 1 files
568 abort: pretxnclose.failpush hook exited with status 1
568 abort: pretxnclose.failpush hook exited with status 1
569 [255]
569 [255]
570
570
571 $ hg -R main push ssh://user@dummy/other -r e7ec4e813ba6
571 $ hg -R main push ssh://user@dummy/other -r e7ec4e813ba6
572 pushing to ssh://user@dummy/other
572 pushing to ssh://user@dummy/other
573 searching for changes
573 searching for changes
574 remote: adding changesets
574 remote: adding changesets
575 remote: adding manifests
575 remote: adding manifests
576 remote: adding file changes
576 remote: adding file changes
577 remote: added 1 changesets with 1 changes to 1 files
577 remote: added 1 changesets with 1 changes to 1 files
578 abort: pretxnclose.failpush hook exited with status 1
578 abort: pretxnclose.failpush hook exited with status 1
579 remote: pre-close-tip:e7ec4e813ba6 draft
579 remote: pre-close-tip:e7ec4e813ba6 draft
580 remote: transaction abort!
580 remote: transaction abort!
581 remote: rollback completed
581 remote: rollback completed
582 [255]
582 [255]
583
583
584 $ hg -R main push http://localhost:$HGPORT2/ -r e7ec4e813ba6
584 $ hg -R main push http://localhost:$HGPORT2/ -r e7ec4e813ba6
585 pushing to http://localhost:$HGPORT2/
585 pushing to http://localhost:$HGPORT2/
586 searching for changes
586 searching for changes
587 remote: adding changesets
587 remote: adding changesets
588 remote: adding manifests
588 remote: adding manifests
589 remote: adding file changes
589 remote: adding file changes
590 remote: added 1 changesets with 1 changes to 1 files
590 remote: added 1 changesets with 1 changes to 1 files
591 abort: pretxnclose.failpush hook exited with status 1
591 abort: pretxnclose.failpush hook exited with status 1
592 [255]
592 [255]
593
593
594 (check that no 'pending' files remain)
594 (check that no 'pending' files remain)
595
595
596 $ ls -1 other/.hg/bookmarks*
596 $ ls -1 other/.hg/bookmarks*
597 other/.hg/bookmarks
597 other/.hg/bookmarks
598 $ ls -1 other/.hg/store/phaseroots*
598 $ ls -1 other/.hg/store/phaseroots*
599 other/.hg/store/phaseroots
599 other/.hg/store/phaseroots
600 $ ls -1 other/.hg/store/00changelog.i*
600 $ ls -1 other/.hg/store/00changelog.i*
601 other/.hg/store/00changelog.i
601 other/.hg/store/00changelog.i
602
602
@@ -1,115 +1,139 b''
1 Verify that pending changesets are seen by pretxn* hooks but not by other
1 Verify that pending changesets are seen by pretxn* hooks but not by other
2 processes that access the destination repo while the hooks are running.
2 processes that access the destination repo while the hooks are running.
3
3
4 The hooks (python and external) both reject changesets after some think time,
4 The hooks (python and external) both reject changesets after some think time,
5 during which another process runs pull. Each hook creates a file ('notify') to
5 during which another process runs pull. Each hook creates a file ('notify') to
6 indicate to the controlling process that it is running; the process removes the
6 indicate to the controlling process that it is running; the process removes the
7 file to indicate the hook can terminate.
7 file to indicate the hook can terminate.
8
8
9 init env vars
9 init env vars
10
10
11 $ d=`pwd`
11 $ d=`pwd`
12 $ maxwait=20
12 $ maxwait=20
13
13
14 utility to run the test - start a push in the background and run pull
14 utility to run the test - start a push in the background and run pull
15
15
16 $ dotest() {
16 $ dotest() {
17 > rm -f notify
17 > rm -f notify
18 > printf 'push '; hg -R child-push tip --template '{node}\n'
18 > printf 'push '; hg -R child-push tip --template '{node}\n'
19 > hg -R child-push -q push > push.out 2>&1 &
19 > hg -R child-push -q push > push.out 2>&1 &
20 >
20 >
21 > # wait for hook to create the notify file
21 > # wait for hook to create the notify file
22 > i=$maxwait
22 > i=$maxwait
23 > while [ ! -f notify -a $i != 0 ]; do
23 > while [ ! -f notify -a $i != 0 ]; do
24 > sleep 1
24 > sleep 1
25 > i=`expr $i - 1`
25 > i=`expr $i - 1`
26 > done
26 > done
27 >
27 >
28 > # run pull
28 > # run pull
29 > hg -R child-pull -q pull
29 > hg -R child-pull -q pull
30 > rc=$?
30 > rc=$?
31 >
31 >
32 > # tell hook to finish; notify should exist.
32 > # tell hook to finish; notify should exist.
33 > rm notify
33 > rm notify
34 > wait
34 > wait
35 >
35 >
36 > cat push.out
36 > cat push.out
37 > printf 'pull '; hg -R child-pull tip --template '{node}\n'
37 > printf 'pull '; hg -R child-pull tip --template '{node}\n'
38 > return $rc
38 > return $rc
39 > }
39 > }
40
40
41 python hook
41 python hook
42
42
43 $ cat <<EOF > reject.py
43 $ cat <<EOF > reject.py
44 > import os, time
44 > import os, time
45 > from mercurial import ui, localrepo
45 > from mercurial import ui, localrepo
46 > def rejecthook(ui, repo, hooktype, node, **opts):
46 > def rejecthook(ui, repo, hooktype, node, **opts):
47 > ui.write('hook %s\\n' % repo['tip'].hex())
47 > ui.write('hook %s\\n' % repo['tip'].hex())
48 > # create the notify file so caller knows we're running
48 > # create the notify file so caller knows we're running
49 > fpath = os.path.join('$d', 'notify')
49 > fpath = os.path.join('$d', 'notify')
50 > f = open(fpath, 'w')
50 > f = open(fpath, 'w')
51 > f.close()
51 > f.close()
52 > # wait for ack - caller should delete the notify file
52 > # wait for ack - caller should delete the notify file
53 > i = $maxwait
53 > i = $maxwait
54 > while os.path.exists(fpath) and i > 0:
54 > while os.path.exists(fpath) and i > 0:
55 > time.sleep(1)
55 > time.sleep(1)
56 > i -= 1
56 > i -= 1
57 > return True # reject the changesets
57 > return True # reject the changesets
58 > EOF
58 > EOF
59
59
60 external hook
60 external hook
61
61
62 $ cat <<EOF > reject.sh
62 $ cat <<EOF > reject.sh
63 > printf 'hook '; hg tip --template '{node}\\n'
63 > printf 'hook '; hg tip --template '{node}\\n'
64 > # create the notify file so caller knows we're running
64 > # create the notify file so caller knows we're running
65 > fpath=$d/notify
65 > fpath=$d/notify
66 > touch \$fpath
66 > touch \$fpath
67 > # wait for ack - caller should delete the notify file
67 > # wait for ack - caller should delete the notify file
68 > i=$maxwait
68 > i=$maxwait
69 > while [ -f \$fpath -a \$i != 0 ]; do
69 > while [ -f \$fpath -a \$i != 0 ]; do
70 > sleep 1
70 > sleep 1
71 > i=\`expr \$i - 1\`
71 > i=\`expr \$i - 1\`
72 > done
72 > done
73 > exit 1 # reject the changesets
73 > exit 1 # reject the changesets
74 > EOF
74 > EOF
75
75
76 create repos
76 create repos
77
77
78 $ hg init parent
78 $ hg init parent
79 $ hg clone -q parent child-push
79 $ hg clone -q parent child-push
80 $ hg clone -q parent child-pull
80 $ hg clone -q parent child-pull
81 $ echo a > child-push/a
81 $ echo a > child-push/a
82 $ hg -R child-push add child-push/a
82 $ hg -R child-push add child-push/a
83 $ hg -R child-push commit -m a -d '1000000 0'
83 $ hg -R child-push commit -m a -d '1000000 0'
84
84
85 test python hook
85 test python hook
86
86
87 $ cat <<EOF > parent/.hg/hgrc
87 $ cat <<EOF > parent/.hg/hgrc
88 > [extensions]
88 > [extensions]
89 > reject = $d/reject.py
89 > reject = $d/reject.py
90 > [hooks]
90 > [hooks]
91 > pretxnchangegroup = python:reject.rejecthook
91 > pretxnchangegroup = python:reject.rejecthook
92 > EOF
92 > EOF
93
93
94 $ dotest
94 $ dotest
95 push 29b62aeb769fdf78d8d9c5f28b017f76d7ef824b
95 push 29b62aeb769fdf78d8d9c5f28b017f76d7ef824b
96 hook 29b62aeb769fdf78d8d9c5f28b017f76d7ef824b
96 hook 29b62aeb769fdf78d8d9c5f28b017f76d7ef824b
97 transaction abort!
97 transaction abort!
98 rollback completed
98 rollback completed
99 abort: pretxnchangegroup hook failed
99 abort: pretxnchangegroup hook failed
100 pull 0000000000000000000000000000000000000000
100 pull 0000000000000000000000000000000000000000
101
101
102 test external hook
102 test external hook
103
103
104 $ cat <<EOF > parent/.hg/hgrc
104 $ cat <<EOF > parent/.hg/hgrc
105 > [hooks]
105 > [hooks]
106 > pretxnchangegroup = sh $d/reject.sh
106 > pretxnchangegroup = sh $d/reject.sh
107 > EOF
107 > EOF
108
108
109 $ dotest
109 $ dotest
110 push 29b62aeb769fdf78d8d9c5f28b017f76d7ef824b
110 push 29b62aeb769fdf78d8d9c5f28b017f76d7ef824b
111 hook 29b62aeb769fdf78d8d9c5f28b017f76d7ef824b
111 hook 29b62aeb769fdf78d8d9c5f28b017f76d7ef824b
112 transaction abort!
112 transaction abort!
113 rollback completed
113 rollback completed
114 abort: pretxnchangegroup hook exited with status 1
114 abort: pretxnchangegroup hook exited with status 1
115 pull 0000000000000000000000000000000000000000
115 pull 0000000000000000000000000000000000000000
116
117 Test that pending on transaction without changegroup see the normal changegroup(
118 (issue4609)
119
120 $ cat <<EOF > parent/.hg/hgrc
121 > [hooks]
122 > pretxnchangegroup=
123 > pretxnclose = hg tip -T 'tip: {node|short}\n'
124 > [phases]
125 > publishing=False
126 > EOF
127
128 setup
129
130 $ cd parent
131 $ echo a > a
132 $ hg add a
133 $ hg commit -m a
134 tip: cb9a9f314b8b
135
136 actual test
137
138 $ hg phase --public .
139 tip: cb9a9f314b8b
General Comments 0
You need to be logged in to leave comments. Login now