Skip to content

Commit 0cc3cad

Browse files
refactor(plugin_manager): Simplify plugin loading and metadata handling
1 parent 8af3e69 commit 0cc3cad

File tree

2 files changed

+39
-51
lines changed

2 files changed

+39
-51
lines changed

chatrixcd/commands.py

Lines changed: 19 additions & 42 deletions
Original file line numberDiff line numberDiff line change
@@ -2362,35 +2362,23 @@ def _gather_plugin_info(self) -> tuple:
23622362
lines.append("• No plugins loaded")
23632363
return lines, info_list
23642364

2365-
# Separate enabled and disabled plugins
2366-
enabled_plugins = [p for p in plugins_status if p.get("enabled", False)]
2367-
disabled_plugins = [p for p in plugins_status if not p.get("enabled", False)]
2368-
2369-
# Sort each list by type, then name
2370-
enabled_plugins.sort(
2371-
key=lambda p: (p.get("type", "generic"), p.get("name", ""))
2372-
)
2373-
disabled_plugins.sort(
2374-
key=lambda p: (p.get("type", "generic"), p.get("name", ""))
2365+
# Sort plugins by enabled status (enabled first), then type, then name
2366+
plugins_status.sort(
2367+
key=lambda p: (
2368+
not p.get(
2369+
"enabled", False
2370+
), # False (enabled) sorts before True (disabled)
2371+
p.get("type", "generic"),
2372+
p.get("name", ""),
2373+
)
23752374
)
23762375

2377-
# Process enabled plugins first
2378-
if enabled_plugins:
2379-
lines.append("**Enabled:**")
2380-
for status in enabled_plugins:
2381-
line = self._format_plugin_line(status, enabled=True)
2382-
lines.append(line)
2383-
info_list.append(self._prepare_plugin_info(status))
2384-
2385-
# Then disabled plugins
2386-
if disabled_plugins:
2387-
if enabled_plugins:
2388-
lines.append("") # Empty line separator
2389-
lines.append("**Disabled:**")
2390-
for status in disabled_plugins:
2391-
line = self._format_plugin_line(status, enabled=False)
2392-
lines.append(line)
2393-
info_list.append(self._prepare_plugin_info(status))
2376+
# Process all plugins
2377+
for status in plugins_status:
2378+
enabled = status.get("enabled", False)
2379+
line = self._format_plugin_line(status, enabled=enabled)
2380+
lines.append(line)
2381+
info_list.append(self._prepare_plugin_info(status))
23942382

23952383
return lines, info_list
23962384

@@ -2502,27 +2490,16 @@ def _build_plugin_html_table(self, plugin_info: list) -> str:
25022490
if not plugin_info:
25032491
return ""
25042492

2505-
# Separate enabled and disabled
2506-
enabled_info = [p for p in plugin_info if p["enabled"]]
2507-
disabled_info = [p for p in plugin_info if not p["enabled"]]
2508-
25092493
table_html = '<br/><table><thead><tr><th colspan="5">Plugins 🔌</th></tr>'
25102494
table_html += (
25112495
"<tr><th>Name</th><th>Description</th><th>Version</th>"
25122496
"<th>Type</th><th>Status</th></tr></thead><tbody>"
25132497
)
25142498

2515-
# Add enabled plugins first
2516-
if enabled_info:
2517-
table_html += '<tr><td colspan="5"><strong>Enabled</strong></td></tr>'
2518-
for info in enabled_info:
2519-
table_html += self._build_plugin_row(info, enabled=True)
2520-
2521-
# Add disabled plugins
2522-
if disabled_info:
2523-
table_html += '<tr><td colspan="5"><strong>Disabled</strong></td></tr>'
2524-
for info in disabled_info:
2525-
table_html += self._build_plugin_row(info, enabled=False)
2499+
# Add all plugins (already sorted by enabled status)
2500+
for info in plugin_info:
2501+
enabled = info["enabled"]
2502+
table_html += self._build_plugin_row(info, enabled=enabled)
25262503

25272504
table_html += "</tbody></table>"
25282505
return table_html

chatrixcd/plugin_manager.py

Lines changed: 20 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -5,13 +5,13 @@
55
webhooks), custom commands, or other extensions.
66
"""
77

8-
import logging
9-
import json
108
import importlib.util
9+
import json
10+
import logging
1111
import sys
12-
from pathlib import Path
13-
from typing import Dict, List, Optional, Any, Type
1412
from abc import ABC, abstractmethod
13+
from pathlib import Path
14+
from typing import Any, Dict, List, Optional, Type
1515

1616
logger = logging.getLogger(__name__)
1717

@@ -59,6 +59,8 @@ def __init__(self, bot: Any, config: Dict[str, Any], metadata: PluginMetadata):
5959
self.config = config
6060
self.metadata = metadata
6161
self.logger = logging.getLogger(f"plugin.{metadata.name}")
62+
# Track runtime enabled state (True if plugin is loaded and initialized)
63+
self._enabled = True
6264

6365
@abstractmethod
6466
async def initialize(self) -> bool:
@@ -106,7 +108,7 @@ def get_status(self) -> Dict[str, Any]:
106108
"version": self.metadata.version,
107109
"type": self.metadata.plugin_type,
108110
"category": self.metadata.category,
109-
"enabled": self.metadata.enabled,
111+
"enabled": self._enabled,
110112
}
111113

112114

@@ -199,7 +201,9 @@ def load_plugin_metadata(self, plugin_dir: Path) -> Optional[PluginMetadata]:
199201
data = json.load(f)
200202

201203
metadata = PluginMetadata(data, plugin_dir)
202-
logger.debug(f"Loaded metadata for plugin: {metadata.name} v{metadata.version}")
204+
logger.debug(
205+
f"Loaded metadata for plugin: {metadata.name} v{metadata.version}"
206+
)
203207
return metadata
204208

205209
except json.JSONDecodeError as e:
@@ -209,7 +213,9 @@ def load_plugin_metadata(self, plugin_dir: Path) -> Optional[PluginMetadata]:
209213
logger.error(f"Error loading metadata from {meta_file}: {e}")
210214
return None
211215

212-
def load_plugin_config(self, plugin_dir: Path, metadata: PluginMetadata) -> Dict[str, Any]:
216+
def load_plugin_config(
217+
self, plugin_dir: Path, metadata: PluginMetadata
218+
) -> Dict[str, Any]:
213219
"""Load plugin configuration from plugin.json file.
214220
215221
Args:
@@ -340,7 +346,9 @@ async def load_plugin(self, plugin_dir: Path) -> bool:
340346
# Track task monitor plugins separately
341347
if isinstance(plugin, TaskMonitorPlugin):
342348
self.task_monitor = plugin
343-
logger.info(f"Loaded task monitor plugin: {metadata.name} v{metadata.version}")
349+
logger.info(
350+
f"Loaded task monitor plugin: {metadata.name} v{metadata.version}"
351+
)
344352
else:
345353
logger.info(f"Loaded plugin: {metadata.name} v{metadata.version}")
346354

@@ -378,7 +386,10 @@ async def load_all_plugins(self) -> int:
378386

379387
if enabled:
380388
# Enforce mutual exclusion: only one TaskMonitorPlugin may be loaded
381-
if metadata.plugin_type == "task_monitor" and self.task_monitor is not None:
389+
if (
390+
metadata.plugin_type == "task_monitor"
391+
and self.task_monitor is not None
392+
):
382393
logger.info(
383394
f"Skipping task monitor plugin '{metadata.name}' because '{self.task_monitor.metadata.name}' is already active"
384395
)

0 commit comments

Comments
 (0)