Files
plain-ub-overfork/app/plugins/system/modules.py
overspend1 4f607f024a Fix plugin system errors and improve module listing
- Fixed BaseModule import error in module_manager.py
- Updated module_manager to properly delegate to plugin_loader
- Added comprehensive .listmodules command showing all available modules
- Enhanced plugin discovery to show detailed module information
- All import errors resolved, bot starts cleanly
2025-07-25 21:02:13 +02:00

228 lines
7.8 KiB
Python
Raw Blame History

This file contains invisible Unicode characters
This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
"""
Module management commands
"""
from app import BOT, Message, bot
from app.plugins.core.loader import plugin_loader
from app.plugins.core.decorators import error_handler
@bot.add_cmd(cmd="plugins")
@error_handler("Plugin management command failed")
async def manage_plugins(bot: BOT, message: Message):
"""
CMD: PLUGINS
INFO: Manage bot plugins
USAGE:
.plugins - List all plugins
.plugins status - Show plugin status
.plugins load <name> - Load plugin
.plugins unload <name> - Unload plugin
.plugins reload - Reload all plugins
.plugins discover - Discover available plugins
"""
args = message.input.split() if message.input else []
if not args or args[0] == "list":
# List loaded plugins
plugins = plugin_loader.list_loaded_plugins()
if not plugins:
await message.reply("No plugins loaded")
return
plugin_text = "🔌 **Loaded Plugins:**\n\n"
for i, plugin_name in enumerate(plugins, 1):
plugin = plugin_loader.get_plugin(plugin_name)
status = "✅ Enabled" if plugin and plugin.enabled else "❌ Disabled"
plugin_text += f"{i}. **{plugin_name}** - {status}\n"
await message.reply(plugin_text)
elif args[0] == "status":
# Show detailed status
status_dict = plugin_loader.get_plugin_status()
if not status_dict:
await message.reply("No plugins loaded")
return
status_text = "📊 **Plugin Status:**\n\n"
enabled_count = sum(status_dict.values())
total_count = len(status_dict)
status_text += f"**Summary:** {enabled_count}/{total_count} plugins enabled\n\n"
for name, enabled in status_dict.items():
status_icon = "" if enabled else ""
status_text += f"{status_icon} **{name}**\n"
await message.reply(status_text)
elif args[0] == "load" and len(args) > 1:
# Load specific plugin
plugin_name = args[1]
processing_msg = await message.reply(f"🔄 Loading plugin: **{plugin_name}**...")
success = await plugin_loader.load_plugin(plugin_name)
if success:
await processing_msg.edit(f"✅ Loaded plugin: **{plugin_name}**")
else:
await processing_msg.edit(f"❌ Failed to load plugin: **{plugin_name}**")
elif args[0] == "unload" and len(args) > 1:
# Unload specific plugin
plugin_name = args[1]
processing_msg = await message.reply(f"🔄 Unloading plugin: **{plugin_name}**...")
success = await plugin_loader.unload_plugin(plugin_name)
if success:
await processing_msg.edit(f"✅ Unloaded plugin: **{plugin_name}**")
else:
await processing_msg.edit(f"❌ Failed to unload plugin: **{plugin_name}**")
elif args[0] == "reload":
# Reload all plugins
processing_msg = await message.reply("🔄 Reloading all plugins...")
results = await plugin_loader.load_all_plugins()
success_count = sum(results.values())
total_count = len(results)
if success_count == total_count:
await processing_msg.edit("✅ All plugins reloaded successfully")
else:
await processing_msg.edit(f"⚠️ Reloaded {success_count}/{total_count} plugins. Check logs for details.")
elif args[0] == "discover":
# Discover available plugins
available_plugins = plugin_loader.discover_plugins()
loaded_plugins = plugin_loader.list_loaded_plugins()
if not available_plugins:
await message.reply("No plugins found in plugins directory")
return
discover_text = "🔍 **Available Plugins:**\n\n"
for i, plugin_name in enumerate(available_plugins, 1):
status = "✅ Loaded" if plugin_name in loaded_plugins else "⭕ Not Loaded"
discover_text += f"{i}. **{plugin_name}** - {status}\n"
await message.reply(discover_text)
else:
# Show help
help_text = """🔌 **Plugin Management Help**
**Commands:**
• `.plugins` - List loaded plugins
• `.plugins status` - Show detailed status
• `.plugins load <name>` - Load a plugin
• `.plugins unload <name>` - Unload a plugin
• `.plugins reload` - Reload all plugins
• `.plugins discover` - Show available plugins
**Examples:**
• `.plugins status`
• `.plugins load ai`
• `.plugins unload torrent_leech`
"""
await message.reply(help_text)
@bot.add_cmd(cmd="pluginfo")
@error_handler("Plugin info command failed")
async def plugin_info(bot: BOT, message: Message):
"""
CMD: PLUGINFO
INFO: Get detailed information about a plugin
USAGE: .pluginfo <plugin_name>
"""
if not message.input:
await message.reply("Please specify a plugin name")
return
plugin_name = message.input.strip()
plugin = plugin_loader.get_plugin(plugin_name)
if not plugin:
available = ", ".join(plugin_loader.list_loaded_plugins())
await message.reply(f"Plugin **{plugin_name}** not found.\n\nLoaded: {available}")
return
info_text = f" **Plugin Information**\n\n"
info_text += f"**Name:** {plugin.name}\n"
info_text += f"**Status:** {'✅ Enabled' if plugin.enabled else '❌ Disabled'}\n"
info_text += f"**Type:** {type(plugin).__name__}\n"
# Show configuration if available
if hasattr(plugin, 'config') and plugin.config:
info_text += f"**Configuration:** {len(plugin.config)} settings\n"
# Show additional info based on plugin type
if hasattr(plugin, 'api_key'):
info_text += f"**API Key:** {'✅ Configured' if plugin.api_key else '❌ Missing'}\n"
if hasattr(plugin, 'commands'):
info_text += f"**Commands:** {', '.join(plugin.commands)}\n"
if hasattr(plugin, 'supported_types'):
info_text += f"**Supported Types:** {', '.join(plugin.supported_types)}\n"
await message.reply(info_text)
@bot.add_cmd(cmd="listmodules")
@error_handler("List modules command failed")
async def list_all_modules(bot: BOT, message: Message):
"""
CMD: LISTMODULES
INFO: List all available modules in the plugins directory
USAGE: .listmodules
"""
# Get all modules by plugin
modules_by_plugin = plugin_loader.discover_all_modules()
loaded_plugins = plugin_loader.list_loaded_plugins()
if not modules_by_plugin:
await message.reply("No modules found in plugins directory")
return
list_text = "📁 **All Available Modules:**\n\n"
total_plugins = 0
total_modules = 0
for plugin_name, modules in modules_by_plugin.items():
total_plugins += 1
total_modules += len(modules)
# Plugin status
status = "✅ Loaded" if plugin_name in loaded_plugins else "⭕ Not Loaded"
list_text += f"**📂 {plugin_name}** ({len(modules)} modules) - {status}\n"
# List modules in this plugin
for module in modules:
list_text += f" • `{module}.py`\n"
list_text += "\n"
# Summary
list_text += f"**📊 Summary:**\n"
list_text += f"• **{total_plugins}** plugin directories\n"
list_text += f"• **{total_modules}** total modules\n"
list_text += f"• **{len(loaded_plugins)}** plugins loaded\n"
# Split message if too long
if len(list_text) > 4000:
parts = [list_text[i:i+4000] for i in range(0, len(list_text), 4000)]
for i, part in enumerate(parts):
if i == 0:
await message.reply(part)
else:
await message.reply(f"**Continued...**\n\n{part}")
else:
await message.reply(list_text)