localrepo: add sparse caches
authorGregory Szorc <gregory.szorc@gmail.com>
Thu, 06 Jul 2017 12:20:53 -0700
changeset 33302 36a415b5a4b2
parent 33301 ca4b78eb11e7
child 33303 8b571495d811
localrepo: add sparse caches The sparse extension maintains caches for the sparse files to a signature and a signature to a matcher. This allows the sparse matchers to be resolved quickly, which is apparently something that can occur in loops. This patch ports the sparse caches to the localrepo class pretty much as-is. There is potentially room to improve the caching mechanism. But that can be done as a follow-up. The default invalidatecaches() now clears the relevant sparse cache. invalidatesignaturecache() has been moved to sparse.py.
hgext/sparse.py
mercurial/localrepo.py
mercurial/sparse.py
--- a/hgext/sparse.py	Thu Jul 06 12:26:04 2017 -0700
+++ b/hgext/sparse.py	Thu Jul 06 12:20:53 2017 -0700
@@ -421,7 +421,7 @@
             """Returns the signature string representing the contents of the
             current project sparse configuration. This can be used to cache the
             sparse matcher for a given set of revs."""
-            signaturecache = self.signaturecache
+            signaturecache = self._sparsesignaturecache
             signature = signaturecache.get('signature')
             if includetemp:
                 tempsignature = signaturecache.get('tempsignature')
@@ -445,13 +445,6 @@
                     signaturecache['tempsignature'] = tempsignature
             return '%s %s' % (str(signature), str(tempsignature))
 
-        def invalidatecaches(self):
-            self.invalidatesignaturecache()
-            return super(SparseRepo, self).invalidatecaches()
-
-        def invalidatesignaturecache(self):
-            self.signaturecache.clear()
-
         def sparsematch(self, *revs, **kwargs):
             """Returns the sparse match function for the given revs.
 
@@ -470,7 +463,7 @@
 
             key = '%s %s' % (str(signature), ' '.join([str(r) for r in revs]))
 
-            result = self.sparsecache.get(key, None)
+            result = self._sparsematchercache.get(key, None)
             if result:
                 return result
 
@@ -513,7 +506,7 @@
                 tempincludes = self.gettemporaryincludes()
                 result = forceincludematcher(result, tempincludes)
 
-            self.sparsecache[key] = result
+            self._sparsematchercache[key] = result
 
             return result
 
@@ -523,7 +516,7 @@
                 '\n'.join(sorted(include)),
                 '\n'.join(sorted(exclude)))
             self.vfs.write("sparse", raw)
-            self.invalidatesignaturecache()
+            sparse.invalidatesignaturecache(self)
 
         def addtemporaryincludes(self, files):
             includes = self.gettemporaryincludes()
@@ -541,7 +534,7 @@
         def _writetemporaryincludes(self, includes):
             raw = '\n'.join(sorted(includes))
             self.vfs.write('tempsparse', raw)
-            self.invalidatesignaturecache()
+            sparse.invalidatesignaturecache(self)
 
         def prunetemporaryincludes(self):
             if repo.vfs.exists('tempsparse'):
@@ -572,15 +565,14 @@
                     dirstate.drop(file)
 
                 self.vfs.unlink('tempsparse')
-                self.invalidatesignaturecache()
+                sparse.invalidatesignaturecache(self)
                 msg = _("cleaned up %d temporarily added file(s) from the "
                         "sparse checkout\n")
                 ui.status(msg % len(tempincludes))
 
     if 'dirstate' in repo._filecache:
         repo.dirstate.repo = repo
-    repo.sparsecache = {}
-    repo.signaturecache = {}
+
     repo.__class__ = SparseRepo
 
 @command('^debugsparse', [
--- a/mercurial/localrepo.py	Thu Jul 06 12:26:04 2017 -0700
+++ b/mercurial/localrepo.py	Thu Jul 06 12:20:53 2017 -0700
@@ -422,6 +422,11 @@
         # generic mapping between names and nodes
         self.names = namespaces.namespaces()
 
+        # Key to signature value.
+        self._sparsesignaturecache = {}
+        # Signature to cached matcher instance.
+        self._sparsematchercache = {}
+
     def close(self):
         self._writecaches()
 
@@ -1300,6 +1305,7 @@
 
         self.unfiltered()._branchcaches.clear()
         self.invalidatevolatilesets()
+        self._sparsesignaturecache.clear()
 
     def invalidatevolatilesets(self):
         self.filteredrevcache.clear()
--- a/mercurial/sparse.py	Thu Jul 06 12:26:04 2017 -0700
+++ b/mercurial/sparse.py	Thu Jul 06 12:20:53 2017 -0700
@@ -126,3 +126,6 @@
         profiles.update(patternsforrev(repo, rev)[2])
 
     return profiles
+
+def invalidatesignaturecache(repo):
+    repo._sparsesignaturecache.clear()