[PATCH 4 of 6 V3] merge: consider successor changesets for a bare update

Sean Farley sean.michael.farley at gmail.com
Wed Jan 15 18:34:19 CST 2014


# HG changeset patch
# User Sean Farley <sean.michael.farley at gmail.com>
# Date 1389825678 21600
#      Wed Jan 15 16:41:18 2014 -0600
# Node ID 97551cab431afbaa04f85ba0278e800b026dc74d
# Parent  c545df40daa10ff9200c81ba566db6329175280b
merge: consider successor changesets for a bare update

Previously, a bare update would ignore any successor changesets thus
potentially leaving you on an obsolete head. This happens commonly when there
is an old bookmark that hasn't been moved forward which is the motivating
reason for this patch series.

Now, we will check for successor changesets if two conditions hold: 1) we are
doing a bare update 2) *and* we are currently on an obsolete head.

If we are in this situation, then we calculate the branchtip of the successor
set and update to that changeset.

Tests coverage has been added.

diff --git a/mercurial/merge.py b/mercurial/merge.py
--- a/mercurial/merge.py
+++ b/mercurial/merge.py
@@ -694,10 +694,32 @@ def update(repo, node, branchmerge, forc
             except error.RepoLookupError:
                 if wc.branch() == "default": # no default branch!
                     node = repo.lookup("tip") # update to tip
                 else:
                     raise util.Abort(_("branch %s not found") % wc.branch())
+
+            if p1.obsolete() and not p1.children():
+                # allow updating to successors
+                successors = obsolete.successorssets(repo, p1.node())
+
+                # check for divergence
+                if len(successors) > 1:
+                    raise util.Abort(_("candidate changeset is divergent"),
+                                     hint=_("use 'hg evolve' to resolve"
+                                            "divergence"))
+
+                # we're not divergent, so we only have one element
+                successors = successors[0]
+
+                # if successors is empty here, then it has been pruned and
+                # there is nothing to consider updating to
+                if successors:
+                    # get the max revision for the given successors set
+                    unfil = [repo.unfiltered()[n].rev() for n in successors]
+                    node = repo[max(unfil)].node()
+                    pa = p1
+
         overwrite = force and not branchmerge
 
         p2 = repo[node]
         if pa is None:
             pa = p1.ancestor(p2)
diff --git a/tests/test-update-branches.t b/tests/test-update-branches.t
--- a/tests/test-update-branches.t
+++ b/tests/test-update-branches.t
@@ -227,10 +227,18 @@ the bookmark (issue4015)
   $ hg book bm
   moving bookmark 'bm' forward from 6efa171f091b
   $ hg bookmarks
    * bm                        5:ff252e8273df
 
+Test that 4 is detected as the no-argument destination from 3
+  $ hg up --quiet 0          # we should be able to update to 3 directly
+  $ hg up --quiet --hidden 3 # but not implemented yet.
+  $ hg up
+  1 files updated, 0 files merged, 0 files removed, 0 files unresolved
+  $ hg id
+  d047485b3896+ (b1)
+
 Test that 5 is detected as a valid destination from 1
   $ hg up --quiet 0          # we should be able to update to 3 directly
   $ hg up --quiet --hidden 3 # but not implemented yet.
   $ hg up 5
   1 files updated, 0 files merged, 0 files removed, 0 files unresolved


More information about the Mercurial-devel mailing list