##// END OF EJS Templates
phases: remove excessive optimization from newheads() (issue5939)...
Yuya Nishihara -
r38941:88efb7d6 default
parent child Browse files
Show More
@@ -1,700 +1,699 b''
1 1 """ Mercurial phases support code
2 2
3 3 ---
4 4
5 5 Copyright 2011 Pierre-Yves David <pierre-yves.david@ens-lyon.org>
6 6 Logilab SA <contact@logilab.fr>
7 7 Augie Fackler <durin42@gmail.com>
8 8
9 9 This software may be used and distributed according to the terms
10 10 of the GNU General Public License version 2 or any later version.
11 11
12 12 ---
13 13
14 14 This module implements most phase logic in mercurial.
15 15
16 16
17 17 Basic Concept
18 18 =============
19 19
20 20 A 'changeset phase' is an indicator that tells us how a changeset is
21 21 manipulated and communicated. The details of each phase is described
22 22 below, here we describe the properties they have in common.
23 23
24 24 Like bookmarks, phases are not stored in history and thus are not
25 25 permanent and leave no audit trail.
26 26
27 27 First, no changeset can be in two phases at once. Phases are ordered,
28 28 so they can be considered from lowest to highest. The default, lowest
29 29 phase is 'public' - this is the normal phase of existing changesets. A
30 30 child changeset can not be in a lower phase than its parents.
31 31
32 32 These phases share a hierarchy of traits:
33 33
34 34 immutable shared
35 35 public: X X
36 36 draft: X
37 37 secret:
38 38
39 39 Local commits are draft by default.
40 40
41 41 Phase Movement and Exchange
42 42 ===========================
43 43
44 44 Phase data is exchanged by pushkey on pull and push. Some servers have
45 45 a publish option set, we call such a server a "publishing server".
46 46 Pushing a draft changeset to a publishing server changes the phase to
47 47 public.
48 48
49 49 A small list of fact/rules define the exchange of phase:
50 50
51 51 * old client never changes server states
52 52 * pull never changes server states
53 53 * publish and old server changesets are seen as public by client
54 54 * any secret changeset seen in another repository is lowered to at
55 55 least draft
56 56
57 57 Here is the final table summing up the 49 possible use cases of phase
58 58 exchange:
59 59
60 60 server
61 61 old publish non-publish
62 62 N X N D P N D P
63 63 old client
64 64 pull
65 65 N - X/X - X/D X/P - X/D X/P
66 66 X - X/X - X/D X/P - X/D X/P
67 67 push
68 68 X X/X X/X X/P X/P X/P X/D X/D X/P
69 69 new client
70 70 pull
71 71 N - P/X - P/D P/P - D/D P/P
72 72 D - P/X - P/D P/P - D/D P/P
73 73 P - P/X - P/D P/P - P/D P/P
74 74 push
75 75 D P/X P/X P/P P/P P/P D/D D/D P/P
76 76 P P/X P/X P/P P/P P/P P/P P/P P/P
77 77
78 78 Legend:
79 79
80 80 A/B = final state on client / state on server
81 81
82 82 * N = new/not present,
83 83 * P = public,
84 84 * D = draft,
85 85 * X = not tracked (i.e., the old client or server has no internal
86 86 way of recording the phase.)
87 87
88 88 passive = only pushes
89 89
90 90
91 91 A cell here can be read like this:
92 92
93 93 "When a new client pushes a draft changeset (D) to a publishing
94 94 server where it's not present (N), it's marked public on both
95 95 sides (P/P)."
96 96
97 97 Note: old client behave as a publishing server with draft only content
98 98 - other people see it as public
99 99 - content is pushed as draft
100 100
101 101 """
102 102
103 103 from __future__ import absolute_import
104 104
105 105 import errno
106 106 import struct
107 107
108 108 from .i18n import _
109 109 from .node import (
110 110 bin,
111 111 hex,
112 112 nullid,
113 113 nullrev,
114 114 short,
115 115 )
116 116 from . import (
117 117 error,
118 118 pycompat,
119 119 smartset,
120 120 txnutil,
121 121 util,
122 122 )
123 123
124 124 _fphasesentry = struct.Struct('>i20s')
125 125
126 126 allphases = public, draft, secret = range(3)
127 127 trackedphases = allphases[1:]
128 128 phasenames = ['public', 'draft', 'secret']
129 129 mutablephases = tuple(allphases[1:])
130 130 remotehiddenphases = tuple(allphases[2:])
131 131
132 132 def _readroots(repo, phasedefaults=None):
133 133 """Read phase roots from disk
134 134
135 135 phasedefaults is a list of fn(repo, roots) callable, which are
136 136 executed if the phase roots file does not exist. When phases are
137 137 being initialized on an existing repository, this could be used to
138 138 set selected changesets phase to something else than public.
139 139
140 140 Return (roots, dirty) where dirty is true if roots differ from
141 141 what is being stored.
142 142 """
143 143 repo = repo.unfiltered()
144 144 dirty = False
145 145 roots = [set() for i in allphases]
146 146 try:
147 147 f, pending = txnutil.trypending(repo.root, repo.svfs, 'phaseroots')
148 148 try:
149 149 for line in f:
150 150 phase, nh = line.split()
151 151 roots[int(phase)].add(bin(nh))
152 152 finally:
153 153 f.close()
154 154 except IOError as inst:
155 155 if inst.errno != errno.ENOENT:
156 156 raise
157 157 if phasedefaults:
158 158 for f in phasedefaults:
159 159 roots = f(repo, roots)
160 160 dirty = True
161 161 return roots, dirty
162 162
163 163 def binaryencode(phasemapping):
164 164 """encode a 'phase -> nodes' mapping into a binary stream
165 165
166 166 Since phases are integer the mapping is actually a python list:
167 167 [[PUBLIC_HEADS], [DRAFTS_HEADS], [SECRET_HEADS]]
168 168 """
169 169 binarydata = []
170 170 for phase, nodes in enumerate(phasemapping):
171 171 for head in nodes:
172 172 binarydata.append(_fphasesentry.pack(phase, head))
173 173 return ''.join(binarydata)
174 174
175 175 def binarydecode(stream):
176 176 """decode a binary stream into a 'phase -> nodes' mapping
177 177
178 178 Since phases are integer the mapping is actually a python list."""
179 179 headsbyphase = [[] for i in allphases]
180 180 entrysize = _fphasesentry.size
181 181 while True:
182 182 entry = stream.read(entrysize)
183 183 if len(entry) < entrysize:
184 184 if entry:
185 185 raise error.Abort(_('bad phase-heads stream'))
186 186 break
187 187 phase, node = _fphasesentry.unpack(entry)
188 188 headsbyphase[phase].append(node)
189 189 return headsbyphase
190 190
191 191 def _trackphasechange(data, rev, old, new):
192 192 """add a phase move the <data> dictionnary
193 193
194 194 If data is None, nothing happens.
195 195 """
196 196 if data is None:
197 197 return
198 198 existing = data.get(rev)
199 199 if existing is not None:
200 200 old = existing[0]
201 201 data[rev] = (old, new)
202 202
203 203 class phasecache(object):
204 204 def __init__(self, repo, phasedefaults, _load=True):
205 205 if _load:
206 206 # Cheap trick to allow shallow-copy without copy module
207 207 self.phaseroots, self.dirty = _readroots(repo, phasedefaults)
208 208 self._loadedrevslen = 0
209 209 self._phasesets = None
210 210 self.filterunknown(repo)
211 211 self.opener = repo.svfs
212 212
213 213 def getrevset(self, repo, phases, subset=None):
214 214 """return a smartset for the given phases"""
215 215 self.loadphaserevs(repo) # ensure phase's sets are loaded
216 216 phases = set(phases)
217 217 if public not in phases:
218 218 # fast path: _phasesets contains the interesting sets,
219 219 # might only need a union and post-filtering.
220 220 if len(phases) == 1:
221 221 [p] = phases
222 222 revs = self._phasesets[p]
223 223 else:
224 224 revs = set.union(*[self._phasesets[p] for p in phases])
225 225 if repo.changelog.filteredrevs:
226 226 revs = revs - repo.changelog.filteredrevs
227 227 if subset is None:
228 228 return smartset.baseset(revs)
229 229 else:
230 230 return subset & smartset.baseset(revs)
231 231 else:
232 232 phases = set(allphases).difference(phases)
233 233 if not phases:
234 234 return smartset.fullreposet(repo)
235 235 if len(phases) == 1:
236 236 [p] = phases
237 237 revs = self._phasesets[p]
238 238 else:
239 239 revs = set.union(*[self._phasesets[p] for p in phases])
240 240 if subset is None:
241 241 subset = smartset.fullreposet(repo)
242 242 if not revs:
243 243 return subset
244 244 return subset.filter(lambda r: r not in revs)
245 245
246 246 def copy(self):
247 247 # Shallow copy meant to ensure isolation in
248 248 # advance/retractboundary(), nothing more.
249 249 ph = self.__class__(None, None, _load=False)
250 250 ph.phaseroots = self.phaseroots[:]
251 251 ph.dirty = self.dirty
252 252 ph.opener = self.opener
253 253 ph._loadedrevslen = self._loadedrevslen
254 254 ph._phasesets = self._phasesets
255 255 return ph
256 256
257 257 def replace(self, phcache):
258 258 """replace all values in 'self' with content of phcache"""
259 259 for a in ('phaseroots', 'dirty', 'opener', '_loadedrevslen',
260 260 '_phasesets'):
261 261 setattr(self, a, getattr(phcache, a))
262 262
263 263 def _getphaserevsnative(self, repo):
264 264 repo = repo.unfiltered()
265 265 nativeroots = []
266 266 for phase in trackedphases:
267 267 nativeroots.append(pycompat.maplist(repo.changelog.rev,
268 268 self.phaseroots[phase]))
269 269 return repo.changelog.computephases(nativeroots)
270 270
271 271 def _computephaserevspure(self, repo):
272 272 repo = repo.unfiltered()
273 273 cl = repo.changelog
274 274 self._phasesets = [set() for phase in allphases]
275 275 roots = pycompat.maplist(cl.rev, self.phaseroots[secret])
276 276 if roots:
277 277 ps = set(cl.descendants(roots))
278 278 for root in roots:
279 279 ps.add(root)
280 280 self._phasesets[secret] = ps
281 281 roots = pycompat.maplist(cl.rev, self.phaseroots[draft])
282 282 if roots:
283 283 ps = set(cl.descendants(roots))
284 284 for root in roots:
285 285 ps.add(root)
286 286 ps.difference_update(self._phasesets[secret])
287 287 self._phasesets[draft] = ps
288 288 self._loadedrevslen = len(cl)
289 289
290 290 def loadphaserevs(self, repo):
291 291 """ensure phase information is loaded in the object"""
292 292 if self._phasesets is None:
293 293 try:
294 294 res = self._getphaserevsnative(repo)
295 295 self._loadedrevslen, self._phasesets = res
296 296 except AttributeError:
297 297 self._computephaserevspure(repo)
298 298
299 299 def invalidate(self):
300 300 self._loadedrevslen = 0
301 301 self._phasesets = None
302 302
303 303 def phase(self, repo, rev):
304 304 # We need a repo argument here to be able to build _phasesets
305 305 # if necessary. The repository instance is not stored in
306 306 # phasecache to avoid reference cycles. The changelog instance
307 307 # is not stored because it is a filecache() property and can
308 308 # be replaced without us being notified.
309 309 if rev == nullrev:
310 310 return public
311 311 if rev < nullrev:
312 312 raise ValueError(_('cannot lookup negative revision'))
313 313 if rev >= self._loadedrevslen:
314 314 self.invalidate()
315 315 self.loadphaserevs(repo)
316 316 for phase in trackedphases:
317 317 if rev in self._phasesets[phase]:
318 318 return phase
319 319 return public
320 320
321 321 def write(self):
322 322 if not self.dirty:
323 323 return
324 324 f = self.opener('phaseroots', 'w', atomictemp=True, checkambig=True)
325 325 try:
326 326 self._write(f)
327 327 finally:
328 328 f.close()
329 329
330 330 def _write(self, fp):
331 331 for phase, roots in enumerate(self.phaseroots):
332 332 for h in sorted(roots):
333 333 fp.write('%i %s\n' % (phase, hex(h)))
334 334 self.dirty = False
335 335
336 336 def _updateroots(self, phase, newroots, tr):
337 337 self.phaseroots[phase] = newroots
338 338 self.invalidate()
339 339 self.dirty = True
340 340
341 341 tr.addfilegenerator('phase', ('phaseroots',), self._write)
342 342 tr.hookargs['phases_moved'] = '1'
343 343
344 344 def registernew(self, repo, tr, targetphase, nodes):
345 345 repo = repo.unfiltered()
346 346 self._retractboundary(repo, tr, targetphase, nodes)
347 347 if tr is not None and 'phases' in tr.changes:
348 348 phasetracking = tr.changes['phases']
349 349 torev = repo.changelog.rev
350 350 phase = self.phase
351 351 for n in nodes:
352 352 rev = torev(n)
353 353 revphase = phase(repo, rev)
354 354 _trackphasechange(phasetracking, rev, None, revphase)
355 355 repo.invalidatevolatilesets()
356 356
357 357 def advanceboundary(self, repo, tr, targetphase, nodes, dryrun=None):
358 358 """Set all 'nodes' to phase 'targetphase'
359 359
360 360 Nodes with a phase lower than 'targetphase' are not affected.
361 361
362 362 If dryrun is True, no actions will be performed
363 363
364 364 Returns a set of revs whose phase is changed or should be changed
365 365 """
366 366 # Be careful to preserve shallow-copied values: do not update
367 367 # phaseroots values, replace them.
368 368 if tr is None:
369 369 phasetracking = None
370 370 else:
371 371 phasetracking = tr.changes.get('phases')
372 372
373 373 repo = repo.unfiltered()
374 374
375 375 changes = set() # set of revisions to be changed
376 376 delroots = [] # set of root deleted by this path
377 377 for phase in xrange(targetphase + 1, len(allphases)):
378 378 # filter nodes that are not in a compatible phase already
379 379 nodes = [n for n in nodes
380 380 if self.phase(repo, repo[n].rev()) >= phase]
381 381 if not nodes:
382 382 break # no roots to move anymore
383 383
384 384 olds = self.phaseroots[phase]
385 385
386 386 affected = repo.revs('%ln::%ln', olds, nodes)
387 387 changes.update(affected)
388 388 if dryrun:
389 389 continue
390 390 for r in affected:
391 391 _trackphasechange(phasetracking, r, self.phase(repo, r),
392 392 targetphase)
393 393
394 394 roots = set(ctx.node() for ctx in repo.set(
395 395 'roots((%ln::) - %ld)', olds, affected))
396 396 if olds != roots:
397 397 self._updateroots(phase, roots, tr)
398 398 # some roots may need to be declared for lower phases
399 399 delroots.extend(olds - roots)
400 400 if not dryrun:
401 401 # declare deleted root in the target phase
402 402 if targetphase != 0:
403 403 self._retractboundary(repo, tr, targetphase, delroots)
404 404 repo.invalidatevolatilesets()
405 405 return changes
406 406
407 407 def retractboundary(self, repo, tr, targetphase, nodes):
408 408 oldroots = self.phaseroots[:targetphase + 1]
409 409 if tr is None:
410 410 phasetracking = None
411 411 else:
412 412 phasetracking = tr.changes.get('phases')
413 413 repo = repo.unfiltered()
414 414 if (self._retractboundary(repo, tr, targetphase, nodes)
415 415 and phasetracking is not None):
416 416
417 417 # find the affected revisions
418 418 new = self.phaseroots[targetphase]
419 419 old = oldroots[targetphase]
420 420 affected = set(repo.revs('(%ln::) - (%ln::)', new, old))
421 421
422 422 # find the phase of the affected revision
423 423 for phase in xrange(targetphase, -1, -1):
424 424 if phase:
425 425 roots = oldroots[phase]
426 426 revs = set(repo.revs('%ln::%ld', roots, affected))
427 427 affected -= revs
428 428 else: # public phase
429 429 revs = affected
430 430 for r in revs:
431 431 _trackphasechange(phasetracking, r, phase, targetphase)
432 432 repo.invalidatevolatilesets()
433 433
434 434 def _retractboundary(self, repo, tr, targetphase, nodes):
435 435 # Be careful to preserve shallow-copied values: do not update
436 436 # phaseroots values, replace them.
437 437
438 438 repo = repo.unfiltered()
439 439 currentroots = self.phaseroots[targetphase]
440 440 finalroots = oldroots = set(currentroots)
441 441 newroots = [n for n in nodes
442 442 if self.phase(repo, repo[n].rev()) < targetphase]
443 443 if newroots:
444 444
445 445 if nullid in newroots:
446 446 raise error.Abort(_('cannot change null revision phase'))
447 447 currentroots = currentroots.copy()
448 448 currentroots.update(newroots)
449 449
450 450 # Only compute new roots for revs above the roots that are being
451 451 # retracted.
452 452 minnewroot = min(repo[n].rev() for n in newroots)
453 453 aboveroots = [n for n in currentroots
454 454 if repo[n].rev() >= minnewroot]
455 455 updatedroots = repo.set('roots(%ln::)', aboveroots)
456 456
457 457 finalroots = set(n for n in currentroots if repo[n].rev() <
458 458 minnewroot)
459 459 finalroots.update(ctx.node() for ctx in updatedroots)
460 460 if finalroots != oldroots:
461 461 self._updateroots(targetphase, finalroots, tr)
462 462 return True
463 463 return False
464 464
465 465 def filterunknown(self, repo):
466 466 """remove unknown nodes from the phase boundary
467 467
468 468 Nothing is lost as unknown nodes only hold data for their descendants.
469 469 """
470 470 filtered = False
471 471 nodemap = repo.changelog.nodemap # to filter unknown nodes
472 472 for phase, nodes in enumerate(self.phaseroots):
473 473 missing = sorted(node for node in nodes if node not in nodemap)
474 474 if missing:
475 475 for mnode in missing:
476 476 repo.ui.debug(
477 477 'removing unknown node %s from %i-phase boundary\n'
478 478 % (short(mnode), phase))
479 479 nodes.symmetric_difference_update(missing)
480 480 filtered = True
481 481 if filtered:
482 482 self.dirty = True
483 483 # filterunknown is called by repo.destroyed, we may have no changes in
484 484 # root but _phasesets contents is certainly invalid (or at least we
485 485 # have not proper way to check that). related to issue 3858.
486 486 #
487 487 # The other caller is __init__ that have no _phasesets initialized
488 488 # anyway. If this change we should consider adding a dedicated
489 489 # "destroyed" function to phasecache or a proper cache key mechanism
490 490 # (see branchmap one)
491 491 self.invalidate()
492 492
493 493 def advanceboundary(repo, tr, targetphase, nodes, dryrun=None):
494 494 """Add nodes to a phase changing other nodes phases if necessary.
495 495
496 496 This function move boundary *forward* this means that all nodes
497 497 are set in the target phase or kept in a *lower* phase.
498 498
499 499 Simplify boundary to contains phase roots only.
500 500
501 501 If dryrun is True, no actions will be performed
502 502
503 503 Returns a set of revs whose phase is changed or should be changed
504 504 """
505 505 phcache = repo._phasecache.copy()
506 506 changes = phcache.advanceboundary(repo, tr, targetphase, nodes,
507 507 dryrun=dryrun)
508 508 if not dryrun:
509 509 repo._phasecache.replace(phcache)
510 510 return changes
511 511
512 512 def retractboundary(repo, tr, targetphase, nodes):
513 513 """Set nodes back to a phase changing other nodes phases if
514 514 necessary.
515 515
516 516 This function move boundary *backward* this means that all nodes
517 517 are set in the target phase or kept in a *higher* phase.
518 518
519 519 Simplify boundary to contains phase roots only."""
520 520 phcache = repo._phasecache.copy()
521 521 phcache.retractboundary(repo, tr, targetphase, nodes)
522 522 repo._phasecache.replace(phcache)
523 523
524 524 def registernew(repo, tr, targetphase, nodes):
525 525 """register a new revision and its phase
526 526
527 527 Code adding revisions to the repository should use this function to
528 528 set new changeset in their target phase (or higher).
529 529 """
530 530 phcache = repo._phasecache.copy()
531 531 phcache.registernew(repo, tr, targetphase, nodes)
532 532 repo._phasecache.replace(phcache)
533 533
534 534 def listphases(repo):
535 535 """List phases root for serialization over pushkey"""
536 536 # Use ordered dictionary so behavior is deterministic.
537 537 keys = util.sortdict()
538 538 value = '%i' % draft
539 539 cl = repo.unfiltered().changelog
540 540 for root in repo._phasecache.phaseroots[draft]:
541 541 if repo._phasecache.phase(repo, cl.rev(root)) <= draft:
542 542 keys[hex(root)] = value
543 543
544 544 if repo.publishing():
545 545 # Add an extra data to let remote know we are a publishing
546 546 # repo. Publishing repo can't just pretend they are old repo.
547 547 # When pushing to a publishing repo, the client still need to
548 548 # push phase boundary
549 549 #
550 550 # Push do not only push changeset. It also push phase data.
551 551 # New phase data may apply to common changeset which won't be
552 552 # push (as they are common). Here is a very simple example:
553 553 #
554 554 # 1) repo A push changeset X as draft to repo B
555 555 # 2) repo B make changeset X public
556 556 # 3) repo B push to repo A. X is not pushed but the data that
557 557 # X as now public should
558 558 #
559 559 # The server can't handle it on it's own as it has no idea of
560 560 # client phase data.
561 561 keys['publishing'] = 'True'
562 562 return keys
563 563
564 564 def pushphase(repo, nhex, oldphasestr, newphasestr):
565 565 """List phases root for serialization over pushkey"""
566 566 repo = repo.unfiltered()
567 567 with repo.lock():
568 568 currentphase = repo[nhex].phase()
569 569 newphase = abs(int(newphasestr)) # let's avoid negative index surprise
570 570 oldphase = abs(int(oldphasestr)) # let's avoid negative index surprise
571 571 if currentphase == oldphase and newphase < oldphase:
572 572 with repo.transaction('pushkey-phase') as tr:
573 573 advanceboundary(repo, tr, newphase, [bin(nhex)])
574 574 return True
575 575 elif currentphase == newphase:
576 576 # raced, but got correct result
577 577 return True
578 578 else:
579 579 return False
580 580
581 581 def subsetphaseheads(repo, subset):
582 582 """Finds the phase heads for a subset of a history
583 583
584 584 Returns a list indexed by phase number where each item is a list of phase
585 585 head nodes.
586 586 """
587 587 cl = repo.changelog
588 588
589 589 headsbyphase = [[] for i in allphases]
590 590 # No need to keep track of secret phase; any heads in the subset that
591 591 # are not mentioned are implicitly secret.
592 592 for phase in allphases[:-1]:
593 593 revset = "heads(%%ln & %s())" % phasenames[phase]
594 594 headsbyphase[phase] = [cl.node(r) for r in repo.revs(revset, subset)]
595 595 return headsbyphase
596 596
597 597 def updatephases(repo, trgetter, headsbyphase):
598 598 """Updates the repo with the given phase heads"""
599 599 # Now advance phase boundaries of all but secret phase
600 600 #
601 601 # run the update (and fetch transaction) only if there are actually things
602 602 # to update. This avoid creating empty transaction during no-op operation.
603 603
604 604 for phase in allphases[:-1]:
605 605 revset = '%%ln - %s()' % phasenames[phase]
606 606 heads = [c.node() for c in repo.set(revset, headsbyphase[phase])]
607 607 if heads:
608 608 advanceboundary(repo, trgetter(), phase, heads)
609 609
610 610 def analyzeremotephases(repo, subset, roots):
611 611 """Compute phases heads and root in a subset of node from root dict
612 612
613 613 * subset is heads of the subset
614 614 * roots is {<nodeid> => phase} mapping. key and value are string.
615 615
616 616 Accept unknown element input
617 617 """
618 618 repo = repo.unfiltered()
619 619 # build list from dictionary
620 620 draftroots = []
621 621 nodemap = repo.changelog.nodemap # to filter unknown nodes
622 622 for nhex, phase in roots.iteritems():
623 623 if nhex == 'publishing': # ignore data related to publish option
624 624 continue
625 625 node = bin(nhex)
626 626 phase = int(phase)
627 627 if phase == public:
628 628 if node != nullid:
629 629 repo.ui.warn(_('ignoring inconsistent public root'
630 630 ' from remote: %s\n') % nhex)
631 631 elif phase == draft:
632 632 if node in nodemap:
633 633 draftroots.append(node)
634 634 else:
635 635 repo.ui.warn(_('ignoring unexpected root from remote: %i %s\n')
636 636 % (phase, nhex))
637 637 # compute heads
638 638 publicheads = newheads(repo, subset, draftroots)
639 639 return publicheads, draftroots
640 640
641 641 class remotephasessummary(object):
642 642 """summarize phase information on the remote side
643 643
644 644 :publishing: True is the remote is publishing
645 645 :publicheads: list of remote public phase heads (nodes)
646 646 :draftheads: list of remote draft phase heads (nodes)
647 647 :draftroots: list of remote draft phase root (nodes)
648 648 """
649 649
650 650 def __init__(self, repo, remotesubset, remoteroots):
651 651 unfi = repo.unfiltered()
652 652 self._allremoteroots = remoteroots
653 653
654 654 self.publishing = remoteroots.get('publishing', False)
655 655
656 656 ana = analyzeremotephases(repo, remotesubset, remoteroots)
657 657 self.publicheads, self.draftroots = ana
658 658 # Get the list of all "heads" revs draft on remote
659 659 dheads = unfi.set('heads(%ln::%ln)', self.draftroots, remotesubset)
660 660 self.draftheads = [c.node() for c in dheads]
661 661
662 662 def newheads(repo, heads, roots):
663 663 """compute new head of a subset minus another
664 664
665 665 * `heads`: define the first subset
666 666 * `roots`: define the second we subtract from the first"""
667 667 repo = repo.unfiltered()
668 revset = repo.set('heads((%ln + parents(%ln)) - (%ln::%ln))',
669 heads, roots, roots, heads)
668 revset = repo.set('heads(::%ln - (%ln::%ln))', heads, roots, heads)
670 669 return [c.node() for c in revset]
671 670
672 671
673 672 def newcommitphase(ui):
674 673 """helper to get the target phase of new commit
675 674
676 675 Handle all possible values for the phases.new-commit options.
677 676
678 677 """
679 678 v = ui.config('phases', 'new-commit')
680 679 try:
681 680 return phasenames.index(v)
682 681 except ValueError:
683 682 try:
684 683 return int(v)
685 684 except ValueError:
686 685 msg = _("phases.new-commit: not a valid phase name ('%s')")
687 686 raise error.ConfigError(msg % v)
688 687
689 688 def hassecret(repo):
690 689 """utility function that check if a repo have any secret changeset."""
691 690 return bool(repo._phasecache.phaseroots[2])
692 691
693 692 def preparehookargs(node, old, new):
694 693 if old is None:
695 694 old = ''
696 695 else:
697 696 old = phasenames[old]
698 697 return {'node': node,
699 698 'oldphase': old,
700 699 'phase': phasenames[new]}
@@ -1,1559 +1,1561 b''
1 1 $ cat >> $HGRCPATH << EOF
2 2 > [extensions]
3 3 > drawdag=$TESTDIR/drawdag.py
4 4 > phasereport=$TESTDIR/testlib/ext-phase-report.py
5 5 > EOF
6 6
7 7 $ hgph() { hg log -G --template "{rev} {phase} {desc} - {node|short}\n" $*; }
8 8
9 9 $ mkcommit() {
10 10 > echo "$1" > "$1"
11 11 > hg add "$1"
12 12 > message="$1"
13 13 > shift
14 14 > hg ci -m "$message" $*
15 15 > }
16 16
17 17 $ hg init alpha
18 18 $ cd alpha
19 19 $ mkcommit a-A
20 20 test-debug-phase: new rev 0: x -> 1
21 21 $ mkcommit a-B
22 22 test-debug-phase: new rev 1: x -> 1
23 23 $ mkcommit a-C
24 24 test-debug-phase: new rev 2: x -> 1
25 25 $ mkcommit a-D
26 26 test-debug-phase: new rev 3: x -> 1
27 27 $ hgph
28 28 @ 3 draft a-D - b555f63b6063
29 29 |
30 30 o 2 draft a-C - 54acac6f23ab
31 31 |
32 32 o 1 draft a-B - 548a3d25dbf0
33 33 |
34 34 o 0 draft a-A - 054250a37db4
35 35
36 36
37 37 $ hg init ../beta
38 38 $ hg push -r 1 ../beta
39 39 pushing to ../beta
40 40 searching for changes
41 41 adding changesets
42 42 adding manifests
43 43 adding file changes
44 44 added 2 changesets with 2 changes to 2 files
45 45 test-debug-phase: new rev 0: x -> 0
46 46 test-debug-phase: new rev 1: x -> 0
47 47 test-debug-phase: move rev 0: 1 -> 0
48 48 test-debug-phase: move rev 1: 1 -> 0
49 49 $ hgph
50 50 @ 3 draft a-D - b555f63b6063
51 51 |
52 52 o 2 draft a-C - 54acac6f23ab
53 53 |
54 54 o 1 public a-B - 548a3d25dbf0
55 55 |
56 56 o 0 public a-A - 054250a37db4
57 57
58 58
59 59 $ cd ../beta
60 60 $ hgph
61 61 o 1 public a-B - 548a3d25dbf0
62 62 |
63 63 o 0 public a-A - 054250a37db4
64 64
65 65 $ hg up -q
66 66 $ mkcommit b-A
67 67 test-debug-phase: new rev 2: x -> 1
68 68 $ hgph
69 69 @ 2 draft b-A - f54f1bb90ff3
70 70 |
71 71 o 1 public a-B - 548a3d25dbf0
72 72 |
73 73 o 0 public a-A - 054250a37db4
74 74
75 75 $ hg pull ../alpha
76 76 pulling from ../alpha
77 77 searching for changes
78 78 adding changesets
79 79 adding manifests
80 80 adding file changes
81 81 added 2 changesets with 2 changes to 2 files (+1 heads)
82 82 new changesets 54acac6f23ab:b555f63b6063
83 83 test-debug-phase: new rev 3: x -> 0
84 84 test-debug-phase: new rev 4: x -> 0
85 85 (run 'hg heads' to see heads, 'hg merge' to merge)
86 86 $ hgph
87 87 o 4 public a-D - b555f63b6063
88 88 |
89 89 o 3 public a-C - 54acac6f23ab
90 90 |
91 91 | @ 2 draft b-A - f54f1bb90ff3
92 92 |/
93 93 o 1 public a-B - 548a3d25dbf0
94 94 |
95 95 o 0 public a-A - 054250a37db4
96 96
97 97
98 98 pull did not updated ../alpha state.
99 99 push from alpha to beta should update phase even if nothing is transferred
100 100
101 101 $ cd ../alpha
102 102 $ hgph # not updated by remote pull
103 103 @ 3 draft a-D - b555f63b6063
104 104 |
105 105 o 2 draft a-C - 54acac6f23ab
106 106 |
107 107 o 1 public a-B - 548a3d25dbf0
108 108 |
109 109 o 0 public a-A - 054250a37db4
110 110
111 111 $ hg push -r 2 ../beta
112 112 pushing to ../beta
113 113 searching for changes
114 114 no changes found
115 115 test-debug-phase: move rev 2: 1 -> 0
116 116 [1]
117 117 $ hgph
118 118 @ 3 draft a-D - b555f63b6063
119 119 |
120 120 o 2 public a-C - 54acac6f23ab
121 121 |
122 122 o 1 public a-B - 548a3d25dbf0
123 123 |
124 124 o 0 public a-A - 054250a37db4
125 125
126 126 $ hg push ../beta
127 127 pushing to ../beta
128 128 searching for changes
129 129 no changes found
130 130 test-debug-phase: move rev 3: 1 -> 0
131 131 [1]
132 132 $ hgph
133 133 @ 3 public a-D - b555f63b6063
134 134 |
135 135 o 2 public a-C - 54acac6f23ab
136 136 |
137 137 o 1 public a-B - 548a3d25dbf0
138 138 |
139 139 o 0 public a-A - 054250a37db4
140 140
141 141
142 142 update must update phase of common changeset too
143 143
144 144 $ hg pull ../beta # getting b-A
145 145 pulling from ../beta
146 146 searching for changes
147 147 adding changesets
148 148 adding manifests
149 149 adding file changes
150 150 added 1 changesets with 1 changes to 1 files (+1 heads)
151 151 new changesets f54f1bb90ff3
152 152 test-debug-phase: new rev 4: x -> 0
153 153 (run 'hg heads' to see heads, 'hg merge' to merge)
154 154
155 155 $ cd ../beta
156 156 $ hgph # not updated by remote pull
157 157 o 4 public a-D - b555f63b6063
158 158 |
159 159 o 3 public a-C - 54acac6f23ab
160 160 |
161 161 | @ 2 draft b-A - f54f1bb90ff3
162 162 |/
163 163 o 1 public a-B - 548a3d25dbf0
164 164 |
165 165 o 0 public a-A - 054250a37db4
166 166
167 167 $ hg pull ../alpha
168 168 pulling from ../alpha
169 169 searching for changes
170 170 no changes found
171 171 1 local changesets published
172 172 test-debug-phase: move rev 2: 1 -> 0
173 173 $ hgph
174 174 o 4 public a-D - b555f63b6063
175 175 |
176 176 o 3 public a-C - 54acac6f23ab
177 177 |
178 178 | @ 2 public b-A - f54f1bb90ff3
179 179 |/
180 180 o 1 public a-B - 548a3d25dbf0
181 181 |
182 182 o 0 public a-A - 054250a37db4
183 183
184 184
185 185 Publish configuration option
186 186 ----------------------------
187 187
188 188 Pull
189 189 ````
190 190
191 191 changegroup are added without phase movement
192 192
193 193 $ hg bundle -a ../base.bundle
194 194 5 changesets found
195 195 $ cd ..
196 196 $ hg init mu
197 197 $ cd mu
198 198 $ cat > .hg/hgrc << EOF
199 199 > [phases]
200 200 > publish=0
201 201 > EOF
202 202 $ hg unbundle ../base.bundle
203 203 adding changesets
204 204 adding manifests
205 205 adding file changes
206 206 added 5 changesets with 5 changes to 5 files (+1 heads)
207 207 new changesets 054250a37db4:b555f63b6063
208 208 test-debug-phase: new rev 0: x -> 1
209 209 test-debug-phase: new rev 1: x -> 1
210 210 test-debug-phase: new rev 2: x -> 1
211 211 test-debug-phase: new rev 3: x -> 1
212 212 test-debug-phase: new rev 4: x -> 1
213 213 (run 'hg heads' to see heads, 'hg merge' to merge)
214 214 $ hgph
215 215 o 4 draft a-D - b555f63b6063
216 216 |
217 217 o 3 draft a-C - 54acac6f23ab
218 218 |
219 219 | o 2 draft b-A - f54f1bb90ff3
220 220 |/
221 221 o 1 draft a-B - 548a3d25dbf0
222 222 |
223 223 o 0 draft a-A - 054250a37db4
224 224
225 225 $ cd ..
226 226
227 227 Pulling from publish=False to publish=False does not move boundary.
228 228
229 229 $ hg init nu
230 230 $ cd nu
231 231 $ cat > .hg/hgrc << EOF
232 232 > [phases]
233 233 > publish=0
234 234 > EOF
235 235 $ hg pull ../mu -r 54acac6f23ab
236 236 pulling from ../mu
237 237 adding changesets
238 238 adding manifests
239 239 adding file changes
240 240 added 3 changesets with 3 changes to 3 files
241 241 new changesets 054250a37db4:54acac6f23ab
242 242 test-debug-phase: new rev 0: x -> 1
243 243 test-debug-phase: new rev 1: x -> 1
244 244 test-debug-phase: new rev 2: x -> 1
245 245 (run 'hg update' to get a working copy)
246 246 $ hgph
247 247 o 2 draft a-C - 54acac6f23ab
248 248 |
249 249 o 1 draft a-B - 548a3d25dbf0
250 250 |
251 251 o 0 draft a-A - 054250a37db4
252 252
253 253
254 254 Even for common
255 255
256 256 $ hg pull ../mu -r f54f1bb90ff3
257 257 pulling from ../mu
258 258 searching for changes
259 259 adding changesets
260 260 adding manifests
261 261 adding file changes
262 262 added 1 changesets with 1 changes to 1 files (+1 heads)
263 263 new changesets f54f1bb90ff3
264 264 test-debug-phase: new rev 3: x -> 1
265 265 (run 'hg heads' to see heads, 'hg merge' to merge)
266 266 $ hgph
267 267 o 3 draft b-A - f54f1bb90ff3
268 268 |
269 269 | o 2 draft a-C - 54acac6f23ab
270 270 |/
271 271 o 1 draft a-B - 548a3d25dbf0
272 272 |
273 273 o 0 draft a-A - 054250a37db4
274 274
275 275
276 276
277 277 Pulling from Publish=True to Publish=False move boundary in common set.
278 278 we are in nu
279 279
280 280 $ hg pull ../alpha -r b555f63b6063
281 281 pulling from ../alpha
282 282 searching for changes
283 283 adding changesets
284 284 adding manifests
285 285 adding file changes
286 286 added 1 changesets with 1 changes to 1 files
287 287 new changesets b555f63b6063
288 288 3 local changesets published
289 289 test-debug-phase: move rev 0: 1 -> 0
290 290 test-debug-phase: move rev 1: 1 -> 0
291 291 test-debug-phase: move rev 2: 1 -> 0
292 292 test-debug-phase: new rev 4: x -> 0
293 293 (run 'hg update' to get a working copy)
294 294 $ hgph # f54f1bb90ff3 stay draft, not ancestor of -r
295 295 o 4 public a-D - b555f63b6063
296 296 |
297 297 | o 3 draft b-A - f54f1bb90ff3
298 298 | |
299 299 o | 2 public a-C - 54acac6f23ab
300 300 |/
301 301 o 1 public a-B - 548a3d25dbf0
302 302 |
303 303 o 0 public a-A - 054250a37db4
304 304
305 305
306 306 pulling from Publish=False to publish=False with some public
307 307
308 308 $ hg up -q f54f1bb90ff3
309 309 $ mkcommit n-A
310 310 test-debug-phase: new rev 5: x -> 1
311 311 $ mkcommit n-B
312 312 test-debug-phase: new rev 6: x -> 1
313 313 $ hgph
314 314 @ 6 draft n-B - 145e75495359
315 315 |
316 316 o 5 draft n-A - d6bcb4f74035
317 317 |
318 318 | o 4 public a-D - b555f63b6063
319 319 | |
320 320 o | 3 draft b-A - f54f1bb90ff3
321 321 | |
322 322 | o 2 public a-C - 54acac6f23ab
323 323 |/
324 324 o 1 public a-B - 548a3d25dbf0
325 325 |
326 326 o 0 public a-A - 054250a37db4
327 327
328 328 $ cd ../mu
329 329 $ hg pull ../nu
330 330 pulling from ../nu
331 331 searching for changes
332 332 adding changesets
333 333 adding manifests
334 334 adding file changes
335 335 added 2 changesets with 2 changes to 2 files
336 336 new changesets d6bcb4f74035:145e75495359
337 337 4 local changesets published
338 338 test-debug-phase: move rev 0: 1 -> 0
339 339 test-debug-phase: move rev 1: 1 -> 0
340 340 test-debug-phase: move rev 3: 1 -> 0
341 341 test-debug-phase: move rev 4: 1 -> 0
342 342 test-debug-phase: new rev 5: x -> 1
343 343 test-debug-phase: new rev 6: x -> 1
344 344 (run 'hg update' to get a working copy)
345 345 $ hgph
346 346 o 6 draft n-B - 145e75495359
347 347 |
348 348 o 5 draft n-A - d6bcb4f74035
349 349 |
350 350 | o 4 public a-D - b555f63b6063
351 351 | |
352 352 | o 3 public a-C - 54acac6f23ab
353 353 | |
354 354 o | 2 draft b-A - f54f1bb90ff3
355 355 |/
356 356 o 1 public a-B - 548a3d25dbf0
357 357 |
358 358 o 0 public a-A - 054250a37db4
359 359
360 360 $ cd ..
361 361
362 362 pulling into publish=True
363 363
364 364 $ cd alpha
365 365 $ hgph
366 366 o 4 public b-A - f54f1bb90ff3
367 367 |
368 368 | @ 3 public a-D - b555f63b6063
369 369 | |
370 370 | o 2 public a-C - 54acac6f23ab
371 371 |/
372 372 o 1 public a-B - 548a3d25dbf0
373 373 |
374 374 o 0 public a-A - 054250a37db4
375 375
376 376 $ hg pull ../mu
377 377 pulling from ../mu
378 378 searching for changes
379 379 adding changesets
380 380 adding manifests
381 381 adding file changes
382 382 added 2 changesets with 2 changes to 2 files
383 383 new changesets d6bcb4f74035:145e75495359
384 384 test-debug-phase: new rev 5: x -> 1
385 385 test-debug-phase: new rev 6: x -> 1
386 386 (run 'hg update' to get a working copy)
387 387 $ hgph
388 388 o 6 draft n-B - 145e75495359
389 389 |
390 390 o 5 draft n-A - d6bcb4f74035
391 391 |
392 392 o 4 public b-A - f54f1bb90ff3
393 393 |
394 394 | @ 3 public a-D - b555f63b6063
395 395 | |
396 396 | o 2 public a-C - 54acac6f23ab
397 397 |/
398 398 o 1 public a-B - 548a3d25dbf0
399 399 |
400 400 o 0 public a-A - 054250a37db4
401 401
402 402 $ cd ..
403 403
404 404 pulling back into original repo
405 405
406 406 $ cd nu
407 407 $ hg pull ../alpha
408 408 pulling from ../alpha
409 409 searching for changes
410 410 no changes found
411 411 3 local changesets published
412 412 test-debug-phase: move rev 3: 1 -> 0
413 413 test-debug-phase: move rev 5: 1 -> 0
414 414 test-debug-phase: move rev 6: 1 -> 0
415 415 $ hgph
416 416 @ 6 public n-B - 145e75495359
417 417 |
418 418 o 5 public n-A - d6bcb4f74035
419 419 |
420 420 | o 4 public a-D - b555f63b6063
421 421 | |
422 422 o | 3 public b-A - f54f1bb90ff3
423 423 | |
424 424 | o 2 public a-C - 54acac6f23ab
425 425 |/
426 426 o 1 public a-B - 548a3d25dbf0
427 427 |
428 428 o 0 public a-A - 054250a37db4
429 429
430 430
431 431 Push
432 432 ````
433 433
434 434 (inserted)
435 435
436 436 Test that phase are pushed even when they are nothing to pus
437 437 (this might be tested later bu are very convenient to not alter too much test)
438 438
439 439 Push back to alpha
440 440
441 441 $ hg push ../alpha # from nu
442 442 pushing to ../alpha
443 443 searching for changes
444 444 no changes found
445 445 test-debug-phase: move rev 5: 1 -> 0
446 446 test-debug-phase: move rev 6: 1 -> 0
447 447 [1]
448 448 $ cd ..
449 449 $ cd alpha
450 450 $ hgph
451 451 o 6 public n-B - 145e75495359
452 452 |
453 453 o 5 public n-A - d6bcb4f74035
454 454 |
455 455 o 4 public b-A - f54f1bb90ff3
456 456 |
457 457 | @ 3 public a-D - b555f63b6063
458 458 | |
459 459 | o 2 public a-C - 54acac6f23ab
460 460 |/
461 461 o 1 public a-B - 548a3d25dbf0
462 462 |
463 463 o 0 public a-A - 054250a37db4
464 464
465 465
466 466 (end insertion)
467 467
468 468
469 469 initial setup
470 470
471 471 $ hg log -G # of alpha
472 472 o changeset: 6:145e75495359
473 473 | tag: tip
474 474 | user: test
475 475 | date: Thu Jan 01 00:00:00 1970 +0000
476 476 | summary: n-B
477 477 |
478 478 o changeset: 5:d6bcb4f74035
479 479 | user: test
480 480 | date: Thu Jan 01 00:00:00 1970 +0000
481 481 | summary: n-A
482 482 |
483 483 o changeset: 4:f54f1bb90ff3
484 484 | parent: 1:548a3d25dbf0
485 485 | user: test
486 486 | date: Thu Jan 01 00:00:00 1970 +0000
487 487 | summary: b-A
488 488 |
489 489 | @ changeset: 3:b555f63b6063
490 490 | | user: test
491 491 | | date: Thu Jan 01 00:00:00 1970 +0000
492 492 | | summary: a-D
493 493 | |
494 494 | o changeset: 2:54acac6f23ab
495 495 |/ user: test
496 496 | date: Thu Jan 01 00:00:00 1970 +0000
497 497 | summary: a-C
498 498 |
499 499 o changeset: 1:548a3d25dbf0
500 500 | user: test
501 501 | date: Thu Jan 01 00:00:00 1970 +0000
502 502 | summary: a-B
503 503 |
504 504 o changeset: 0:054250a37db4
505 505 user: test
506 506 date: Thu Jan 01 00:00:00 1970 +0000
507 507 summary: a-A
508 508
509 509 $ mkcommit a-E
510 510 test-debug-phase: new rev 7: x -> 1
511 511 $ mkcommit a-F
512 512 test-debug-phase: new rev 8: x -> 1
513 513 $ mkcommit a-G
514 514 test-debug-phase: new rev 9: x -> 1
515 515 $ hg up d6bcb4f74035 -q
516 516 $ mkcommit a-H
517 517 test-debug-phase: new rev 10: x -> 1
518 518 created new head
519 519 $ hgph
520 520 @ 10 draft a-H - 967b449fbc94
521 521 |
522 522 | o 9 draft a-G - 3e27b6f1eee1
523 523 | |
524 524 | o 8 draft a-F - b740e3e5c05d
525 525 | |
526 526 | o 7 draft a-E - e9f537e46dea
527 527 | |
528 528 +---o 6 public n-B - 145e75495359
529 529 | |
530 530 o | 5 public n-A - d6bcb4f74035
531 531 | |
532 532 o | 4 public b-A - f54f1bb90ff3
533 533 | |
534 534 | o 3 public a-D - b555f63b6063
535 535 | |
536 536 | o 2 public a-C - 54acac6f23ab
537 537 |/
538 538 o 1 public a-B - 548a3d25dbf0
539 539 |
540 540 o 0 public a-A - 054250a37db4
541 541
542 542
543 543 Pulling from bundle does not alter phases of changeset not present in the bundle
544 544
545 545 #if repobundlerepo
546 546 $ hg bundle --base 1 -r 6 -r 3 ../partial-bundle.hg
547 547 5 changesets found
548 548 $ hg pull ../partial-bundle.hg
549 549 pulling from ../partial-bundle.hg
550 550 searching for changes
551 551 no changes found
552 552 $ hgph
553 553 @ 10 draft a-H - 967b449fbc94
554 554 |
555 555 | o 9 draft a-G - 3e27b6f1eee1
556 556 | |
557 557 | o 8 draft a-F - b740e3e5c05d
558 558 | |
559 559 | o 7 draft a-E - e9f537e46dea
560 560 | |
561 561 +---o 6 public n-B - 145e75495359
562 562 | |
563 563 o | 5 public n-A - d6bcb4f74035
564 564 | |
565 565 o | 4 public b-A - f54f1bb90ff3
566 566 | |
567 567 | o 3 public a-D - b555f63b6063
568 568 | |
569 569 | o 2 public a-C - 54acac6f23ab
570 570 |/
571 571 o 1 public a-B - 548a3d25dbf0
572 572 |
573 573 o 0 public a-A - 054250a37db4
574 574
575 575 #endif
576 576
577 577 Pushing to Publish=False (unknown changeset)
578 578
579 579 $ hg push ../mu -r b740e3e5c05d # a-F
580 580 pushing to ../mu
581 581 searching for changes
582 582 adding changesets
583 583 adding manifests
584 584 adding file changes
585 585 added 2 changesets with 2 changes to 2 files
586 586 test-debug-phase: new rev 7: x -> 1
587 587 test-debug-phase: new rev 8: x -> 1
588 588 $ hgph
589 589 @ 10 draft a-H - 967b449fbc94
590 590 |
591 591 | o 9 draft a-G - 3e27b6f1eee1
592 592 | |
593 593 | o 8 draft a-F - b740e3e5c05d
594 594 | |
595 595 | o 7 draft a-E - e9f537e46dea
596 596 | |
597 597 +---o 6 public n-B - 145e75495359
598 598 | |
599 599 o | 5 public n-A - d6bcb4f74035
600 600 | |
601 601 o | 4 public b-A - f54f1bb90ff3
602 602 | |
603 603 | o 3 public a-D - b555f63b6063
604 604 | |
605 605 | o 2 public a-C - 54acac6f23ab
606 606 |/
607 607 o 1 public a-B - 548a3d25dbf0
608 608 |
609 609 o 0 public a-A - 054250a37db4
610 610
611 611
612 612 $ cd ../mu
613 613 $ hgph # again f54f1bb90ff3, d6bcb4f74035 and 145e75495359 stay draft,
614 614 > # not ancestor of -r
615 615 o 8 draft a-F - b740e3e5c05d
616 616 |
617 617 o 7 draft a-E - e9f537e46dea
618 618 |
619 619 | o 6 draft n-B - 145e75495359
620 620 | |
621 621 | o 5 draft n-A - d6bcb4f74035
622 622 | |
623 623 o | 4 public a-D - b555f63b6063
624 624 | |
625 625 o | 3 public a-C - 54acac6f23ab
626 626 | |
627 627 | o 2 draft b-A - f54f1bb90ff3
628 628 |/
629 629 o 1 public a-B - 548a3d25dbf0
630 630 |
631 631 o 0 public a-A - 054250a37db4
632 632
633 633
634 634 Pushing to Publish=True (unknown changeset)
635 635
636 636 $ hg push ../beta -r b740e3e5c05d
637 637 pushing to ../beta
638 638 searching for changes
639 639 adding changesets
640 640 adding manifests
641 641 adding file changes
642 642 added 2 changesets with 2 changes to 2 files
643 643 test-debug-phase: new rev 5: x -> 0
644 644 test-debug-phase: new rev 6: x -> 0
645 645 test-debug-phase: move rev 7: 1 -> 0
646 646 test-debug-phase: move rev 8: 1 -> 0
647 647 $ hgph # again f54f1bb90ff3, d6bcb4f74035 and 145e75495359 stay draft,
648 648 > # not ancestor of -r
649 649 o 8 public a-F - b740e3e5c05d
650 650 |
651 651 o 7 public a-E - e9f537e46dea
652 652 |
653 653 | o 6 draft n-B - 145e75495359
654 654 | |
655 655 | o 5 draft n-A - d6bcb4f74035
656 656 | |
657 657 o | 4 public a-D - b555f63b6063
658 658 | |
659 659 o | 3 public a-C - 54acac6f23ab
660 660 | |
661 661 | o 2 draft b-A - f54f1bb90ff3
662 662 |/
663 663 o 1 public a-B - 548a3d25dbf0
664 664 |
665 665 o 0 public a-A - 054250a37db4
666 666
667 667
668 668 Pushing to Publish=True (common changeset)
669 669
670 670 $ cd ../beta
671 671 $ hg push ../alpha
672 672 pushing to ../alpha
673 673 searching for changes
674 674 no changes found
675 675 test-debug-phase: move rev 7: 1 -> 0
676 676 test-debug-phase: move rev 8: 1 -> 0
677 677 [1]
678 678 $ hgph
679 679 o 6 public a-F - b740e3e5c05d
680 680 |
681 681 o 5 public a-E - e9f537e46dea
682 682 |
683 683 o 4 public a-D - b555f63b6063
684 684 |
685 685 o 3 public a-C - 54acac6f23ab
686 686 |
687 687 | @ 2 public b-A - f54f1bb90ff3
688 688 |/
689 689 o 1 public a-B - 548a3d25dbf0
690 690 |
691 691 o 0 public a-A - 054250a37db4
692 692
693 693 $ cd ../alpha
694 694 $ hgph
695 695 @ 10 draft a-H - 967b449fbc94
696 696 |
697 697 | o 9 draft a-G - 3e27b6f1eee1
698 698 | |
699 699 | o 8 public a-F - b740e3e5c05d
700 700 | |
701 701 | o 7 public a-E - e9f537e46dea
702 702 | |
703 703 +---o 6 public n-B - 145e75495359
704 704 | |
705 705 o | 5 public n-A - d6bcb4f74035
706 706 | |
707 707 o | 4 public b-A - f54f1bb90ff3
708 708 | |
709 709 | o 3 public a-D - b555f63b6063
710 710 | |
711 711 | o 2 public a-C - 54acac6f23ab
712 712 |/
713 713 o 1 public a-B - 548a3d25dbf0
714 714 |
715 715 o 0 public a-A - 054250a37db4
716 716
717 717
718 718 Pushing to Publish=False (common changeset that change phase + unknown one)
719 719
720 720 $ hg push ../mu -r 967b449fbc94 -f
721 721 pushing to ../mu
722 722 searching for changes
723 723 adding changesets
724 724 adding manifests
725 725 adding file changes
726 726 added 1 changesets with 1 changes to 1 files (+1 heads)
727 727 test-debug-phase: move rev 2: 1 -> 0
728 728 test-debug-phase: move rev 5: 1 -> 0
729 729 test-debug-phase: new rev 9: x -> 1
730 730 $ hgph
731 731 @ 10 draft a-H - 967b449fbc94
732 732 |
733 733 | o 9 draft a-G - 3e27b6f1eee1
734 734 | |
735 735 | o 8 public a-F - b740e3e5c05d
736 736 | |
737 737 | o 7 public a-E - e9f537e46dea
738 738 | |
739 739 +---o 6 public n-B - 145e75495359
740 740 | |
741 741 o | 5 public n-A - d6bcb4f74035
742 742 | |
743 743 o | 4 public b-A - f54f1bb90ff3
744 744 | |
745 745 | o 3 public a-D - b555f63b6063
746 746 | |
747 747 | o 2 public a-C - 54acac6f23ab
748 748 |/
749 749 o 1 public a-B - 548a3d25dbf0
750 750 |
751 751 o 0 public a-A - 054250a37db4
752 752
753 753 $ cd ../mu
754 754 $ hgph # d6bcb4f74035 should have changed phase
755 755 > # 145e75495359 is still draft. not ancestor of -r
756 756 o 9 draft a-H - 967b449fbc94
757 757 |
758 758 | o 8 public a-F - b740e3e5c05d
759 759 | |
760 760 | o 7 public a-E - e9f537e46dea
761 761 | |
762 762 +---o 6 draft n-B - 145e75495359
763 763 | |
764 764 o | 5 public n-A - d6bcb4f74035
765 765 | |
766 766 | o 4 public a-D - b555f63b6063
767 767 | |
768 768 | o 3 public a-C - 54acac6f23ab
769 769 | |
770 770 o | 2 public b-A - f54f1bb90ff3
771 771 |/
772 772 o 1 public a-B - 548a3d25dbf0
773 773 |
774 774 o 0 public a-A - 054250a37db4
775 775
776 776
777 777
778 778 Pushing to Publish=True (common changeset from publish=False)
779 779
780 780 (in mu)
781 781 $ hg push ../alpha
782 782 pushing to ../alpha
783 783 searching for changes
784 784 no changes found
785 785 test-debug-phase: move rev 10: 1 -> 0
786 786 test-debug-phase: move rev 6: 1 -> 0
787 787 test-debug-phase: move rev 9: 1 -> 0
788 788 [1]
789 789 $ hgph
790 790 o 9 public a-H - 967b449fbc94
791 791 |
792 792 | o 8 public a-F - b740e3e5c05d
793 793 | |
794 794 | o 7 public a-E - e9f537e46dea
795 795 | |
796 796 +---o 6 public n-B - 145e75495359
797 797 | |
798 798 o | 5 public n-A - d6bcb4f74035
799 799 | |
800 800 | o 4 public a-D - b555f63b6063
801 801 | |
802 802 | o 3 public a-C - 54acac6f23ab
803 803 | |
804 804 o | 2 public b-A - f54f1bb90ff3
805 805 |/
806 806 o 1 public a-B - 548a3d25dbf0
807 807 |
808 808 o 0 public a-A - 054250a37db4
809 809
810 810 $ hgph -R ../alpha # a-H should have been synced to 0
811 811 @ 10 public a-H - 967b449fbc94
812 812 |
813 813 | o 9 draft a-G - 3e27b6f1eee1
814 814 | |
815 815 | o 8 public a-F - b740e3e5c05d
816 816 | |
817 817 | o 7 public a-E - e9f537e46dea
818 818 | |
819 819 +---o 6 public n-B - 145e75495359
820 820 | |
821 821 o | 5 public n-A - d6bcb4f74035
822 822 | |
823 823 o | 4 public b-A - f54f1bb90ff3
824 824 | |
825 825 | o 3 public a-D - b555f63b6063
826 826 | |
827 827 | o 2 public a-C - 54acac6f23ab
828 828 |/
829 829 o 1 public a-B - 548a3d25dbf0
830 830 |
831 831 o 0 public a-A - 054250a37db4
832 832
833 833
834 834
835 835 Bare push with next changeset and common changeset needing sync (issue3575)
836 836
837 837 (reset some stat on remote repo to avoid confusing other tests)
838 838
839 839 $ hg -R ../alpha --config extensions.strip= strip --no-backup 967b449fbc94
840 840 0 files updated, 0 files merged, 1 files removed, 0 files unresolved
841 841 $ hg phase --force --draft b740e3e5c05d 967b449fbc94
842 842 test-debug-phase: move rev 8: 0 -> 1
843 843 test-debug-phase: move rev 9: 0 -> 1
844 844 $ hg push -fv ../alpha
845 845 pushing to ../alpha
846 846 searching for changes
847 847 1 changesets found
848 848 uncompressed size of bundle content:
849 849 178 (changelog)
850 850 165 (manifests)
851 851 131 a-H
852 852 adding changesets
853 853 adding manifests
854 854 adding file changes
855 855 added 1 changesets with 1 changes to 1 files (+1 heads)
856 856 test-debug-phase: new rev 10: x -> 0
857 857 test-debug-phase: move rev 8: 1 -> 0
858 858 test-debug-phase: move rev 9: 1 -> 0
859 859 $ hgph
860 860 o 9 public a-H - 967b449fbc94
861 861 |
862 862 | o 8 public a-F - b740e3e5c05d
863 863 | |
864 864 | o 7 public a-E - e9f537e46dea
865 865 | |
866 866 +---o 6 public n-B - 145e75495359
867 867 | |
868 868 o | 5 public n-A - d6bcb4f74035
869 869 | |
870 870 | o 4 public a-D - b555f63b6063
871 871 | |
872 872 | o 3 public a-C - 54acac6f23ab
873 873 | |
874 874 o | 2 public b-A - f54f1bb90ff3
875 875 |/
876 876 o 1 public a-B - 548a3d25dbf0
877 877 |
878 878 o 0 public a-A - 054250a37db4
879 879
880 880
881 881 $ hg -R ../alpha update 967b449fbc94 #for latter test consistency
882 882 1 files updated, 0 files merged, 0 files removed, 0 files unresolved
883 883 $ hgph -R ../alpha
884 884 @ 10 public a-H - 967b449fbc94
885 885 |
886 886 | o 9 draft a-G - 3e27b6f1eee1
887 887 | |
888 888 | o 8 public a-F - b740e3e5c05d
889 889 | |
890 890 | o 7 public a-E - e9f537e46dea
891 891 | |
892 892 +---o 6 public n-B - 145e75495359
893 893 | |
894 894 o | 5 public n-A - d6bcb4f74035
895 895 | |
896 896 o | 4 public b-A - f54f1bb90ff3
897 897 | |
898 898 | o 3 public a-D - b555f63b6063
899 899 | |
900 900 | o 2 public a-C - 54acac6f23ab
901 901 |/
902 902 o 1 public a-B - 548a3d25dbf0
903 903 |
904 904 o 0 public a-A - 054250a37db4
905 905
906 906
907 907 Discovery locally secret changeset on a remote repository:
908 908
909 909 - should make it non-secret
910 910
911 911 $ cd ../alpha
912 912 $ mkcommit A-secret --config phases.new-commit=2
913 913 test-debug-phase: new rev 11: x -> 2
914 914 $ hgph
915 915 @ 11 secret A-secret - 435b5d83910c
916 916 |
917 917 o 10 public a-H - 967b449fbc94
918 918 |
919 919 | o 9 draft a-G - 3e27b6f1eee1
920 920 | |
921 921 | o 8 public a-F - b740e3e5c05d
922 922 | |
923 923 | o 7 public a-E - e9f537e46dea
924 924 | |
925 925 +---o 6 public n-B - 145e75495359
926 926 | |
927 927 o | 5 public n-A - d6bcb4f74035
928 928 | |
929 929 o | 4 public b-A - f54f1bb90ff3
930 930 | |
931 931 | o 3 public a-D - b555f63b6063
932 932 | |
933 933 | o 2 public a-C - 54acac6f23ab
934 934 |/
935 935 o 1 public a-B - 548a3d25dbf0
936 936 |
937 937 o 0 public a-A - 054250a37db4
938 938
939 939 $ hg bundle --base 'parents(.)' -r . ../secret-bundle.hg
940 940 1 changesets found
941 941 $ hg -R ../mu unbundle ../secret-bundle.hg
942 942 adding changesets
943 943 adding manifests
944 944 adding file changes
945 945 added 1 changesets with 1 changes to 1 files
946 946 new changesets 435b5d83910c
947 947 test-debug-phase: new rev 10: x -> 1
948 948 (run 'hg update' to get a working copy)
949 949 $ hgph -R ../mu
950 950 o 10 draft A-secret - 435b5d83910c
951 951 |
952 952 o 9 public a-H - 967b449fbc94
953 953 |
954 954 | o 8 public a-F - b740e3e5c05d
955 955 | |
956 956 | o 7 public a-E - e9f537e46dea
957 957 | |
958 958 +---o 6 public n-B - 145e75495359
959 959 | |
960 960 o | 5 public n-A - d6bcb4f74035
961 961 | |
962 962 | o 4 public a-D - b555f63b6063
963 963 | |
964 964 | o 3 public a-C - 54acac6f23ab
965 965 | |
966 966 o | 2 public b-A - f54f1bb90ff3
967 967 |/
968 968 o 1 public a-B - 548a3d25dbf0
969 969 |
970 970 o 0 public a-A - 054250a37db4
971 971
972 972 $ hg pull ../mu
973 973 pulling from ../mu
974 974 searching for changes
975 975 no changes found
976 976 test-debug-phase: move rev 11: 2 -> 1
977 977 $ hgph
978 978 @ 11 draft A-secret - 435b5d83910c
979 979 |
980 980 o 10 public a-H - 967b449fbc94
981 981 |
982 982 | o 9 draft a-G - 3e27b6f1eee1
983 983 | |
984 984 | o 8 public a-F - b740e3e5c05d
985 985 | |
986 986 | o 7 public a-E - e9f537e46dea
987 987 | |
988 988 +---o 6 public n-B - 145e75495359
989 989 | |
990 990 o | 5 public n-A - d6bcb4f74035
991 991 | |
992 992 o | 4 public b-A - f54f1bb90ff3
993 993 | |
994 994 | o 3 public a-D - b555f63b6063
995 995 | |
996 996 | o 2 public a-C - 54acac6f23ab
997 997 |/
998 998 o 1 public a-B - 548a3d25dbf0
999 999 |
1000 1000 o 0 public a-A - 054250a37db4
1001 1001
1002 1002
1003 1003 pushing a locally public and draft changesets remotely secret should make them
1004 1004 appear on the remote side.
1005 1005
1006 1006 $ hg -R ../mu phase --secret --force 967b449fbc94
1007 1007 test-debug-phase: move rev 9: 0 -> 2
1008 1008 test-debug-phase: move rev 10: 1 -> 2
1009 1009 $ hg push -r 435b5d83910c ../mu
1010 1010 pushing to ../mu
1011 1011 searching for changes
1012 1012 abort: push creates new remote head 435b5d83910c!
1013 1013 (merge or see 'hg help push' for details about pushing new heads)
1014 1014 [255]
1015 1015 $ hg push -fr 435b5d83910c ../mu # because the push will create new visible head
1016 1016 pushing to ../mu
1017 1017 searching for changes
1018 1018 adding changesets
1019 1019 adding manifests
1020 1020 adding file changes
1021 1021 added 0 changesets with 0 changes to 2 files
1022 1022 test-debug-phase: move rev 9: 2 -> 0
1023 1023 test-debug-phase: move rev 10: 2 -> 1
1024 1024 $ hgph -R ../mu
1025 1025 o 10 draft A-secret - 435b5d83910c
1026 1026 |
1027 1027 o 9 public a-H - 967b449fbc94
1028 1028 |
1029 1029 | o 8 public a-F - b740e3e5c05d
1030 1030 | |
1031 1031 | o 7 public a-E - e9f537e46dea
1032 1032 | |
1033 1033 +---o 6 public n-B - 145e75495359
1034 1034 | |
1035 1035 o | 5 public n-A - d6bcb4f74035
1036 1036 | |
1037 1037 | o 4 public a-D - b555f63b6063
1038 1038 | |
1039 1039 | o 3 public a-C - 54acac6f23ab
1040 1040 | |
1041 1041 o | 2 public b-A - f54f1bb90ff3
1042 1042 |/
1043 1043 o 1 public a-B - 548a3d25dbf0
1044 1044 |
1045 1045 o 0 public a-A - 054250a37db4
1046 1046
1047 1047
1048 1048 pull new changeset with common draft locally
1049 1049
1050 1050 $ hg up -q 967b449fbc94 # create a new root for draft
1051 1051 $ mkcommit 'alpha-more'
1052 1052 test-debug-phase: new rev 12: x -> 1
1053 1053 created new head
1054 1054 $ hg push -fr . ../mu
1055 1055 pushing to ../mu
1056 1056 searching for changes
1057 1057 adding changesets
1058 1058 adding manifests
1059 1059 adding file changes
1060 1060 added 1 changesets with 1 changes to 1 files (+1 heads)
1061 1061 test-debug-phase: new rev 11: x -> 1
1062 1062 $ cd ../mu
1063 1063 $ hg phase --secret --force 1c5cfd894796
1064 1064 test-debug-phase: move rev 11: 1 -> 2
1065 1065 $ hg up -q 435b5d83910c
1066 1066 $ mkcommit 'mu-more'
1067 1067 test-debug-phase: new rev 12: x -> 1
1068 1068 $ cd ../alpha
1069 1069 $ hg pull ../mu
1070 1070 pulling from ../mu
1071 1071 searching for changes
1072 1072 adding changesets
1073 1073 adding manifests
1074 1074 adding file changes
1075 1075 added 1 changesets with 1 changes to 1 files
1076 1076 new changesets 5237fb433fc8
1077 1077 test-debug-phase: new rev 13: x -> 1
1078 1078 (run 'hg update' to get a working copy)
1079 1079 $ hgph
1080 1080 o 13 draft mu-more - 5237fb433fc8
1081 1081 |
1082 1082 | @ 12 draft alpha-more - 1c5cfd894796
1083 1083 | |
1084 1084 o | 11 draft A-secret - 435b5d83910c
1085 1085 |/
1086 1086 o 10 public a-H - 967b449fbc94
1087 1087 |
1088 1088 | o 9 draft a-G - 3e27b6f1eee1
1089 1089 | |
1090 1090 | o 8 public a-F - b740e3e5c05d
1091 1091 | |
1092 1092 | o 7 public a-E - e9f537e46dea
1093 1093 | |
1094 1094 +---o 6 public n-B - 145e75495359
1095 1095 | |
1096 1096 o | 5 public n-A - d6bcb4f74035
1097 1097 | |
1098 1098 o | 4 public b-A - f54f1bb90ff3
1099 1099 | |
1100 1100 | o 3 public a-D - b555f63b6063
1101 1101 | |
1102 1102 | o 2 public a-C - 54acac6f23ab
1103 1103 |/
1104 1104 o 1 public a-B - 548a3d25dbf0
1105 1105 |
1106 1106 o 0 public a-A - 054250a37db4
1107 1107
1108 1108
1109 1109 Test that test are properly ignored on remote event when existing locally
1110 1110
1111 1111 $ cd ..
1112 1112 $ hg clone -qU -r b555f63b6063 -r f54f1bb90ff3 beta gamma
1113 1113 test-debug-phase: new rev 0: x -> 0
1114 1114 test-debug-phase: new rev 1: x -> 0
1115 1115 test-debug-phase: new rev 2: x -> 0
1116 1116 test-debug-phase: new rev 3: x -> 0
1117 1117 test-debug-phase: new rev 4: x -> 0
1118 1118
1119 1119 # pathological case are
1120 1120 #
1121 1121 # * secret remotely
1122 1122 # * known locally
1123 1123 # * repo have uncommon changeset
1124 1124
1125 1125 $ hg -R beta phase --secret --force f54f1bb90ff3
1126 1126 test-debug-phase: move rev 2: 0 -> 2
1127 1127 $ hg -R gamma phase --draft --force f54f1bb90ff3
1128 1128 test-debug-phase: move rev 2: 0 -> 1
1129 1129
1130 1130 $ cd gamma
1131 1131 $ hg pull ../beta
1132 1132 pulling from ../beta
1133 1133 searching for changes
1134 1134 adding changesets
1135 1135 adding manifests
1136 1136 adding file changes
1137 1137 added 2 changesets with 2 changes to 2 files
1138 1138 new changesets e9f537e46dea:b740e3e5c05d
1139 1139 test-debug-phase: new rev 5: x -> 0
1140 1140 test-debug-phase: new rev 6: x -> 0
1141 1141 (run 'hg update' to get a working copy)
1142 1142 $ hg phase f54f1bb90ff3
1143 1143 2: draft
1144 1144
1145 1145 same over the wire
1146 1146
1147 1147 $ cd ../beta
1148 1148 $ hg serve -p $HGPORT -d --pid-file=../beta.pid -E ../beta-error.log
1149 1149 $ cat ../beta.pid >> $DAEMON_PIDS
1150 1150 $ cd ../gamma
1151 1151
1152 1152 $ hg pull http://localhost:$HGPORT/ # bundle2+
1153 1153 pulling from http://localhost:$HGPORT/
1154 1154 searching for changes
1155 1155 no changes found
1156 1156 $ hg phase f54f1bb90ff3
1157 1157 2: draft
1158 1158
1159 1159 enforce bundle1
1160 1160
1161 1161 $ hg pull http://localhost:$HGPORT/ --config devel.legacy.exchange=bundle1
1162 1162 pulling from http://localhost:$HGPORT/
1163 1163 searching for changes
1164 1164 no changes found
1165 1165 $ hg phase f54f1bb90ff3
1166 1166 2: draft
1167 1167
1168 1168 check that secret local on both side are not synced to public
1169 1169
1170 1170 $ hg push -r b555f63b6063 http://localhost:$HGPORT/
1171 1171 pushing to http://localhost:$HGPORT/
1172 1172 searching for changes
1173 1173 no changes found
1174 1174 [1]
1175 1175 $ hg phase f54f1bb90ff3
1176 1176 2: draft
1177 1177
1178 1178 $ killdaemons.py
1179 1179
1180 1180 put the changeset in the draft state again
1181 1181 (first test after this one expect to be able to copy)
1182 1182
1183 1183 $ cd ..
1184 1184
1185 1185
1186 1186 Test Clone behavior
1187 1187
1188 1188 A. Clone without secret changeset
1189 1189
1190 1190 1. cloning non-publishing repository
1191 1191 (Phase should be preserved)
1192 1192
1193 1193 # make sure there is no secret so we can use a copy clone
1194 1194
1195 1195 $ hg -R mu phase --draft 'secret()'
1196 1196 test-debug-phase: move rev 11: 2 -> 1
1197 1197
1198 1198 $ hg clone -U mu Tau
1199 1199 $ hgph -R Tau
1200 1200 o 12 draft mu-more - 5237fb433fc8
1201 1201 |
1202 1202 | o 11 draft alpha-more - 1c5cfd894796
1203 1203 | |
1204 1204 o | 10 draft A-secret - 435b5d83910c
1205 1205 |/
1206 1206 o 9 public a-H - 967b449fbc94
1207 1207 |
1208 1208 | o 8 public a-F - b740e3e5c05d
1209 1209 | |
1210 1210 | o 7 public a-E - e9f537e46dea
1211 1211 | |
1212 1212 +---o 6 public n-B - 145e75495359
1213 1213 | |
1214 1214 o | 5 public n-A - d6bcb4f74035
1215 1215 | |
1216 1216 | o 4 public a-D - b555f63b6063
1217 1217 | |
1218 1218 | o 3 public a-C - 54acac6f23ab
1219 1219 | |
1220 1220 o | 2 public b-A - f54f1bb90ff3
1221 1221 |/
1222 1222 o 1 public a-B - 548a3d25dbf0
1223 1223 |
1224 1224 o 0 public a-A - 054250a37db4
1225 1225
1226 1226
1227 1227 2. cloning publishing repository
1228 1228
1229 1229 (everything should be public)
1230 1230
1231 1231 $ hg clone -U alpha Upsilon
1232 1232 $ hgph -R Upsilon
1233 1233 o 13 public mu-more - 5237fb433fc8
1234 1234 |
1235 1235 | o 12 public alpha-more - 1c5cfd894796
1236 1236 | |
1237 1237 o | 11 public A-secret - 435b5d83910c
1238 1238 |/
1239 1239 o 10 public a-H - 967b449fbc94
1240 1240 |
1241 1241 | o 9 public a-G - 3e27b6f1eee1
1242 1242 | |
1243 1243 | o 8 public a-F - b740e3e5c05d
1244 1244 | |
1245 1245 | o 7 public a-E - e9f537e46dea
1246 1246 | |
1247 1247 +---o 6 public n-B - 145e75495359
1248 1248 | |
1249 1249 o | 5 public n-A - d6bcb4f74035
1250 1250 | |
1251 1251 o | 4 public b-A - f54f1bb90ff3
1252 1252 | |
1253 1253 | o 3 public a-D - b555f63b6063
1254 1254 | |
1255 1255 | o 2 public a-C - 54acac6f23ab
1256 1256 |/
1257 1257 o 1 public a-B - 548a3d25dbf0
1258 1258 |
1259 1259 o 0 public a-A - 054250a37db4
1260 1260
1261 1261 #if unix-permissions no-root
1262 1262
1263 1263 Pushing From an unlockable repo
1264 1264 --------------------------------
1265 1265 (issue3684)
1266 1266
1267 1267 Unability to lock the source repo should not prevent the push. It will prevent
1268 1268 the retrieval of remote phase during push. For example, pushing to a publishing
1269 1269 server won't turn changeset public.
1270 1270
1271 1271 1. Test that push is not prevented
1272 1272
1273 1273 $ hg init Phi
1274 1274 $ cd Upsilon
1275 1275 $ chmod -R -w .hg
1276 1276 $ hg push ../Phi
1277 1277 pushing to ../Phi
1278 1278 searching for changes
1279 1279 adding changesets
1280 1280 adding manifests
1281 1281 adding file changes
1282 1282 added 14 changesets with 14 changes to 14 files (+3 heads)
1283 1283 test-debug-phase: new rev 0: x -> 0
1284 1284 test-debug-phase: new rev 1: x -> 0
1285 1285 test-debug-phase: new rev 2: x -> 0
1286 1286 test-debug-phase: new rev 3: x -> 0
1287 1287 test-debug-phase: new rev 4: x -> 0
1288 1288 test-debug-phase: new rev 5: x -> 0
1289 1289 test-debug-phase: new rev 6: x -> 0
1290 1290 test-debug-phase: new rev 7: x -> 0
1291 1291 test-debug-phase: new rev 8: x -> 0
1292 1292 test-debug-phase: new rev 9: x -> 0
1293 1293 test-debug-phase: new rev 10: x -> 0
1294 1294 test-debug-phase: new rev 11: x -> 0
1295 1295 test-debug-phase: new rev 12: x -> 0
1296 1296 test-debug-phase: new rev 13: x -> 0
1297 1297 $ chmod -R +w .hg
1298 1298
1299 1299 2. Test that failed phases movement are reported
1300 1300
1301 1301 $ hg phase --force --draft 3
1302 1302 test-debug-phase: move rev 3: 0 -> 1
1303 1303 test-debug-phase: move rev 7: 0 -> 1
1304 1304 test-debug-phase: move rev 8: 0 -> 1
1305 1305 test-debug-phase: move rev 9: 0 -> 1
1306 1306 $ chmod -R -w .hg
1307 1307 $ hg push ../Phi
1308 1308 pushing to ../Phi
1309 1309 searching for changes
1310 1310 no changes found
1311 1311 cannot lock source repo, skipping local public phase update
1312 1312 [1]
1313 1313 $ chmod -R +w .hg
1314 1314
1315 1315 3. Test that push is prevented if lock was already acquired (not a permission
1316 1316 error, but EEXIST)
1317 1317
1318 1318 $ touch .hg/store/lock
1319 1319 $ hg push ../Phi --config ui.timeout=1
1320 1320 pushing to ../Phi
1321 1321 waiting for lock on repository $TESTTMP/Upsilon held by ''
1322 1322 abort: repository $TESTTMP/Upsilon: timed out waiting for lock held by ''
1323 1323 (lock might be very busy)
1324 1324 [255]
1325 1325 $ rm .hg/store/lock
1326 1326
1327 1327 $ cd ..
1328 1328
1329 1329 #endif
1330 1330
1331 1331 Test that clone behaves like pull and doesn't publish changesets as plain push
1332 1332 does. The conditional output accounts for changes in the conditional block
1333 1333 above.
1334 1334
1335 1335 #if unix-permissions no-root
1336 1336 $ hg -R Upsilon phase -q --force --draft 2
1337 1337 test-debug-phase: move rev 2: 0 -> 1
1338 1338 #else
1339 1339 $ hg -R Upsilon phase -q --force --draft 2
1340 1340 test-debug-phase: move rev 2: 0 -> 1
1341 1341 test-debug-phase: move rev 3: 0 -> 1
1342 1342 test-debug-phase: move rev 7: 0 -> 1
1343 1343 test-debug-phase: move rev 8: 0 -> 1
1344 1344 test-debug-phase: move rev 9: 0 -> 1
1345 1345 #endif
1346 1346
1347 1347 $ hg clone -q Upsilon Pi -r 7
1348 1348 test-debug-phase: new rev 0: x -> 0
1349 1349 test-debug-phase: new rev 1: x -> 0
1350 1350 test-debug-phase: new rev 2: x -> 0
1351 1351 test-debug-phase: new rev 3: x -> 0
1352 1352 test-debug-phase: new rev 4: x -> 0
1353 1353 $ hgph Upsilon -r 'min(draft())'
1354 1354 o 2 draft a-C - 54acac6f23ab
1355 1355 |
1356 1356 ~
1357 1357
1358 1358 $ hg -R Upsilon push Pi -r 7
1359 1359 pushing to Pi
1360 1360 searching for changes
1361 1361 no changes found
1362 1362 test-debug-phase: move rev 2: 1 -> 0
1363 1363 test-debug-phase: move rev 3: 1 -> 0
1364 1364 test-debug-phase: move rev 7: 1 -> 0
1365 1365 [1]
1366 1366 $ hgph Upsilon -r 'min(draft())'
1367 1367 o 8 draft a-F - b740e3e5c05d
1368 1368 |
1369 1369 ~
1370 1370
1371 1371 $ hg -R Upsilon push Pi -r 8
1372 1372 pushing to Pi
1373 1373 searching for changes
1374 1374 adding changesets
1375 1375 adding manifests
1376 1376 adding file changes
1377 1377 added 1 changesets with 1 changes to 1 files
1378 1378 test-debug-phase: new rev 5: x -> 0
1379 1379 test-debug-phase: move rev 8: 1 -> 0
1380 1380
1381 1381 $ hgph Upsilon -r 'min(draft())'
1382 1382 o 9 draft a-G - 3e27b6f1eee1
1383 1383 |
1384 1384 ~
1385 1385
1386 1386 Test phases exchange when a phaseroot is on a merge
1387 1387
1388 1388 $ hg init mergetest
1389 1389 $ cd mergetest
1390 1390 > cat > .hg/hgrc << EOF
1391 1391 > [phases]
1392 1392 > publish = false
1393 1393 > EOF
1394 1394
1395 1395 $ hg debugdrawdag << EOF
1396 1396 > E Z
1397 1397 > |\|
1398 1398 > D Y
1399 1399 > | |
1400 1400 > C X
1401 1401 > |/
1402 1402 > B
1403 1403 > |
1404 1404 > A
1405 1405 > EOF
1406 1406 test-debug-phase: new rev 0: x -> 1
1407 1407 test-debug-phase: new rev 1: x -> 1
1408 1408 test-debug-phase: new rev 2: x -> 1
1409 1409 test-debug-phase: new rev 3: x -> 1
1410 1410 test-debug-phase: new rev 4: x -> 1
1411 1411 test-debug-phase: new rev 5: x -> 1
1412 1412 test-debug-phase: new rev 6: x -> 1
1413 1413 test-debug-phase: new rev 7: x -> 1
1414 1414
1415 1415 $ hg phase --public -r D
1416 1416 test-debug-phase: move rev 0: 1 -> 0
1417 1417 test-debug-phase: move rev 1: 1 -> 0
1418 1418 test-debug-phase: move rev 2: 1 -> 0
1419 1419 test-debug-phase: move rev 4: 1 -> 0
1420 1420
1421 1421 $ hg log -G -T '{shortest(node, 5)} {phase}'
1422 1422 o bb947 draft
1423 1423 |
1424 1424 | o 5ac28 draft
1425 1425 |/|
1426 1426 o | 13b7b draft
1427 1427 | |
1428 1428 | o f5853 public
1429 1429 | |
1430 1430 o | c67c4 draft
1431 1431 | |
1432 1432 | o 26805 public
1433 1433 |/
1434 1434 o 11247 public
1435 1435 |
1436 1436 o 426ba public
1437 1437
1438 1438 $ cd ..
1439 1439
1440 1440 Works with default settings
1441 1441
1442 1442 $ hg -R mergetest serve -p $HGPORT -d --pid-file=hg.pid
1443 1443 $ cat hg.pid >> $DAEMON_PIDS
1444 1444
1445 1445 $ hg clone -U http://localhost:$HGPORT mergetest-normal
1446 1446 requesting all changes
1447 1447 adding changesets
1448 1448 adding manifests
1449 1449 adding file changes
1450 1450 added 8 changesets with 7 changes to 7 files (+1 heads)
1451 1451 new changesets 426bada5c675:bb94757e651a
1452 1452 test-debug-phase: new rev 0: x -> 0
1453 1453 test-debug-phase: new rev 1: x -> 0
1454 1454 test-debug-phase: new rev 2: x -> 0
1455 1455 test-debug-phase: new rev 3: x -> 1
1456 1456 test-debug-phase: new rev 4: x -> 0
1457 1457 test-debug-phase: new rev 5: x -> 1
1458 1458 test-debug-phase: new rev 6: x -> 1
1459 1459 test-debug-phase: new rev 7: x -> 1
1460 1460
1461 1461 $ hg -R mergetest-normal log -G -T '{shortest(node, 5)} {phase}'
1462 1462 o bb947 draft
1463 1463 |
1464 1464 | o 5ac28 draft
1465 1465 |/|
1466 1466 o | 13b7b draft
1467 1467 | |
1468 1468 | o f5853 public
1469 1469 | |
1470 1470 o | c67c4 draft
1471 1471 | |
1472 1472 | o 26805 public
1473 1473 |/
1474 1474 o 11247 public
1475 1475 |
1476 1476 o 426ba public
1477 1477
1478 1478 $ killdaemons.py
1479 1479
1480 1480 With legacy listkeys over bundle2
1481 TODO issue 5939: public phase lost on 26805 and f5853
1481 (issue 5939: public phase was lost on 26805 and f5853 before, due to a bug
1482 of phase heads computation)
1482 1483
1483 1484 $ hg -R mergetest --config devel.legacy.exchange=phases serve -p $HGPORT -d --pid-file=hg.pid
1484 1485 $ cat hg.pid >> $DAEMON_PIDS
1485 1486
1486 1487 $ hg clone -U http://localhost:$HGPORT mergetest-nobinarypart
1487 1488 requesting all changes
1488 1489 adding changesets
1489 1490 adding manifests
1490 1491 adding file changes
1491 1492 added 8 changesets with 7 changes to 7 files (+1 heads)
1492 1493 new changesets 426bada5c675:bb94757e651a
1493 1494 test-debug-phase: new rev 0: x -> 0
1494 1495 test-debug-phase: new rev 1: x -> 0
1495 test-debug-phase: new rev 2: x -> 1
1496 test-debug-phase: new rev 2: x -> 0
1496 1497 test-debug-phase: new rev 3: x -> 1
1497 test-debug-phase: new rev 4: x -> 1
1498 test-debug-phase: new rev 4: x -> 0
1498 1499 test-debug-phase: new rev 5: x -> 1
1499 1500 test-debug-phase: new rev 6: x -> 1
1500 1501 test-debug-phase: new rev 7: x -> 1
1501 1502
1502 1503 $ hg -R mergetest-nobinarypart log -G -T '{shortest(node, 5)} {phase}'
1503 1504 o bb947 draft
1504 1505 |
1505 1506 | o 5ac28 draft
1506 1507 |/|
1507 1508 o | 13b7b draft
1508 1509 | |
1509 | o f5853 draft
1510 | o f5853 public
1510 1511 | |
1511 1512 o | c67c4 draft
1512 1513 | |
1513 | o 26805 draft
1514 | o 26805 public
1514 1515 |/
1515 1516 o 11247 public
1516 1517 |
1517 1518 o 426ba public
1518 1519
1519 1520 $ killdaemons.py
1520 1521
1521 1522 Without bundle2
1522 TODO issue 5939: public phase lost on 26805 and f5853
1523 (issue 5939: public phase was lost on 26805 and f5853 before, due to a bug
1524 of phase heads computation)
1523 1525
1524 1526 $ hg -R mergetest serve -p $HGPORT -d --pid-file=hg.pid
1525 1527 $ cat hg.pid >> $DAEMON_PIDS
1526 1528
1527 1529 $ hg --config devel.legacy.exchange=bundle1 clone -U http://localhost:$HGPORT mergetest-bundle1
1528 1530 requesting all changes
1529 1531 adding changesets
1530 1532 adding manifests
1531 1533 adding file changes
1532 1534 added 8 changesets with 7 changes to 7 files (+1 heads)
1533 1535 new changesets 426bada5c675:bb94757e651a
1534 1536 test-debug-phase: new rev 0: x -> 0
1535 1537 test-debug-phase: new rev 1: x -> 0
1536 test-debug-phase: new rev 2: x -> 1
1538 test-debug-phase: new rev 2: x -> 0
1537 1539 test-debug-phase: new rev 3: x -> 1
1538 test-debug-phase: new rev 4: x -> 1
1540 test-debug-phase: new rev 4: x -> 0
1539 1541 test-debug-phase: new rev 5: x -> 1
1540 1542 test-debug-phase: new rev 6: x -> 1
1541 1543 test-debug-phase: new rev 7: x -> 1
1542 1544
1543 1545 $ hg -R mergetest-bundle1 log -G -T '{shortest(node, 5)} {phase}'
1544 1546 o bb947 draft
1545 1547 |
1546 1548 | o 5ac28 draft
1547 1549 |/|
1548 1550 o | 13b7b draft
1549 1551 | |
1550 | o f5853 draft
1552 | o f5853 public
1551 1553 | |
1552 1554 o | c67c4 draft
1553 1555 | |
1554 | o 26805 draft
1556 | o 26805 public
1555 1557 |/
1556 1558 o 11247 public
1557 1559 |
1558 1560 o 426ba public
1559 1561
General Comments 0
You need to be logged in to leave comments. Login now