[PATCH 3 of 4] revert: call status against revert target too

Pierre-Yves David pierre-yves.david at ens-lyon.org
Wed Aug 13 15:13:53 CDT 2014


# HG changeset patch
# User Pierre-Yves David <pierre-yves.david at fb.com>
# Date 1403621232 -3600
#      Tue Jun 24 15:47:12 2014 +0100
# Node ID 404ea53d797b8de16c6ce15da42663b08cf9bcf7
# Parent  f92a82e1addd276b8a05488410c506e41c88bc4e
revert: call status against revert target too

We now call status against the target (and possibly against the working
directory parent is different). We do not use the information from the two
sources yet, but this is coming soon.

We need the status information aganst the dirstate in all case because we need
to be able to backup local modification.

diff --git a/mercurial/cmdutil.py b/mercurial/cmdutil.py
--- a/mercurial/cmdutil.py
+++ b/mercurial/cmdutil.py
@@ -2364,14 +2364,34 @@ def revert(ui, repo, ctx, parents, *pats
                 names[abs] = m.rel(abs), m.exact(abs)
 
         # get the list of subrepos that must be reverted
         targetsubs = sorted(s for s in ctx.substate if m(s))
 
-        # Find status of all file in `names`. (Against working directory parent)
+        # Find status of all file in `names`.
         m = scmutil.matchfiles(repo, names)
-        changes = repo.status(node1=parent, match=m)[:4]
-        dsmodified, dsadded, dsremoved, dsdeleted = map(set, changes)
+
+        changes = repo.status(node1=node, match=m, clean=True)
+        modified = set(changes[0])
+        added    = set(changes[1])
+        removed  = set(changes[2])
+        deleted  = set(changes[3])
+
+        # We need to account for the state of file in the dirstate
+        #
+        # Even, when we revert agains something else than parent. this will
+        # slightly alter the behavior of revert (doing back up or not, delete
+        # or just forget etc)
+        if parent == node:
+            dsmodified = modified
+            dsadded = added
+            dsremoved = removed
+            modified, added, removed = set(), set(), set()
+        else:
+            changes = repo.status(node1=parent, match=m)
+            dsmodified = set(changes[0])
+            dsadded    = set(changes[1])
+            dsremoved  = set(changes[2])
 
         # if f is a rename, update `names` to also revert the source
         cwd = repo.getcwd()
         for f in dsadded:
             src = repo.dirstate.copied(f)
@@ -2393,12 +2413,12 @@ def revert(ui, repo, ctx, parents, *pats
         dsmodified -= missingmodified
         missingadded = dsadded - smf
         dsadded -= missingadded
         missingremoved = dsremoved - smf
         dsremoved -= missingremoved
-        missingdeleted = dsdeleted - smf
-        dsdeleted -= missingdeleted
+        missingdeleted = deleted - smf
+        deleted -= missingdeleted
 
         # action to be actually performed by revert
         # (<list of file>, message>) tuple
         actions = {'revert': ([], _('reverting %s\n')),
                    'add': ([], _('adding %s\n')),
@@ -2414,11 +2434,11 @@ def revert(ui, repo, ctx, parents, *pats
             (missingmodified,  (actions['remove'],   True)),
             (dsadded,          (actions['revert'],   True)),
             (missingadded,     (actions['remove'],   False)),
             (dsremoved,        (actions['undelete'], True)),
             (missingremoved,   (None,                False)),
-            (dsdeleted,        (actions['revert'],   False)),
+            (deleted,          (actions['revert'],   False)),
             (missingdeleted,   (actions['remove'],   False)),
             )
 
         for abs, (rel, exact) in sorted(names.items()):
             # hash on file in target manifest (or None if missing from target)


More information about the Mercurial-devel mailing list