""" 插件管理插件 提供插件的热重载、启用、禁用等管理功能 """ import tomllib from pathlib import Path from loguru import logger from utils.plugin_base import PluginBase from utils.decorators import on_text_message from utils.plugin_manager import PluginManager class ManagePlugin(PluginBase): """插件管理插件""" # 插件元数据 description = "插件管理,支持热重载、启用、禁用" author = "ShiHao" version = "1.0.0" def __init__(self): super().__init__() self.config = None self.admins = [] async def async_init(self): """插件异步初始化""" # 从主配置文件读取管理员列表 with open("main_config.toml", "rb") as f: main_config = tomllib.load(f) self.admins = main_config.get("Bot", {}).get("admins", []) logger.info(f"插件管理插件已加载,管理员: {self.admins}") @on_text_message() async def handle_command(self, bot, message: dict): """处理管理命令""" content = message.get("Content", "").strip() from_wxid = message.get("FromWxid", "") sender_wxid = message.get("SenderWxid", "") logger.debug(f"ManagePlugin: content={content}, from={from_wxid}, sender={sender_wxid}, admins={self.admins}") # 检查权限 if not self.admins or sender_wxid not in self.admins: return # 插件列表 if content == "/插件列表" or content == "/plugins": await self._list_plugins(bot, from_wxid) # 重载插件 elif content.startswith("/重载插件 ") or content.startswith("/reload "): plugin_name = content.split(maxsplit=1)[1].strip() await self._reload_plugin(bot, from_wxid, plugin_name) # 启用插件 elif content.startswith("/启用插件 ") or content.startswith("/enable "): plugin_name = content.split(maxsplit=1)[1].strip() await self._enable_plugin(bot, from_wxid, plugin_name) # 禁用插件 elif content.startswith("/禁用插件 ") or content.startswith("/disable "): plugin_name = content.split(maxsplit=1)[1].strip() await self._disable_plugin(bot, from_wxid, plugin_name) async def _list_plugins(self, bot, to_wxid: str): """列出所有插件""" try: pm = PluginManager() plugins = pm.get_plugin_info() if not plugins: await bot.send_text(to_wxid, "暂无插件") return lines = ["📦 插件列表\n"] for plugin in plugins: status = "✅ 已启用" if plugin.get("enabled", False) else "❌ 已禁用" lines.append( f"{status} {plugin.get('name', 'Unknown')}\n" f" 版本: {plugin.get('version', 'Unknown')}\n" f" 作者: {plugin.get('author', 'Unknown')}\n" ) response = "\n".join(lines) await bot.send_text(to_wxid, response) logger.info(f"已发送插件列表给 {to_wxid}") except Exception as e: logger.error(f"列出插件失败: {e}") await bot.send_text(to_wxid, f"❌ 获取插件列表失败: {e}") async def _reload_plugin(self, bot, to_wxid: str, plugin_name: str): """重载插件""" pm = PluginManager() if plugin_name == "ManagePlugin": await bot.send_text(to_wxid, "❌ ManagePlugin 不能被重载") return success = await pm.reload_plugin(plugin_name) if success: await bot.send_text(to_wxid, f"✅ 插件 {plugin_name} 重载成功") logger.info(f"插件 {plugin_name} 已被重载") else: await bot.send_text(to_wxid, f"❌ 插件 {plugin_name} 重载失败") async def _enable_plugin(self, bot, to_wxid: str, plugin_name: str): """启用插件""" pm = PluginManager() # 检查插件是否存在 plugin_info = pm.get_plugin_info(plugin_name) if not plugin_info: await bot.send_text(to_wxid, f"❌ 插件 {plugin_name} 不存在") return # 检查是否已启用 if plugin_info["enabled"]: await bot.send_text(to_wxid, f"ℹ️ 插件 {plugin_name} 已经是启用状态") return # 加载插件 success = await pm.load_plugin(plugin_name) if success: await bot.send_text(to_wxid, f"✅ 插件 {plugin_name} 已启用") logger.info(f"插件 {plugin_name} 已被启用") else: await bot.send_text(to_wxid, f"❌ 插件 {plugin_name} 启用失败") async def _disable_plugin(self, bot, to_wxid: str, plugin_name: str): """禁用插件""" pm = PluginManager() if plugin_name == "ManagePlugin": await bot.send_text(to_wxid, "❌ ManagePlugin 不能被禁用") return # 检查插件是否存在 plugin_info = pm.get_plugin_info(plugin_name) if not plugin_info: await bot.send_text(to_wxid, f"❌ 插件 {plugin_name} 不存在") return # 检查是否已禁用 if not plugin_info["enabled"]: await bot.send_text(to_wxid, f"ℹ️ 插件 {plugin_name} 已经是禁用状态") return # 卸载插件 success = await pm.unload_plugin(plugin_name) if success: await bot.send_text(to_wxid, f"✅ 插件 {plugin_name} 已禁用") logger.info(f"插件 {plugin_name} 已被禁用") else: await bot.send_text(to_wxid, f"❌ 插件 {plugin_name} 禁用失败")