Skip to content

Commit 1fd8c65

Browse files
committed
Replace PluginTypeRepository and PluginRepository with KeyedCollection
1 parent c2144c1 commit 1fd8c65

File tree

5 files changed

+18
-93
lines changed

5 files changed

+18
-93
lines changed

betty/plugin/__init__.py

Lines changed: 2 additions & 34 deletions
Original file line numberDiff line numberDiff line change
@@ -8,8 +8,7 @@
88
from __future__ import annotations
99

1010
from functools import update_wrapper
11-
from importlib import metadata
12-
from typing import TYPE_CHECKING, Any, Generic, Self, final
11+
from typing import TYPE_CHECKING, Generic, Self, final
1312

1413
from typing_extensions import TypeVar, override
1514

@@ -21,7 +20,7 @@
2120

2221
if TYPE_CHECKING:
2322
import builtins
24-
from collections.abc import Iterable, Iterator, Mapping
23+
from collections.abc import Iterable
2524

2625
from betty.locale.localizable import (
2726
CountableLocalizable,
@@ -171,34 +170,3 @@ def plugin(cls) -> _PluginDefinitionCoT:
171170
raise NotImplementedError(
172171
f"{fully_qualified_name(cls)} was not decorated with a {fully_qualified_name(PluginDefinition)} subclass."
173172
)
174-
175-
176-
_PluginT = TypeVar("_PluginT", bound=Plugin, default=Plugin)
177-
178-
179-
@final
180-
class PluginTypeRepository:
181-
"""
182-
A repository of available plugin types.
183-
"""
184-
185-
def __init__(self):
186-
self._plugin_types: Mapping[MachineName, type[PluginDefinition]] | None = None
187-
188-
def _get_plugin_types(self) -> Mapping[MachineName, type[PluginDefinition]]:
189-
if self._plugin_types is None:
190-
self._plugin_types = {
191-
plugin.type().id: plugin
192-
for entry_point in metadata.entry_points(group="betty.plugin")
193-
if (plugin := entry_point.load())
194-
}
195-
return self._plugin_types
196-
197-
def __contains__(self, value: Any) -> bool:
198-
return value in self._get_plugin_types()
199-
200-
def __getitem__(self, plugin_type_id: MachineName, /) -> type[PluginDefinition]:
201-
return self._get_plugin_types()[plugin_type_id]
202-
203-
def __iter__(self) -> Iterator[type[PluginDefinition]]:
204-
return iter(self._get_plugin_types().values())

betty/plugin/manager/__init__.py

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -13,8 +13,9 @@
1313
from betty.typing import threadsafe
1414

1515
if TYPE_CHECKING:
16+
from betty.collections import KeyedCollection
1617
from betty.machine_name import MachineName
17-
from betty.plugin.repository import PluginRepository
18+
from betty.plugin.resolve import ResolvableId
1819

1920
_PluginDefinitionT = TypeVar(
2021
"_PluginDefinitionT", bound=PluginDefinition, default=PluginDefinition
@@ -30,7 +31,9 @@ class PluginManager(ABC):
3031
@abstractmethod
3132
async def plugins(
3233
self, plugin_type: type[_PluginDefinitionT] | MachineName, /
33-
) -> PluginRepository[_PluginDefinitionT]:
34+
) -> KeyedCollection[
35+
MachineName, ResolvableId[_PluginDefinitionT], _PluginDefinitionT
36+
]:
3437
"""
3538
Get the available plugins for the given type.
3639
"""

betty/plugin/manager/service.py

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -18,8 +18,10 @@
1818
if TYPE_CHECKING:
1919
from collections.abc import MutableMapping
2020

21+
from betty.collections import KeyedCollection
2122
from betty.machine_name import MachineName
2223
from betty.plugin.repository import PluginRepository
24+
from betty.plugin.resolve import ResolvableId
2325
from betty.service.level import ServiceLevel
2426

2527

@@ -51,7 +53,9 @@ def types(self) -> plugin.PluginTypeRepository:
5153
@override
5254
async def plugins(
5355
self, plugin_type: type[_PluginDefinitionT] | MachineName, /
54-
) -> PluginRepository[_PluginDefinitionT]:
56+
) -> KeyedCollection[
57+
MachineName, ResolvableId[_PluginDefinitionT], _PluginDefinitionT
58+
]:
5559
if isinstance(plugin_type, str):
5660
plugin_type = cast(type[_PluginDefinitionT], self.types[plugin_type])
5761
repository: PluginRepository[_PluginDefinitionT] | None

