[PATCH [RFC][V2]] revert: add support for reverting subrepos

Angel Ezquerra angel.ezquerra at gmail.com
Thu Jan 12 14:48:04 CST 2012

# HG changeset patch
# User Angel Ezquerra <angel.ezquerra at gmail.com>
# Date 1326364670 -3600
# Node ID 747979cca1c541b84d2a15b3e037c63388db1c59
# Parent  c47d69ce5208d5b5cfd2fb2f0f1d7a2b4795fbf5
revert: add support for reverting subrepos

Reverting a subrepo is done by updating it to the revision that is selected on
the parent repo .hgsubstate file.


- reverting added and removed subrepos is not supported (yet).

- This patch only allows reverting subrepos if the --no-backup flag is used,
since no backups are performed on the contents of the subrepo. It could be
possible to add support for backing up the subrepo contents by first performing
a "revert --all" on the subrepo, and then updating the subrepo to the proper

- The behavior of the --all flag has changed. It now reverts subrepos as well.
Note that this may lead to data loss if the user has a dirty subrepo. Since this
only works with the --no-backup flag it seems reasonable.

diff --git a/mercurial/commands.py b/mercurial/commands.py
--- a/mercurial/commands.py
+++ b/mercurial/commands.py
@@ -4791,8 +4791,6 @@
             if path in names:
             if path in repo[node].substate:
-                ui.warn("%s: %s\n" % (m.rel(path),
-                    'reverting subrepos is unsupported'))
             path_ = path + '/'
             for f in names:
@@ -4806,6 +4804,13 @@
             if abs not in names:
                 names[abs] = m.rel(abs), m.exact(abs)
+        targetsubs = [s for s in repo[node].substate if m(s)]
+        if targetsubs and not opts.get('no_backup'):
+            msg = _("cannot revert subrepos unless the no-backup flag is set")
+            hint = _("there are subrepos on the revert list, "
+                     "use --no-backup to revert them")
+            raise util.Abort(msg, hint=hint)
         m = scmutil.matchfiles(repo, names)
         changes = repo.status(match=m)[:4]
         modified, added, removed, deleted = map(set, changes)
@@ -4934,6 +4939,13 @@
+            if targetsubs:
+                # Revert the subrepos on the revert list
+                # reverting a subrepo is done by updating it to the revision
+                # specified in the corresponding substate dictionary
+                for sname in targetsubs:
+                    ui.status(_('reverting subrepo %s\n') % sname)
+                    ctx.sub(sname).get(ctx.substate[sname], overwrite=True)

More information about the Mercurial-devel mailing list