[PATCH 09 of 10 shelve-ext v2] shelve: add logic to preserve active bookmarks
Kostia Balytskyi
ikostia at fb.com
Thu Jan 19 10:10:36 EST 2017
# HG changeset patch
# User Kostia Balytskyi <ikostia at fb.com>
# Date 1484740179 28800
# Wed Jan 18 03:49:39 2017 -0800
# Node ID 088c9191d662d5c0003310119c51540926a815f7
# Parent 94a237a046059ef246aacb2c3ad809c9f0bdbe70
shelve: add logic to preserve active bookmarks
This adds an explicit active-bookmark-handling logic
to *both* traditional and obs-based shelve. Although it
is possible to only add it to obs-based, I think it would
be ugly and I see no harm in explicitly handling bookmarks
in addition to reliance on trasnactions.
diff --git a/hgext/shelve.py b/hgext/shelve.py
--- a/hgext/shelve.py
+++ b/hgext/shelve.py
@@ -29,6 +29,7 @@ import time
from mercurial.i18n import _
from mercurial import (
+ bookmarks,
bundle2,
bundlerepo,
changegroup,
@@ -188,6 +189,8 @@ class shelvedstate(object):
_nokeep = 'nokeep'
_obsbased = 'obsbased'
_traditional = 'traditional'
+ # colon is essential to differentiate from a real bookmark name
+ _noactivebook = ':no-active-bookmark'
def __init__(self, ui, repo):
self.ui = ui
@@ -210,6 +213,7 @@ class shelvedstate(object):
branchtorestore = fp.readline().strip()
keep = fp.readline().strip() == cls._keep
obsshelve = fp.readline().strip() == cls._obsbased
+ activebook = fp.readline().strip()
except (ValueError, TypeError) as err:
raise error.CorruptedState(str(err))
finally:
@@ -225,6 +229,9 @@ class shelvedstate(object):
obj.branchtorestore = branchtorestore
obj.keep = keep
obj.obsshelve = obsshelve
+ obj.activebookmark = ''
+ if activebook != cls._noactivebook:
+ obj.activebookmark = activebook
except error.RepoLookupError as err:
raise error.CorruptedState(str(err))
@@ -232,7 +239,7 @@ class shelvedstate(object):
@classmethod
def save(cls, repo, name, originalwctx, pendingctx, nodestoprune,
- branchtorestore, keep=False, obsshelve=False):
+ branchtorestore, keep=False, obsshelve=False, activebook=''):
fp = repo.vfs(cls._filename, 'wb')
fp.write('%i\n' % cls._version)
fp.write('%s\n' % name)
@@ -245,6 +252,7 @@ class shelvedstate(object):
fp.write('%s\n' % branchtorestore)
fp.write('%s\n' % (cls._keep if keep else cls._nokeep))
fp.write('%s\n' % (cls._obsbased if obsshelve else cls._traditional))
+ fp.write('%s\n' % (activebook or cls._noactivebook))
fp.close()
@classmethod
@@ -283,6 +291,16 @@ def cleanupoldbackups(repo):
if err.errno != errno.ENOENT:
raise
+def _backupactivebookmark(repo):
+ activebookmark = repo._activebookmark
+ if activebookmark:
+ bookmarks.deactivate(repo)
+ return activebookmark
+
+def _restoreactivebookmark(repo, mark):
+ if mark:
+ bookmarks.activate(repo, mark)
+
def _aborttransaction(repo):
'''Abort current transaction for shelve/unshelve, but keep dirstate
'''
@@ -402,7 +420,9 @@ def _includeunknownfiles(repo, pats, opt
extra['shelve_unknown'] = '\0'.join(s.unknown)
repo[None].add(s.unknown)
-def _finishshelve(ui, repo, tr, node):
+def _finishshelve(ui, repo, tr, node, activebookmark):
+ if activebookmark:
+ bookmarks.activate(repo, activebookmark)
if isobsshelve(repo, ui):
obsolete.createmarkers(repo, [(repo.unfiltered()[node], ())])
tr.close()
@@ -426,7 +446,7 @@ def _docreatecmd(ui, repo, pats, opts):
if not opts.get('message'):
opts['message'] = desc
- lock = tr = None
+ lock = tr = activebookmark = None
try:
lock = repo.lock()
@@ -442,6 +462,7 @@ def _docreatecmd(ui, repo, pats, opts):
not opts.get('addremove', False))
name = getshelvename(repo, parent, opts)
+ activebookmark = _backupactivebookmark(repo)
extra = {}
if includeunknown:
_includeunknownfiles(repo, pats, opts, extra)
@@ -456,7 +477,8 @@ def _docreatecmd(ui, repo, pats, opts):
node = cmdutil.commit(ui, repo, commitfunc, pats, opts)
else:
node = cmdutil.dorecord(ui, repo, commitfunc, None,
- False, cmdutil.recordfilter, *pats, **opts)
+ False, cmdutil.recordfilter, *pats,
+ **opts)
if not node:
_nothingtoshelvemessaging(ui, repo, pats, opts)
return 1
@@ -473,8 +495,9 @@ def _docreatecmd(ui, repo, pats, opts):
if origbranch != repo['.'].branch() and not _isbareshelve(pats, opts):
repo.dirstate.setbranch(origbranch)
- _finishshelve(ui, repo, tr, node)
+ _finishshelve(ui, repo, tr, node, activebookmark)
finally:
+ _restoreactivebookmark(repo, activebookmark)
lockmod.release(tr, lock)
def _isbareshelve(pats, opts):
@@ -697,6 +720,7 @@ def unshelvecontinue(ui, repo, state, op
restorebranch(ui, repo, state.branchtorestore)
state.prunenodes()
+ _restoreactivebookmark(repo, state.activebookmark)
shelvedstate.clear(repo)
unshelvecleanup(ui, repo, state.name, opts)
ui.status(_("unshelve of '%s' complete\n") % state.name)
@@ -741,7 +765,8 @@ def _unshelverestorecommit(ui, repo, bas
return repo, shelvectx
def _rebaserestoredcommit(ui, repo, opts, tr, oldtiprev, basename, pctx,
- tmpwctx, shelvectx, branchtorestore, obsshelve):
+ tmpwctx, shelvectx, branchtorestore, obsshelve,
+ activebookmark):
"""Rebase restored commit from its original location to a destination"""
# If the shelve is not immediately on top of the commit
# we'll be merging with, rebase it to be on top.
@@ -778,7 +803,8 @@ def _rebaserestoredcommit(ui, repo, opts
nodestoprune = [repo.changelog.node(rev)
for rev in xrange(oldtiprev, len(repo))]
shelvedstate.save(repo, basename, pctx, tmpwctx, nodestoprune,
- branchtorestore, opts.get('keep'), obsshelve)
+ branchtorestore, opts.get('keep'), obsshelve,
+ activebookmark)
util.rename(repo.join('rebasestate'),
repo.join('unshelverebasestate'))
@@ -805,7 +831,8 @@ def _forgetunknownfiles(repo, shelvectx,
toforget = (addedafter & shelveunknown) - addedbefore
repo[None].forget(toforget)
-def _finishunshelve(repo, oldtiprev, tr, obsshelve):
+def _finishunshelve(repo, oldtiprev, tr, obsshelve, activebookmark):
+ _restoreactivebookmark(repo, activebookmark)
if obsshelve:
tr.close()
return
@@ -958,6 +985,7 @@ def _dounshelve(ui, repo, *shelved, **op
# and shelvectx is the unshelved changes. Then we merge it all down
# to the original pctx.
+ activebookmark = _backupactivebookmark(repo)
tmpwctx, addedbefore = _commitworkingcopychanges(ui, repo, opts,
tmpwctx)
@@ -973,7 +1001,7 @@ def _dounshelve(ui, repo, *shelved, **op
shelvectx = _rebaserestoredcommit(ui, repo, opts, tr, oldtiprev,
basename, pctx, tmpwctx,
shelvectx, branchtorestore,
- obsshelve)
+ obsshelve, activebookmark)
mergefiles(ui, repo, pctx, shelvectx)
restorebranch(ui, repo, branchtorestore)
_forgetunknownfiles(repo, shelvectx, addedbefore)
@@ -982,7 +1010,7 @@ def _dounshelve(ui, repo, *shelved, **op
_obsoleteredundantnodes(repo, tr, pctx, shelvectx, tmpwctx)
shelvedstate.clear(repo)
- _finishunshelve(repo, oldtiprev, tr, obsshelve)
+ _finishunshelve(repo, oldtiprev, tr, obsshelve, activebookmark)
unshelvecleanup(ui, repo, basename, opts)
finally:
if tr:
More information about the Mercurial-devel
mailing list