betty/plugin/repository/__init__.py

Lines changed: 5 additions & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -4,53 +4,22 @@
44

55
from __future__ import annotations
66

7-
from abc import ABC, abstractmethod
8-
from typing import TYPE_CHECKING, Generic
7+
from abc import ABC
8+
from typing import Generic
99

1010
from typing_extensions import TypeVar
1111

1212
from betty.plugin import PluginDefinition
1313

14-
if TYPE_CHECKING:
15-
import builtins
16-
from collections.abc import Iterator
17-
18-
from betty.machine_name import MachineName
19-
2014
_PluginDefinitionT = TypeVar(
2115
"_PluginDefinitionT", bound=PluginDefinition, default=PluginDefinition
2216
)
2317

2418

19+
# @todo Remove this
20+
# @todo
21+
# @todo
2522
class PluginRepository(ABC, Generic[_PluginDefinitionT]):
2623
"""
2724
Access discovered plugins.
2825
"""
29-
30-
def __init__(self, plugin_type: builtins.type[_PluginDefinitionT]):
31-
self._type = plugin_type
32-
33-
@property
34-
def type(self) -> builtins.type[_PluginDefinitionT]:
35-
"""
36-
The plugin type contained by this repository.
37-
"""
38-
return self._type
39-
40-
@abstractmethod
41-
def get(self, plugin_id: MachineName, /) -> _PluginDefinitionT:
42-
"""
43-
Get a single plugin by its ID.
44-
45-
:raises PluginUnavailable: if no plugin can be found for the given ID.
46-
"""
47-
48-
def __len__(self) -> int:
49-
return len(list(self.__iter__()))
50-
51-
@abstractmethod
52-
def __iter__(self) -> Iterator[_PluginDefinitionT]:
53-
pass
54-
55-
def __getitem__(self, plugin_id: MachineName) -> _PluginDefinitionT:
56-
return self.get(plugin_id)

betty/tests/plugin/test___init__.py

Lines changed: 1 addition & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,7 @@
11
from __future__ import annotations
22

33
from betty.locale.localize import DEFAULT_LOCALIZER
4-
from betty.model import EntityDefinition
5-
from betty.plugin import (
6-
PluginDefinition,
7-
PluginTypeDefinition,
8-
PluginTypeRepository,
9-
)
4+
from betty.plugin import PluginDefinition, PluginTypeDefinition
105
from betty.plugin.dependent import DependentPluginDefinition
116
from betty.plugin.ordered import OrderedPluginDefinition
127
from betty.service.level import universe
@@ -136,17 +131,3 @@ class _PluginDefinition(PluginDefinition[DummyPlugin]):
136131
actual = sut.reference_label_with_type.localize(DEFAULT_LOCALIZER)
137132
assert id in actual
138133
assert plugin_type_label in actual
139-
140-
141-
class TestPluginTypeRepository:
142-
def test___contains__(self) -> None:
143-
sut = PluginTypeRepository()
144-
assert "entity" in sut
145-
146-
def test___getitem__(self) -> None:
147-
sut = PluginTypeRepository()
148-
assert sut["entity"].type().id == "entity"
149-
150-
def test___iter__(self) -> None:
151-
sut = PluginTypeRepository()
152-
assert EntityDefinition in list(iter(sut))

0 commit comments

Comments
 (0)