interfaces: convert `imanifestrevisionstored` to a Protocol class
This is similar to 1df97507c6b8 for `ipeer`, because the Protocol nature needs
to be explicit on each class, as it isn't inherited.
While we're here, make the methods abstract. There's some background info on
this in f5d134e57f51 and fd200f5bcaea, but in short, the plan is to explicitly
subclass this instead of relying on structured typing, and explicit inheritence
will see this as a method implementation that returns None at runtime
(regardless of how it is typed), instead of a mandatory function for the
subclass to supply. The `Protocol` class has `abc.ABCMeta` as the metaclass, so
there's nothing more to do with the inheritence list.
--- a/mercurial/interfaces/repository.py Wed Oct 23 12:44:09 2024 -0400
+++ b/mercurial/interfaces/repository.py Tue Dec 10 21:37:14 2024 -0500
@@ -8,6 +8,7 @@
from __future__ import annotations
+import abc
import typing
from typing import (
@@ -1171,15 +1172,17 @@
"""
-class imanifestrevisionstored(imanifestrevisionbase):
+class imanifestrevisionstored(imanifestrevisionbase, Protocol):
"""Interface representing a manifest revision committed to storage."""
+ @abc.abstractmethod
def node(self) -> bytes:
"""The binary node for this manifest."""
parents: list[bytes]
"""List of binary nodes that are parents for this manifest revision."""
+ @abc.abstractmethod
def readdelta(self, shallow: bool = False):
"""Obtain the manifest data structure representing changes from parent.
@@ -1195,6 +1198,7 @@
The returned object conforms to the ``imanifestdict`` interface.
"""
+ @abc.abstractmethod
def read_any_fast_delta(
self,
valid_bases: Collection[int] | None = None,
@@ -1223,6 +1227,7 @@
The returned object conforms to the ``imanifestdict`` interface.
"""
+ @abc.abstractmethod
def read_delta_parents(self, *, shallow: bool = False, exact: bool = True):
"""return a diff from this revision against both parents.
@@ -1237,6 +1242,7 @@
The returned object conforms to the ``imanifestdict`` interface."""
+ @abc.abstractmethod
def read_delta_new_entries(self, *, shallow: bool = False):
"""Return a manifest containing just the entries that might be new to
the repository.
@@ -1252,12 +1258,14 @@
The returned object conforms to the ``imanifestdict`` interface."""
+ @abc.abstractmethod
def readfast(self, shallow: bool = False):
"""Calls either ``read()`` or ``readdelta()``.
The faster of the two options is called.
"""
+ @abc.abstractmethod
def find(self, key: bytes) -> tuple[bytes, bytes]:
"""Calls self.read().find(key)``.