|
|
|
|
@ -1,44 +1,89 @@
|
|
|
|
|
# 钩子系统核心模块
|
|
|
|
|
# 该模块实现了一个轻量级的钩子(Hook)机制,支持注册回调函数、执行动作钩子(Action Hook)和过滤钩子(Filter Hook)
|
|
|
|
|
# 主要功能包括:管理钩子与回调函数的映射关系、按顺序执行钩子回调、处理回调执行过程中的异常并记录日志
|
|
|
|
|
# 适用于需要模块解耦、灵活扩展的场景,通过钩子机制实现不同组件间的间接交互
|
|
|
|
|
|
|
|
|
|
import logging
|
|
|
|
|
|
|
|
|
|
# 初始化日志记录器,用于记录钩子注册、执行过程中的调试信息和错误信息
|
|
|
|
|
logger = logging.getLogger(__name__)
|
|
|
|
|
|
|
|
|
|
# 私有字典,用于存储钩子名称与回调函数列表的映射关系
|
|
|
|
|
# 键为钩子名称(字符串),值为注册到该钩子的回调函数列表
|
|
|
|
|
_hooks = {}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def register(hook_name: str, callback: callable):
|
|
|
|
|
"""
|
|
|
|
|
注册一个钩子回调。
|
|
|
|
|
注册一个回调函数到指定的钩子上。
|
|
|
|
|
同一钩子可以注册多个回调函数,执行时将按注册顺序依次调用。
|
|
|
|
|
|
|
|
|
|
参数:
|
|
|
|
|
hook_name: 钩子名称,用于标识一组相关的回调函数
|
|
|
|
|
callback: 可调用对象(函数、方法等),将在钩子触发时执行
|
|
|
|
|
"""
|
|
|
|
|
# 如果钩子名称不在映射表中,初始化一个空列表用于存储回调
|
|
|
|
|
if hook_name not in _hooks:
|
|
|
|
|
_hooks[hook_name] = []
|
|
|
|
|
# 将回调函数添加到对应钩子的列表中
|
|
|
|
|
_hooks[hook_name].append(callback)
|
|
|
|
|
# 记录调试日志,说明已成功注册回调
|
|
|
|
|
logger.debug(f"Registered hook '{hook_name}' with callback '{callback.__name__}'")
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def run_action(hook_name: str, *args, **kwargs):
|
|
|
|
|
"""
|
|
|
|
|
执行一个 Action Hook。
|
|
|
|
|
它会按顺序执行所有注册到该钩子上的回调函数。
|
|
|
|
|
执行指定名称的动作钩子(Action Hook)。
|
|
|
|
|
动作钩子用于触发一系列操作,不关注返回值,按注册顺序依次执行所有回调函数。
|
|
|
|
|
|
|
|
|
|
参数:
|
|
|
|
|
hook_name: 要执行的钩子名称
|
|
|
|
|
*args: 传递给回调函数的位置参数
|
|
|
|
|
**kwargs: 传递给回调函数的关键字参数
|
|
|
|
|
"""
|
|
|
|
|
# 检查该钩子是否有注册的回调函数
|
|
|
|
|
if hook_name in _hooks:
|
|
|
|
|
logger.debug(f"Running action hook '{hook_name}'")
|
|
|
|
|
# 遍历执行该钩子下的所有回调函数
|
|
|
|
|
for callback in _hooks[hook_name]:
|
|
|
|
|
try:
|
|
|
|
|
# 调用回调函数并传递参数
|
|
|
|
|
callback(*args, **kwargs)
|
|
|
|
|
except Exception as e:
|
|
|
|
|
logger.error(f"Error running action hook '{hook_name}' callback '{callback.__name__}': {e}", exc_info=True)
|
|
|
|
|
# 捕获并记录回调执行过程中的异常,不中断后续回调
|
|
|
|
|
logger.error(
|
|
|
|
|
f"Error running action hook '{hook_name}' callback '{callback.__name__}': {e}",
|
|
|
|
|
exc_info=True # 记录完整的异常堆栈信息,便于调试
|
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def apply_filters(hook_name: str, value, *args, **kwargs):
|
|
|
|
|
"""
|
|
|
|
|
执行一个 Filter Hook。
|
|
|
|
|
它会把 value 依次传递给所有注册的回调函数进行处理。
|
|
|
|
|
执行指定名称的过滤钩子(Filter Hook)。
|
|
|
|
|
过滤钩子用于对某个值进行一系列处理,将值依次传递给所有回调函数,最终返回处理后的结果。
|
|
|
|
|
|
|
|
|
|
参数:
|
|
|
|
|
hook_name: 要执行的钩子名称
|
|
|
|
|
value: 初始值,将被回调函数依次处理
|
|
|
|
|
*args: 传递给回调函数的额外位置参数
|
|
|
|
|
**kwargs: 传递给回调函数的额外关键字参数
|
|
|
|
|
|
|
|
|
|
返回:
|
|
|
|
|
经过所有回调函数处理后的最终值
|
|
|
|
|
"""
|
|
|
|
|
# 检查该钩子是否有注册的回调函数
|
|
|
|
|
if hook_name in _hooks:
|
|
|
|
|
logger.debug(f"Applying filter hook '{hook_name}'")
|
|
|
|
|
# 遍历执行该钩子下的所有回调函数,依次处理值
|
|
|
|
|
for callback in _hooks[hook_name]:
|
|
|
|
|
try:
|
|
|
|
|
# 调用回调函数,传入当前值和其他参数,并用返回值更新当前值
|
|
|
|
|
value = callback(value, *args, **kwargs)
|
|
|
|
|
except Exception as e:
|
|
|
|
|
logger.error(f"Error applying filter hook '{hook_name}' callback '{callback.__name__}': {e}", exc_info=True)
|
|
|
|
|
return value
|
|
|
|
|
# 捕获并记录回调执行过程中的异常,不中断后续回调
|
|
|
|
|
logger.error(
|
|
|
|
|
f"Error applying filter hook '{hook_name}' callback '{callback.__name__}': {e}",
|
|
|
|
|
exc_info=True # 记录完整的异常堆栈信息,便于调试
|
|
|
|
|
)
|
|
|
|
|
# 返回最终处理后的值
|
|
|
|
|
return value
|