feat: 迁移Windpicker-owo的Event系统重构\n\n- 引入新的BaseEvent和HandlerResult架构\n- 实现灵活的事件订阅与激活机制\n- 添加事件管理器单例模式\n- 支持事件缓存和权重排序\n- 统一事件处理接口
This commit is contained in:
109
src/plugin_system/base/base_event.py
Normal file
109
src/plugin_system/base/base_event.py
Normal file
@@ -0,0 +1,109 @@
|
||||
from typing import List, Dict, Any, Optional
|
||||
from src.common.logger import get_logger
|
||||
|
||||
logger = get_logger("base_event")
|
||||
|
||||
class HandlerResult:
|
||||
"""事件处理器执行结果
|
||||
|
||||
所有事件处理器必须返回此类的实例
|
||||
"""
|
||||
def __init__(self, success: bool, continue_process: bool, message: str = "", handler_name: str = ""):
|
||||
self.success = success
|
||||
self.continue_process = continue_process
|
||||
self.message = message
|
||||
self.handler_name = handler_name
|
||||
|
||||
def __repr__(self):
|
||||
return f"HandlerResult(success={self.success}, continue_process={self.continue_process}, message='{self.message}', handler_name='{self.handler_name}')"
|
||||
|
||||
class HandlerResultsCollection:
|
||||
"""HandlerResult集合,提供便捷的查询方法"""
|
||||
|
||||
def __init__(self, results: List[HandlerResult]):
|
||||
self.results = results
|
||||
|
||||
def all_continue_process(self) -> bool:
|
||||
"""检查是否所有handler的continue_process都为True"""
|
||||
return all(result.continue_process for result in self.results)
|
||||
|
||||
def get_all_results(self) -> List[HandlerResult]:
|
||||
"""获取所有HandlerResult"""
|
||||
return self.results
|
||||
|
||||
def get_failed_handlers(self) -> List[HandlerResult]:
|
||||
"""获取执行失败的handler结果"""
|
||||
return [result for result in self.results if not result.success]
|
||||
|
||||
def get_stopped_handlers(self) -> List[HandlerResult]:
|
||||
"""获取continue_process为False的handler结果"""
|
||||
return [result for result in self.results if not result.continue_process]
|
||||
|
||||
def get_handler_result(self, handler_name: str) -> Optional[HandlerResult]:
|
||||
"""获取指定handler的结果"""
|
||||
for result in self.results:
|
||||
if result.handler_name == handler_name:
|
||||
return result
|
||||
return None
|
||||
|
||||
def get_success_count(self) -> int:
|
||||
"""获取成功执行的handler数量"""
|
||||
return sum(1 for result in self.results if result.success)
|
||||
|
||||
def get_failure_count(self) -> int:
|
||||
"""获取执行失败的handler数量"""
|
||||
return sum(1 for result in self.results if not result.success)
|
||||
|
||||
def get_summary(self) -> Dict[str, Any]:
|
||||
"""获取执行摘要"""
|
||||
return {
|
||||
"total_handlers": len(self.results),
|
||||
"success_count": self.get_success_count(),
|
||||
"failure_count": self.get_failure_count(),
|
||||
"continue_process": self.all_continue_process(),
|
||||
"failed_handlers": [r.handler_name for r in self.get_failed_handlers()],
|
||||
"stopped_handlers": [r.handler_name for r in self.get_stopped_handlers()]
|
||||
}
|
||||
|
||||
class BaseEvent:
|
||||
def __init__(self, name: str):
|
||||
self.name = name
|
||||
self.enabled = True
|
||||
|
||||
from src.plugin_system.base.base_events_handler import BaseEventHandler
|
||||
self.subscribers: List["BaseEventHandler"] = [] # 订阅该事件的事件处理器列表
|
||||
|
||||
def __name__(self):
|
||||
return self.name
|
||||
|
||||
async def activate(self, params: dict) -> HandlerResultsCollection:
|
||||
"""激活事件,执行所有订阅的处理器
|
||||
|
||||
Args:
|
||||
params: 传递给处理器的参数
|
||||
|
||||
Returns:
|
||||
HandlerResultsCollection: 所有处理器的执行结果集合
|
||||
"""
|
||||
if not self.enabled:
|
||||
return HandlerResultsCollection([])
|
||||
|
||||
# 按权重从高到低排序订阅者
|
||||
# 使用直接属性访问,-1代表自动权重
|
||||
sorted_subscribers = sorted(self.subscribers, key=lambda h: h.weight if hasattr(h, 'weight') and h.weight != -1 else 0, reverse=True)
|
||||
|
||||
results = []
|
||||
for subscriber in sorted_subscribers:
|
||||
try:
|
||||
result = await subscriber.execute(params)
|
||||
if not result.handler_name:
|
||||
# 补充handler_name
|
||||
result.handler_name = subscriber.handler_name if hasattr(subscriber, 'handler_name') else subscriber.__class__.__name__
|
||||
results.append(result)
|
||||
except Exception as e:
|
||||
# 处理执行异常
|
||||
handler_name = subscriber.handler_name if hasattr(subscriber, 'handler_name') else subscriber.__class__.__name__
|
||||
logger.error(f"事件处理器 {handler_name} 执行失败: {e}")
|
||||
results.append(HandlerResult(False, True, str(e), handler_name))
|
||||
|
||||
return HandlerResultsCollection(results)
|
||||
@@ -1,8 +1,8 @@
|
||||
from abc import ABC, abstractmethod
|
||||
from typing import Tuple, Optional, Dict
|
||||
from typing import Tuple, Optional, Dict, List, Union
|
||||
|
||||
from src.common.logger import get_logger
|
||||
from .component_types import MaiMessages, EventType, EventHandlerInfo, ComponentType
|
||||
from .component_types import EventType, EventHandlerInfo, ComponentType
|
||||
|
||||
logger = get_logger("base_event_handler")
|
||||
|
||||
@@ -13,8 +13,6 @@ class BaseEventHandler(ABC):
|
||||
所有事件处理器都应该继承这个基类,提供事件处理的基本接口
|
||||
"""
|
||||
|
||||
event_type: EventType = EventType.UNKNOWN
|
||||
"""事件类型,默认为未知"""
|
||||
handler_name: str = ""
|
||||
"""处理器名称"""
|
||||
handler_description: str = ""
|
||||
@@ -23,6 +21,8 @@ class BaseEventHandler(ABC):
|
||||
"""处理器权重,越大权重越高"""
|
||||
intercept_message: bool = False
|
||||
"""是否拦截消息,默认为否"""
|
||||
init_subscribe: List[Union[EventType, str]] = [EventType.UNKNOWN]
|
||||
"""初始化时订阅的事件名称"""
|
||||
|
||||
def __init__(self):
|
||||
self.log_prefix = "[EventHandler]"
|
||||
@@ -30,18 +30,51 @@ class BaseEventHandler(ABC):
|
||||
"""对应插件名"""
|
||||
self.plugin_config: Optional[Dict] = None
|
||||
"""插件配置字典"""
|
||||
if self.event_type == EventType.UNKNOWN:
|
||||
self.subscribed_events = []
|
||||
"""订阅的事件列表"""
|
||||
if EventType.UNKNOWN in self.init_subscribe:
|
||||
raise NotImplementedError("事件处理器必须指定 event_type")
|
||||
|
||||
@abstractmethod
|
||||
async def execute(self, message: MaiMessages) -> Tuple[bool, bool, Optional[str]]:
|
||||
async def execute(self, kwargs: dict | None) -> Tuple[bool, bool, Optional[str]]:
|
||||
"""执行事件处理的抽象方法,子类必须实现
|
||||
|
||||
Args:
|
||||
kwargs (dict | None): 事件消息对象,当你注册的事件为ON_START和ON_STOP时message为None
|
||||
Returns:
|
||||
Tuple[bool, bool, Optional[str]]: (是否执行成功, 是否需要继续处理, 可选的返回消息)
|
||||
"""
|
||||
raise NotImplementedError("子类必须实现 execute 方法")
|
||||
|
||||
def subscribe(self, event_name: str) -> None:
|
||||
"""订阅一个事件
|
||||
|
||||
Args:
|
||||
event_name (str): 要订阅的事件名称
|
||||
"""
|
||||
from src.plugin_system.core.event_manager import event_manager
|
||||
|
||||
if not event_manager.subscribe_handler_to_event(self.handler_name, event_name):
|
||||
logger.error(f"事件处理器 {self.handler_name} 订阅事件 {event_name} 失败")
|
||||
return
|
||||
|
||||
logger.debug(f"{self.log_prefix} 订阅事件 {event_name}")
|
||||
self.subscribed_events.append(event_name)
|
||||
|
||||
def unsubscribe(self, event_name: str) -> None:
|
||||
"""取消订阅一个事件
|
||||
|
||||
Args:
|
||||
event_name (str): 要取消订阅的事件名称
|
||||
"""
|
||||
from src.plugin_system.core.event_manager import event_manager
|
||||
|
||||
if event_manager.unsubscribe_handler_from_event(self.handler_name, event_name):
|
||||
logger.debug(f"{self.log_prefix} 取消订阅事件 {event_name}")
|
||||
if event_name in self.subscribed_events:
|
||||
self.subscribed_events.remove(event_name)
|
||||
else:
|
||||
logger.warning(f"{self.log_prefix} 未订阅事件 {event_name},无法取消订阅")
|
||||
|
||||
@classmethod
|
||||
def get_handler_info(cls) -> "EventHandlerInfo":
|
||||
"""获取事件处理器的信息"""
|
||||
@@ -54,7 +87,6 @@ class BaseEventHandler(ABC):
|
||||
name=name,
|
||||
component_type=ComponentType.EVENT_HANDLER,
|
||||
description=getattr(cls, "handler_description", "events处理器"),
|
||||
event_type=cls.event_type,
|
||||
weight=cls.weight,
|
||||
intercept_message=cls.intercept_message,
|
||||
)
|
||||
|
||||
Reference in New Issue
Block a user