eed418477f
Previously, all templates were named with the .html extension, which caused problems for editors to recognize the Jinja2 syntax used in them. In this commit, all templates have been renamed to use the .jinja2 extension to better reflect their use of Jinja2 and to improve editor recognition. |
||
---|---|---|
.. | ||
account | ||
admin | ||
app | ||
genshin | ||
group | ||
jobs | ||
system | ||
tools | ||
__init__.py | ||
README.md |
plugins 目录
说明
该目录仅限处理交互层和业务层数据交换的任务
如有任何核心接口,请转到 core
目录添加
如有任何API请求接口,请转到 models
目录添加
新版插件 Plugin 的写法
关于路径
插件应该写在 plugins
文件夹下,可以是一个包或者是一个文件,但文件名、文件夹名中不能包含_
字符
关于类
-
除了要使用
ConversationHandler
的插件外,都要继承core.plugin.Plugin
from core.plugin import Plugin class TestPlugin(Plugin): pass
-
针对要用
ConversationHandler
的插件,要继承core.plugin.Plugin.Conversation
from core.plugin import Plugin class TestConversationPlugin(Plugin.Conversation): pass
-
关于初始化方法以及依赖注入
初始化类, 可写在
__init__
和__async_init__
中, 其中__async_init__
应该是异步方法, 用于执行初始化时需要的异步操作. 这两个方法的执行顺序是__init__
在前,__async_init__
在后若需要注入依赖, 直接在插件类的
__init__
方法中,提供相应的参数以及标注标注即可, 例如我需要注入一个MySQL
from service.mysql import MySQL from core.plugin import Plugin class TestPlugin(Plugin): def __init__(self, mysql: MySQL): self.mysql = mysql async def __async_init__(self): """do something"""
关于 handler
给函数加上 core.plugin.handler
这一装饰器即可将这个函数注册为handler
非 ConversationHandler
的 handler
-
直接使用
core.plugin.handler
装饰器第一个参数是
handler
的种类,后续参数为该handler
除callback
参数外的其余参数from core.plugin import Plugin, handler from telegram import Update from telegram.ext import CommandHandler, CallbackContext class TestPlugin(Plugin): @handler(CommandHandler, command='start', block=False) async def start(self, update: Update, context: CallbackContext): await update.effective_chat.send_message('hello world!')
比如上面代码中的
command='start', block=False
就是CommandHandler
的参数 -
使用
core.plugin.handler
的子装饰器这种方式比第一种简单, 不需要声明
handler
的类型from core.plugin import Plugin, handler from telegram import Update from telegram.ext import CallbackContext class TestPlugin(Plugin): @handler.command(command='start', block=False) async def start(self, update: Update, context: CallbackContext): await update.effective_chat.send_message('hello world!')
对于 ConversationHandler
由于 ConversationHandler
比较特殊,所以一个 Plugin 类中只能存在一个 ConversationHandler
conversation.entry_point
、conversation.state
和 conversation.fallback
装饰器分别对应
ConversationHandler
的 entry_points
、stats
和 fallbacks
参数
from telegram import Update
from telegram.ext import CallbackContext, filters
from core.plugin import Plugin, conversation, handler
STATE_A, STATE_B, STATE_C = range(3)
class TestConversation(Plugin.Conversation, allow_reentry=True, block=False):
@conversation.entry_point # 标注这个handler是ConversationHandler的一个entry_point
@handler.command(command='entry')
async def entry_point(self, update: Update, context: CallbackContext):
"""do something"""
@conversation.state(state=STATE_A)
@handler.message(filters=filters.TEXT)
async def state(self, update: Update, context: CallbackContext):
"""do something"""
@conversation.fallback
@handler.message(filters=filters.TEXT)
async def fallback(self, update: Update, context: CallbackContext):
"""do something"""
@handler.inline_query() # 你可以在此 Plugin 下定义其它类型的 handler
async def inline_query(self, update: Update, context: CallbackContext):
"""do something"""
对于 Job
- 依然需要继承
core.plugin.Plugin
- 直接使用
core.plugin.job
装饰器 参数都与官方JobQueue
类对应
from core.plugin import Plugin, job
class TestJob(Plugin):
@job.run_repeating(interval=datetime.timedelta(hours=2), name="TestJob")
async def refresh(self, _: CallbackContext):
logger.info("TestJob")
注意
被注册到 handler
的函数需要添加 error_callable
修饰器作为错误统一处理
被注册到 handler
的函数必须使用 @restricts()
修饰器 预防洪水攻击 但 ConversationHandler
外只需要注册入口函数使用
如果引用服务,参数需要声明需要引用服务的类型并设置默认传入为 None
必要的函数必须捕获异常后通知用户或者直接抛出异常
部分修饰器为带参修饰器,必须带括号,否则会出现调用错误