# HG changeset patch # User Matt Harbison # Date 2022-04-18 15:21:09 # Node ID 20d151e434290560812de96b2a7ce9908d3fac2f # Parent 9c8d67a3af5e1f360f4a3677fb205bb27a34d0e2 git: adapt to some recent dirstate API changes There are still old methods like add() and drop(). I don't see anything that looks equivalent, so there's likely more work to do. But this allows diff and commit to work again on the simple webpage repo for thg. Differential Revision: https://phab.mercurial-scm.org/D12567 diff --git a/hgext/git/__init__.py b/hgext/git/__init__.py --- a/hgext/git/__init__.py +++ b/hgext/git/__init__.py @@ -16,6 +16,7 @@ from mercurial import ( localrepo, pycompat, registrar, + requirements as requirementsmod, scmutil, store, util, @@ -300,9 +301,15 @@ def reposetup(ui, repo): class gitlocalrepo(orig): def _makedirstate(self): + v2_req = requirementsmod.DIRSTATE_V2_REQUIREMENT + use_dirstate_v2 = v2_req in self.requirements + # TODO narrow support here return dirstate.gitdirstate( - self.ui, self.vfs.base, self.store.git + self.ui, + self.vfs, + self.store.git, + use_dirstate_v2, ) def commit(self, *args, **kwargs): diff --git a/hgext/git/dirstate.py b/hgext/git/dirstate.py --- a/hgext/git/dirstate.py +++ b/hgext/git/dirstate.py @@ -4,6 +4,7 @@ import os from mercurial.node import sha1nodeconstants from mercurial import ( + dirstatemap, error, extensions, match as matchmod, @@ -11,6 +12,9 @@ from mercurial import ( scmutil, util, ) +from mercurial.dirstateutils import ( + timestamp, +) from mercurial.interfaces import ( dirstate as intdirstate, util as interfaceutil, @@ -18,6 +22,9 @@ from mercurial.interfaces import ( from . import gitutil + +DirstateItem = dirstatemap.DirstateItem +propertycache = util.propertycache pygit2 = gitutil.get_pygit2() @@ -67,13 +74,28 @@ if pygit2: @interfaceutil.implementer(intdirstate.idirstate) class gitdirstate: - def __init__(self, ui, root, gitrepo): + def __init__(self, ui, vfs, gitrepo, use_dirstate_v2): self._ui = ui - self._root = os.path.dirname(root) + self._root = os.path.dirname(vfs.base) + self._opener = vfs self.git = gitrepo self._plchangecallbacks = {} # TODO: context.poststatusfixup is bad and uses this attribute self._dirty = False + self._mapcls = dirstatemap.dirstatemap + self._use_dirstate_v2 = use_dirstate_v2 + + @propertycache + def _map(self): + """Return the dirstate contents (see documentation for dirstatemap).""" + self._map = self._mapcls( + self._ui, + self._opener, + self._root, + sha1nodeconstants, + self._use_dirstate_v2, + ) + return self._map def p1(self): try: @@ -142,6 +164,13 @@ class gitdirstate: [], [], ) + + try: + mtime_boundary = timestamp.get_fs_now(self._opener) + except OSError: + # In largefiles or readonly context + mtime_boundary = None + gstatus = self.git.status() for path, status in gstatus.items(): path = pycompat.fsencode(path) @@ -193,6 +222,7 @@ class gitdirstate: scmutil.status( modified, added, removed, deleted, unknown, ignored, clean ), + mtime_boundary, ) def flagfunc(self, buildfallback): @@ -205,6 +235,13 @@ class gitdirstate: os.path.dirname(pycompat.fsencode(self.git.path)) ) + def get_entry(self, path): + """return a DirstateItem for the associated path""" + entry = self._map.get(path) + if entry is None: + return DirstateItem() + return entry + def normalize(self, path): normed = util.normcase(path) assert normed == path, b"TODO handling of case folding: %s != %s" % (