Merge branch 'main' of https://gitea.functen.cn/shihao/WechatHookBot
This commit is contained in:
@@ -1,5 +1,12 @@
|
||||
"""
|
||||
消息处理装饰器模块
|
||||
|
||||
提供插件消息处理和定时任务的装饰器
|
||||
使用工厂模式消除重复代码
|
||||
"""
|
||||
|
||||
from functools import wraps
|
||||
from typing import Callable, Union
|
||||
from typing import Callable, Dict, Union
|
||||
|
||||
from apscheduler.schedulers.asyncio import AsyncIOScheduler
|
||||
from apscheduler.triggers.cron import CronTrigger
|
||||
@@ -8,15 +15,16 @@ from apscheduler.triggers.interval import IntervalTrigger
|
||||
scheduler = AsyncIOScheduler()
|
||||
|
||||
|
||||
# ==================== 定时任务装饰器 ====================
|
||||
|
||||
def schedule(
|
||||
trigger: Union[str, CronTrigger, IntervalTrigger],
|
||||
**trigger_args
|
||||
) -> Callable:
|
||||
"""
|
||||
定时任务装饰器
|
||||
|
||||
例子:
|
||||
|
||||
例子:
|
||||
- @schedule('interval', seconds=30)
|
||||
- @schedule('cron', hour=8, minute=30, second=30)
|
||||
- @schedule('date', run_date='2024-01-01 00:00:00')
|
||||
@@ -44,23 +52,16 @@ def add_job_safe(scheduler: AsyncIOScheduler, job_id: str, func: Callable, bot,
|
||||
"""添加函数到定时任务中,如果存在则先删除现有的任务"""
|
||||
try:
|
||||
scheduler.remove_job(job_id)
|
||||
except:
|
||||
except Exception:
|
||||
pass
|
||||
|
||||
# 读取调度器配置
|
||||
|
||||
# 使用统一配置管理器读取调度器配置
|
||||
try:
|
||||
import tomllib
|
||||
from pathlib import Path
|
||||
config_path = Path("main_config.toml")
|
||||
if config_path.exists():
|
||||
with open(config_path, "rb") as f:
|
||||
config = tomllib.load(f)
|
||||
scheduler_config = config.get("Scheduler", {})
|
||||
else:
|
||||
scheduler_config = {}
|
||||
except:
|
||||
from utils.config_manager import get_scheduler_config
|
||||
scheduler_config = get_scheduler_config()
|
||||
except Exception:
|
||||
scheduler_config = {}
|
||||
|
||||
|
||||
# 应用调度器配置
|
||||
job_kwargs = {
|
||||
"coalesce": scheduler_config.get("coalesce", True),
|
||||
@@ -68,7 +69,7 @@ def add_job_safe(scheduler: AsyncIOScheduler, job_id: str, func: Callable, bot,
|
||||
"misfire_grace_time": scheduler_config.get("misfire_grace_time", 30)
|
||||
}
|
||||
job_kwargs.update(trigger_args)
|
||||
|
||||
|
||||
scheduler.add_job(func, trigger, args=[bot], id=job_id, **job_kwargs)
|
||||
|
||||
|
||||
@@ -76,182 +77,106 @@ def remove_job_safe(scheduler: AsyncIOScheduler, job_id: str):
|
||||
"""从定时任务中移除任务"""
|
||||
try:
|
||||
scheduler.remove_job(job_id)
|
||||
except:
|
||||
except Exception:
|
||||
pass
|
||||
|
||||
|
||||
def on_text_message(priority=50):
|
||||
"""文本消息装饰器"""
|
||||
# ==================== 消息装饰器工厂 ====================
|
||||
|
||||
def decorator(func):
|
||||
if callable(priority): # 无参数调用时
|
||||
f = priority
|
||||
setattr(f, '_event_type', 'text_message')
|
||||
setattr(f, '_priority', 50)
|
||||
return f
|
||||
# 有参数调用时
|
||||
setattr(func, '_event_type', 'text_message')
|
||||
setattr(func, '_priority', min(max(priority, 0), 99))
|
||||
return func
|
||||
def _create_message_decorator(event_type: str, description: str):
|
||||
"""
|
||||
消息装饰器工厂函数
|
||||
|
||||
return decorator if not callable(priority) else decorator(priority)
|
||||
生成支持两种调用方式的装饰器:
|
||||
- @on_xxx_message (无参数,使用默认优先级50)
|
||||
- @on_xxx_message(priority=80) (有参数,自定义优先级)
|
||||
|
||||
Args:
|
||||
event_type: 事件类型字符串,如 'text_message'
|
||||
description: 装饰器描述,用于生成文档字符串
|
||||
|
||||
def on_image_message(priority=50):
|
||||
"""图片消息装饰器"""
|
||||
Returns:
|
||||
装饰器函数
|
||||
"""
|
||||
def decorator_factory(priority=50):
|
||||
def decorator(func):
|
||||
# 处理无参数调用: @on_xxx_message 时 priority 实际是被装饰的函数
|
||||
if callable(priority):
|
||||
target_func = priority
|
||||
actual_priority = 50
|
||||
else:
|
||||
target_func = func
|
||||
actual_priority = min(max(priority, 0), 99)
|
||||
|
||||
def decorator(func):
|
||||
setattr(target_func, '_event_type', event_type)
|
||||
setattr(target_func, '_priority', actual_priority)
|
||||
return target_func
|
||||
|
||||
# 判断调用方式
|
||||
if callable(priority):
|
||||
f = priority
|
||||
setattr(f, '_event_type', 'image_message')
|
||||
setattr(f, '_priority', 50)
|
||||
return f
|
||||
setattr(func, '_event_type', 'image_message')
|
||||
setattr(func, '_priority', min(max(priority, 0), 99))
|
||||
return func
|
||||
return decorator(priority)
|
||||
return decorator
|
||||
|
||||
return decorator if not callable(priority) else decorator(priority)
|
||||
decorator_factory.__doc__ = f"{description}装饰器"
|
||||
decorator_factory.__name__ = f"on_{event_type}"
|
||||
return decorator_factory
|
||||
|
||||
|
||||
def on_voice_message(priority=50):
|
||||
"""语音消息装饰器"""
|
||||
# ==================== 消息类型定义 ====================
|
||||
|
||||
def decorator(func):
|
||||
if callable(priority):
|
||||
f = priority
|
||||
setattr(f, '_event_type', 'voice_message')
|
||||
setattr(f, '_priority', 50)
|
||||
return f
|
||||
setattr(func, '_event_type', 'voice_message')
|
||||
setattr(func, '_priority', min(max(priority, 0), 99))
|
||||
return func
|
||||
|
||||
return decorator if not callable(priority) else decorator(priority)
|
||||
# 事件类型 -> 中文描述 映射表
|
||||
MESSAGE_DECORATOR_TYPES: Dict[str, str] = {
|
||||
'text_message': '文本消息',
|
||||
'image_message': '图片消息',
|
||||
'voice_message': '语音消息',
|
||||
'video_message': '视频消息',
|
||||
'emoji_message': '表情消息',
|
||||
'file_message': '文件消息',
|
||||
'quote_message': '引用消息',
|
||||
'pat_message': '拍一拍',
|
||||
'at_message': '@消息',
|
||||
'system_message': '系统消息',
|
||||
'other_message': '其他消息',
|
||||
}
|
||||
|
||||
|
||||
def on_emoji_message(priority=50):
|
||||
"""表情消息装饰器"""
|
||||
# ==================== 生成所有消息装饰器 ====================
|
||||
|
||||
def decorator(func):
|
||||
if callable(priority):
|
||||
f = priority
|
||||
setattr(f, '_event_type', 'emoji_message')
|
||||
setattr(f, '_priority', 50)
|
||||
return f
|
||||
setattr(func, '_event_type', 'emoji_message')
|
||||
setattr(func, '_priority', min(max(priority, 0), 99))
|
||||
return func
|
||||
|
||||
return decorator if not callable(priority) else decorator(priority)
|
||||
# 使用工厂函数生成装饰器
|
||||
on_text_message = _create_message_decorator('text_message', '文本消息')
|
||||
on_image_message = _create_message_decorator('image_message', '图片消息')
|
||||
on_voice_message = _create_message_decorator('voice_message', '语音消息')
|
||||
on_video_message = _create_message_decorator('video_message', '视频消息')
|
||||
on_emoji_message = _create_message_decorator('emoji_message', '表情消息')
|
||||
on_file_message = _create_message_decorator('file_message', '文件消息')
|
||||
on_quote_message = _create_message_decorator('quote_message', '引用消息')
|
||||
on_pat_message = _create_message_decorator('pat_message', '拍一拍')
|
||||
on_at_message = _create_message_decorator('at_message', '@消息')
|
||||
on_system_message = _create_message_decorator('system_message', '系统消息')
|
||||
on_other_message = _create_message_decorator('other_message', '其他消息')
|
||||
|
||||
|
||||
def on_file_message(priority=50):
|
||||
"""文件消息装饰器"""
|
||||
# ==================== 导出列表 ====================
|
||||
|
||||
def decorator(func):
|
||||
if callable(priority):
|
||||
f = priority
|
||||
setattr(f, '_event_type', 'file_message')
|
||||
setattr(f, '_priority', 50)
|
||||
return f
|
||||
setattr(func, '_event_type', 'file_message')
|
||||
setattr(func, '_priority', min(max(priority, 0), 99))
|
||||
return func
|
||||
|
||||
return decorator if not callable(priority) else decorator(priority)
|
||||
|
||||
|
||||
def on_quote_message(priority=50):
|
||||
"""引用消息装饰器"""
|
||||
|
||||
def decorator(func):
|
||||
if callable(priority):
|
||||
f = priority
|
||||
setattr(f, '_event_type', 'quote_message')
|
||||
setattr(f, '_priority', 50)
|
||||
return f
|
||||
setattr(func, '_event_type', 'quote_message')
|
||||
setattr(func, '_priority', min(max(priority, 0), 99))
|
||||
return func
|
||||
|
||||
return decorator if not callable(priority) else decorator(priority)
|
||||
|
||||
|
||||
def on_video_message(priority=50):
|
||||
"""视频消息装饰器"""
|
||||
|
||||
def decorator(func):
|
||||
if callable(priority):
|
||||
f = priority
|
||||
setattr(f, '_event_type', 'video_message')
|
||||
setattr(f, '_priority', 50)
|
||||
return f
|
||||
setattr(func, '_event_type', 'video_message')
|
||||
setattr(func, '_priority', min(max(priority, 0), 99))
|
||||
return func
|
||||
|
||||
return decorator if not callable(priority) else decorator(priority)
|
||||
|
||||
|
||||
def on_pat_message(priority=50):
|
||||
"""拍一拍消息装饰器"""
|
||||
|
||||
def decorator(func):
|
||||
if callable(priority):
|
||||
f = priority
|
||||
setattr(f, '_event_type', 'pat_message')
|
||||
setattr(f, '_priority', 50)
|
||||
return f
|
||||
setattr(func, '_event_type', 'pat_message')
|
||||
setattr(func, '_priority', min(max(priority, 0), 99))
|
||||
return func
|
||||
|
||||
return decorator if not callable(priority) else decorator(priority)
|
||||
|
||||
|
||||
def on_at_message(priority=50):
|
||||
"""被@消息装饰器"""
|
||||
|
||||
def decorator(func):
|
||||
if callable(priority):
|
||||
f = priority
|
||||
setattr(f, '_event_type', 'at_message')
|
||||
setattr(f, '_priority', 50)
|
||||
return f
|
||||
setattr(func, '_event_type', 'at_message')
|
||||
setattr(func, '_priority', min(max(priority, 0), 99))
|
||||
return func
|
||||
|
||||
return decorator if not callable(priority) else decorator(priority)
|
||||
|
||||
|
||||
def on_system_message(priority=50):
|
||||
"""其他消息装饰器"""
|
||||
|
||||
def decorator(func):
|
||||
if callable(priority):
|
||||
f = priority
|
||||
setattr(f, '_event_type', 'system_message')
|
||||
setattr(f, '_priority', 50)
|
||||
return f
|
||||
setattr(func, '_event_type', 'other_message')
|
||||
setattr(func, '_priority', min(max(priority, 0), 99))
|
||||
return func
|
||||
|
||||
return decorator if not callable(priority) else decorator(priority)
|
||||
|
||||
|
||||
def on_other_message(priority=50):
|
||||
"""其他消息装饰器"""
|
||||
|
||||
def decorator(func):
|
||||
if callable(priority):
|
||||
f = priority
|
||||
setattr(f, '_event_type', 'other_message')
|
||||
setattr(f, '_priority', 50)
|
||||
return f
|
||||
setattr(func, '_event_type', 'other_message')
|
||||
setattr(func, '_priority', min(max(priority, 0), 99))
|
||||
return func
|
||||
|
||||
return decorator if not callable(priority) else decorator(priority)
|
||||
__all__ = [
|
||||
# 定时任务
|
||||
'scheduler',
|
||||
'schedule',
|
||||
'add_job_safe',
|
||||
'remove_job_safe',
|
||||
# 消息装饰器
|
||||
'on_text_message',
|
||||
'on_image_message',
|
||||
'on_voice_message',
|
||||
'on_video_message',
|
||||
'on_emoji_message',
|
||||
'on_file_message',
|
||||
'on_quote_message',
|
||||
'on_pat_message',
|
||||
'on_at_message',
|
||||
'on_system_message',
|
||||
'on_other_message',
|
||||
# 工具
|
||||
'MESSAGE_DECORATOR_TYPES',
|
||||
'_create_message_decorator',
|
||||
]
|
||||
|
||||
Reference in New Issue
Block a user