diff --git a/mercurial/localrepo.py b/mercurial/localrepo.py --- a/mercurial/localrepo.py +++ b/mercurial/localrepo.py @@ -1469,6 +1469,8 @@ class localrepository: # post-dirstate-status hooks self._postdsstatus = [] + self._pending_narrow_pats = None + # generic mapping between names and nodes self.names = namespaces.namespaces() @@ -1799,7 +1801,11 @@ class localrepository: A tuple of (includes, excludes). """ - return narrowspec.load(self) + # the narrow management should probably move into its own object + val = self._pending_narrow_pats + if val is None: + val = narrowspec.load(self) + return val @storecache(narrowspec.FILENAME) def _storenarrowmatch(self): diff --git a/mercurial/narrowspec.py b/mercurial/narrowspec.py --- a/mercurial/narrowspec.py +++ b/mercurial/narrowspec.py @@ -5,6 +5,7 @@ # This software may be used and distributed according to the terms of the # GNU General Public License version 2 or any later version. +import weakref from .i18n import _ from .pycompat import getattr @@ -174,10 +175,40 @@ def load(repo): def save(repo, includepats, excludepats): + repo = repo.unfiltered() + validatepatterns(includepats) validatepatterns(excludepats) spec = format(includepats, excludepats) - repo.svfs.write(FILENAME, spec) + + tr = repo.currenttransaction() + if tr is None: + repo.svfs.write(FILENAME, spec) + else: + # the roundtrip is sometime different + # not taking any chance for now + value = parseconfig(repo.ui, spec) + reporef = weakref.ref(repo) + + def clean_pending(tr): + r = reporef() + if r is not None: + r._pending_narrow_pats = None + + tr.addpostclose(b'narrow-spec', clean_pending) + tr.addabort(b'narrow-spec', clean_pending) + repo._pending_narrow_pats = value + + def write_spec(f): + f.write(spec) + + tr.addfilegenerator( + # XXX think about order at some point + b"narrow-spec", + (FILENAME,), + write_spec, + location=b'store', + ) def copytoworkingcopy(repo):