From 13ef344c2d419059600607747a7bc640af97fd29 Mon Sep 17 00:00:00 2001 From: RF-Tar-Railt Date: Mon, 2 Dec 2024 15:34:24 +0800 Subject: [PATCH] :sparkles: Lifespan's requirement --- arclet/entari/builtins/echo.py | 6 +++++- arclet/entari/core.py | 5 +++++ arclet/entari/plugin/__init__.py | 9 +++++++++ arclet/entari/plugin/model.py | 17 +++++++++++++++-- arclet/entari/plugin/service.py | 9 +++++---- 5 files changed, 39 insertions(+), 7 deletions(-) diff --git a/arclet/entari/builtins/echo.py b/arclet/entari/builtins/echo.py index d7e5205..aeed38e 100644 --- a/arclet/entari/builtins/echo.py +++ b/arclet/entari/builtins/echo.py @@ -3,7 +3,11 @@ from arclet.entari import MessageChain, Session, command, metadata from arclet.entari.command import Match -metadata(__file__) +metadata( + "echo", + author=["RF-Tar-Railt "], + description="Echo the content", +) cmd = command.mount(Alconna("echo", Args["content?", AllParam], meta=CommandMeta(compact=True))) diff --git a/arclet/entari/core.py b/arclet/entari/core.py index 8a3c6be..c61d90f 100644 --- a/arclet/entari/core.py +++ b/arclet/entari/core.py @@ -5,6 +5,7 @@ import os from arclet.letoderea import BaseAuxiliary, Contexts, Param, Provider, ProviderFactory, es, global_providers +from creart import it from launart import Launart from loguru import logger from satori import LoginStatus @@ -125,3 +126,7 @@ async def account_hook(self, account: Account, state: LoginStatus): await asyncio.gather(*_connected, return_exceptions=True) elif state == LoginStatus.DISCONNECT: await asyncio.gather(*_disconnected, return_exceptions=True) + + @classmethod + def current(cls): + return it(Launart).get_component(cls) diff --git a/arclet/entari/plugin/__init__.py b/arclet/entari/plugin/__init__.py index 0bb1932..f9fd6f1 100644 --- a/arclet/entari/plugin/__init__.py +++ b/arclet/entari/plugin/__init__.py @@ -99,6 +99,15 @@ def metadata(data: PluginMetadata): plugin._metadata = data # type: ignore +def requirements(*reqs: str): + if not (plugin := _current_plugin.get(None)): + raise LookupError("no plugin context found") + plugin.inject(*reqs) + + +inject = requirements + + def find_plugin(name: str) -> Plugin | None: return plugin_service.plugins.get(name) diff --git a/arclet/entari/plugin/model.py b/arclet/entari/plugin/model.py index d398766..dac0ad3 100644 --- a/arclet/entari/plugin/model.py +++ b/arclet/entari/plugin/model.py @@ -128,6 +128,7 @@ class Plugin: dispatchers: dict[str, PluginDispatcher] = field(default_factory=dict) subplugins: set[str] = field(default_factory=set) config: dict[str, Any] = field(default_factory=dict) + _requires: list[str] = field(default_factory=list) _metadata: PluginMetadata | None = None _is_disposed: bool = False @@ -171,6 +172,15 @@ def current() -> Plugin: def metadata(self) -> PluginMetadata | None: return self._metadata + def inject(self, *requires: str): + plugin = self + while plugin.id in plugin_service._subplugined: + plugin = plugin_service.plugins[plugin_service._subplugined[plugin.id]] + plugin._requires.extend(requires) + if plugin._lifecycle: + plugin._lifecycle.requires.update(requires) + return self + def __post_init__(self): plugin_service.plugins[self.id] = self if self.id not in plugin_service._keep_values: @@ -178,7 +188,7 @@ def __post_init__(self): if self.id not in plugin_service._referents: plugin_service._referents[self.id] = set() if self.id not in plugin_service._subplugined: - self._lifecycle = PluginLifecycleService(self.id) + self._lifecycle = PluginLifecycleService(self.id, set(self._requires)) if plugin_service.status.blocking and (self._preparing or self._running or self._cleanup): it(Launart).add_component(self._lifecycle) finalize(self, self.dispose) @@ -278,7 +288,10 @@ class KeepingVariable: def __init__(self, obj: T, dispose: Callable[[T], None] | None = None): self.obj = obj self._dispose = dispose - setattr(self.obj, "__keeping__", True) + try: + setattr(self.obj, "__keeping__", True) + except AttributeError: + pass def dispose(self): if hasattr(self.obj, "dispose"): diff --git a/arclet/entari/plugin/service.py b/arclet/entari/plugin/service.py index 8b6b944..ee16413 100644 --- a/arclet/entari/plugin/service.py +++ b/arclet/entari/plugin/service.py @@ -16,15 +16,16 @@ def id(self) -> str: @property def required(self) -> set[str]: - return {"arclet.entari.plugin.manager"} + return {"entari.plugin.manager", *self.requires} @property def stages(self) -> set[Phase]: return {"preparing", "cleanup", "blocking"} - def __init__(self, plugin_id: str): + def __init__(self, plugin_id: str, requires: set[str]): super().__init__() self.plugin_id = plugin_id + self.requires = requires @property def available(self) -> bool: @@ -77,7 +78,7 @@ async def launch(self, manager: Launart): class PluginManagerService(Service): - id = "arclet.entari.plugin.manager" + id = "entari.plugin.manager" plugins: dict[str, "Plugin"] _keep_values: dict[str, dict[str, "KeepingVariable"]] @@ -95,7 +96,7 @@ def __init__(self): @property def required(self) -> set[str]: - return set() + return {"entari.service"} @property def stages(self) -> set[Phase]: