[PATCH 4 of 4 V2] destutil: add more precise error classes for destmerge

Pierre-Yves David pierre-yves.david at ens-lyon.org
Sun Feb 14 10:38:16 EST 2016


# HG changeset patch
# User Pierre-Yves David <pierre-yves.david at fb.com>
# Date 1455060641 0
#      Tue Feb 09 23:30:41 2016 +0000
# Node ID 191223342dcb0e8e87b2b3f038fdda98b3d51a26
# Parent  e025ec586bdf3111bb1ca85672c7cab3b407cf46
# EXP-Topic destination
# Available At http://hg.netv6.net/marmoute-wip/mercurial/
#              hg pull http://hg.netv6.net/marmoute-wip/mercurial/ -r 191223342dcb
destutil: add more precise error classes for destmerge

Having exception classes more precise than 'Abort' will allow us to properly
catch "nothing to rebase" situations when we will be using 'destmerge' in
rebase.

diff --git a/mercurial/destutil.py b/mercurial/destutil.py
--- a/mercurial/destutil.py
+++ b/mercurial/destutil.py
@@ -207,14 +207,14 @@ def _destmergebook(repo, action='merge',
             node = bmheads[1]
         else:
             node = bmheads[0]
     elif len(bmheads) > 2:
         msg, hint = msgdestmerge['toomanybookmarks'][action]
-        raise error.Abort(msg, hint=hint)
+        raise error.ManyMergeDestAbort(msg, hint=hint)
     elif len(bmheads) <= 1:
         msg, hint = msgdestmerge['nootherbookmarks'][action]
-        raise error.Abort(msg, hint=hint)
+        raise error.NoMergeDestAbort(msg, hint=hint)
     assert node is not None
     return node
 
 def _destmergebranch(repo, action='merge', sourceset=None, onheadcheck=True):
     """find merge destination based on branch heads"""
@@ -223,17 +223,17 @@ def _destmergebranch(repo, action='merge
     if sourceset is None:
         sourceset = [repo[repo.dirstate.p1()].rev()]
         branch = repo.dirstate.branch()
     elif not sourceset:
         msg, hint = msgdestmerge['emptysourceset'][action]
-        raise error.Abort(msg, hint=hint)
+        raise error.NoMergeDestAbort(msg, hint=hint)
     else:
         branch = None
         for ctx in repo.set('roots(%ld::%ld)', sourceset, sourceset):
             if branch is not None and ctx.branch() != branch:
                 msg, hint = msgdestmerge['multiplebranchessourceset'][action]
-                raise error.Abort(msg, hint=hint)
+                raise error.ManyMergeDestAbort(msg, hint=hint)
             branch = ctx.branch()
 
     bheads = repo.branchheads(branch)
     if onheadcheck and not repo.revs('%ld and %ln', sourceset, bheads):
         # Case A: working copy if not on a head. (merge only)
@@ -254,11 +254,11 @@ def _destmergebranch(repo, action='merge
         # This means that there will be more than 1 candidate. This is
         # ambiguous. We abort asking the user to pick as explicit destination
         # instead.
         msg, hint = msgdestmerge['toomanyheads'][action]
         msg %= (branch, len(bheads) + 1)
-        raise error.Abort(msg, hint=hint)
+        raise error.ManyMergeDestAbort(msg, hint=hint)
     elif not nbhs:
         # Case B: There is no other anonymous heads
         #
         # This means that there is no natural candidate to merge with.
         # We abort, with various messages for various cases.
@@ -267,11 +267,11 @@ def _destmergebranch(repo, action='merge
         elif len(repo.heads()) > 1:
             msg, hint = msgdestmerge['nootherbranchheads'][action]
             msg %= branch
         else:
             msg, hint = msgdestmerge['nootherheads'][action]
-        raise error.Abort(msg, hint=hint)
+        raise error.NoMergeDestAbort(msg, hint=hint)
     else:
         node = nbhs[0]
     assert node is not None
     return node
 
diff --git a/mercurial/error.py b/mercurial/error.py
--- a/mercurial/error.py
+++ b/mercurial/error.py
@@ -70,10 +70,19 @@ class ConfigError(Abort):
     """Exception raised when parsing config files"""
 
 class UpdateAbort(Abort):
     """Raised when an update is aborted for destination issue"""
 
+class MergeDestAbort(Abort):
+    """Raised when an update is aborted for destination issues"""
+
+class NoMergeDestAbort(Abort):
+    """Raised when an update is aborted because there is nothing to merge"""
+
+class ManyMergeDestAbort(Abort):
+    """Raised when an update is aborted because destination is ambigious"""
+
 class ResponseExpected(Abort):
     """Raised when an EOF is received for a prompt"""
     def __init__(self):
         from .i18n import _
         Abort.__init__(self, _('response expected'))


More information about the Mercurial-devel mailing list