Patchwork [10,of,11,sparse] dirstate: move customizations to rebuild() from sparse extension

login
register
mail settings
Submitter Gregory Szorc
Date July 8, 2017, 11:29 p.m.
Message ID <a2867557f9c2314aeea1.1499556545@ubuntu-vm-main>
Download mbox | patch
Permalink /patch/22136/
State Accepted
Headers show

Comments

Gregory Szorc - July 8, 2017, 11:29 p.m.
# HG changeset patch
# User Gregory Szorc <gregory.szorc@gmail.com>
# Date 1499537680 25200
#      Sat Jul 08 11:14:40 2017 -0700
# Node ID a2867557f9c2314aeea19a946dfb8e167def4fb8
# Parent  151bee7bb0e2ea8e612bbb0e16fa45d6e446ec05
dirstate: move customizations to rebuild() from sparse extension

This is a pretty straightforward port of the monkeypatch from
sparse directly into dirstate.

Unless the sparse feature is enabled via the sparse extension,
the sparse matcher will be an alwaysmatcher and the added
branch won't be taken.

Patch

diff --git a/hgext/sparse.py b/hgext/sparse.py
--- a/hgext/sparse.py
+++ b/hgext/sparse.py
@@ -223,23 +223,6 @@  def _setupdirstate(ui):
 
     replacefilecache(dirstate.dirstate, '_ignore', ignorewrapper)
 
-    # dirstate.rebuild should not add non-matching files
-    def _rebuild(orig, self, parent, allfiles, changedfiles=None):
-        matcher = self._sparsematcher
-        if not matcher.always():
-            allfiles = allfiles.matches(matcher)
-            if changedfiles:
-                changedfiles = [f for f in changedfiles if matcher(f)]
-
-            if changedfiles is not None:
-                # In _rebuild, these files will be deleted from the dirstate
-                # when they are not found to be in allfiles
-                dirstatefilestoremove = set(f for f in self if not matcher(f))
-                changedfiles = dirstatefilestoremove.union(changedfiles)
-
-        return orig(self, parent, allfiles, changedfiles)
-    extensions.wrapfunction(dirstate.dirstate, 'rebuild', _rebuild)
-
 @command('^debugsparse', [
     ('I', 'include', False, _('include files in the sparse checkout')),
     ('X', 'exclude', False, _('exclude files in the sparse checkout')),
diff --git a/mercurial/dirstate.py b/mercurial/dirstate.py
--- a/mercurial/dirstate.py
+++ b/mercurial/dirstate.py
@@ -774,6 +774,19 @@  class dirstate(object):
         self._dirty = True
 
     def rebuild(self, parent, allfiles, changedfiles=None):
+        # Filter allfiles and changedfiles through a sparse matcher if it is
+        # active.
+        matcher = self._sparsematcher
+        if not matcher.always():
+            allfiles = allfiles.matches(matcher)
+
+            if changedfiles:
+                changedfiles = [f for f in changedfiles if matcher(f)]
+
+            if changedfiles is not None:
+                toremove = set(f for f in self if not matcher(f))
+                changedfiles = toremove.union(changedfiles)
+
         if changedfiles is None:
             # Rebuild entire dirstate
             changedfiles = allfiles