# HG changeset patch # User Joerg Sonnenberger # Date 2021-01-18 23:20:53 # Node ID 0903d6b9b1dfc66f52fcb5794a71a2cde22313ef # Parent cad17d50736ca5bd3ba83b82697461a2cf646fdc repository: introduce register_changeset callback The new callback is called whenever a changeset is added to the repository (commit, unbundle or exchange). Since the bulk operations already parse the changeset (readfiles or full changesetrevision), always use the latter to avoid redundant lookups. The first consumer of the new interface needs to look at extra. Differential Revision: https://phab.mercurial-scm.org/D9780 diff --git a/mercurial/changegroup.py b/mercurial/changegroup.py --- a/mercurial/changegroup.py +++ b/mercurial/changegroup.py @@ -323,7 +323,10 @@ class cg1unpacker(object): cgnodes.append(node) def onchangelog(cl, node): - efilesset.update(cl.readfiles(node)) + rev = cl.rev(node) + ctx = cl.changelogrevision(rev) + efilesset.update(ctx.files) + repo.register_changeset(rev, ctx) self.changelogheader() deltas = self.deltaiter() diff --git a/mercurial/commit.py b/mercurial/commit.py --- a/mercurial/commit.py +++ b/mercurial/commit.py @@ -97,6 +97,9 @@ def commitctx(repo, ctx, error=False, or extra, ) rev = repo[n].rev() + if oldtip != repo.changelog.tiprev(): + repo.register_changeset(rev, repo.changelog.changelogrevision(rev)) + xp1, xp2 = p1.hex(), p2 and p2.hex() or b'' repo.hook( b'pretxncommit', diff --git a/mercurial/exchangev2.py b/mercurial/exchangev2.py --- a/mercurial/exchangev2.py +++ b/mercurial/exchangev2.py @@ -372,6 +372,8 @@ def _processchangesetdata(repo, tr, objs # so we can set the linkrev accordingly when manifests are added. manifestnodes[rev] = revision.manifest + repo.register_changeset(rev, revision) + nodesbyphase = {phase: set() for phase in phases.phasenames.values()} remotebookmarks = {} diff --git a/mercurial/interfaces/repository.py b/mercurial/interfaces/repository.py --- a/mercurial/interfaces/repository.py +++ b/mercurial/interfaces/repository.py @@ -1641,6 +1641,14 @@ class ilocalrepositorymain(interfaceutil def revbranchcache(): pass + def register_changeset(rev, changelogrevision): + """Extension point for caches for new nodes. + + Multiple consumers are expected to need parts of the changelogrevision, + so it is provided as optimization to avoid duplicate lookups. A simple + cache would be fragile when other revisions are accessed, too.""" + pass + def branchtip(branchtip, ignoremissing=False): """Return the tip node for a given branch.""" diff --git a/mercurial/localrepo.py b/mercurial/localrepo.py --- a/mercurial/localrepo.py +++ b/mercurial/localrepo.py @@ -2062,6 +2062,9 @@ class localrepository(object): self._revbranchcache = branchmap.revbranchcache(self.unfiltered()) return self._revbranchcache + def register_changeset(self, rev, changelogrevision): + pass + def branchtip(self, branch, ignoremissing=False): """return the tip node for a given branch