claude-mpm 4.0.28__py3-none-any.whl → 4.0.30__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- claude_mpm/agents/BASE_AGENT_TEMPLATE.md +48 -3
- claude_mpm/agents/BASE_PM.md +20 -15
- claude_mpm/agents/INSTRUCTIONS.md +12 -2
- claude_mpm/agents/templates/agent-manager.json +24 -0
- claude_mpm/agents/templates/agent-manager.md +304 -0
- claude_mpm/agents/templates/documentation.json +16 -3
- claude_mpm/agents/templates/engineer.json +19 -5
- claude_mpm/agents/templates/ops.json +19 -5
- claude_mpm/agents/templates/qa.json +16 -3
- claude_mpm/agents/templates/refactoring_engineer.json +25 -7
- claude_mpm/agents/templates/research.json +19 -5
- claude_mpm/cli/__init__.py +4 -0
- claude_mpm/cli/commands/__init__.py +4 -0
- claude_mpm/cli/commands/agent_manager.py +521 -0
- claude_mpm/cli/commands/agents.py +2 -1
- claude_mpm/cli/commands/cleanup.py +1 -1
- claude_mpm/cli/commands/doctor.py +209 -0
- claude_mpm/cli/commands/mcp.py +3 -3
- claude_mpm/cli/commands/mcp_install_commands.py +12 -30
- claude_mpm/cli/commands/mcp_server_commands.py +9 -9
- claude_mpm/cli/commands/memory.py +1 -1
- claude_mpm/cli/commands/run.py +31 -2
- claude_mpm/cli/commands/run_config_checker.py +1 -1
- claude_mpm/cli/parsers/agent_manager_parser.py +247 -0
- claude_mpm/cli/parsers/base_parser.py +12 -1
- claude_mpm/cli/parsers/mcp_parser.py +1 -1
- claude_mpm/cli/parsers/run_parser.py +1 -1
- claude_mpm/cli/shared/__init__.py +1 -1
- claude_mpm/cli/startup_logging.py +463 -0
- claude_mpm/constants.py +2 -0
- claude_mpm/core/claude_runner.py +81 -2
- claude_mpm/core/constants.py +2 -2
- claude_mpm/core/framework_loader.py +45 -11
- claude_mpm/core/interactive_session.py +82 -3
- claude_mpm/core/output_style_manager.py +6 -6
- claude_mpm/core/socketio_pool.py +2 -2
- claude_mpm/core/unified_paths.py +128 -0
- claude_mpm/dashboard/static/built/components/event-viewer.js +1 -1
- claude_mpm/dashboard/static/built/components/module-viewer.js +1 -1
- claude_mpm/dashboard/static/built/dashboard.js +1 -1
- claude_mpm/dashboard/static/built/socket-client.js +1 -1
- claude_mpm/dashboard/static/css/dashboard.css +170 -0
- claude_mpm/dashboard/static/dist/components/module-viewer.js +1 -1
- claude_mpm/dashboard/static/dist/dashboard.js +1 -1
- claude_mpm/dashboard/static/dist/socket-client.js +1 -1
- claude_mpm/dashboard/static/js/components/file-tool-tracker.js +21 -3
- claude_mpm/dashboard/static/js/components/module-viewer.js +129 -1
- claude_mpm/dashboard/static/js/dashboard.js +116 -0
- claude_mpm/dashboard/static/js/socket-client.js +0 -1
- claude_mpm/hooks/claude_hooks/connection_pool.py +1 -1
- claude_mpm/hooks/claude_hooks/hook_handler.py +1 -1
- claude_mpm/scripts/mcp_server.py +2 -2
- claude_mpm/services/agents/agent_builder.py +455 -0
- claude_mpm/services/agents/deployment/agent_template_builder.py +10 -3
- claude_mpm/services/agents/deployment/agent_validator.py +1 -0
- claude_mpm/services/agents/deployment/multi_source_deployment_service.py +69 -1
- claude_mpm/services/diagnostics/__init__.py +18 -0
- claude_mpm/services/diagnostics/checks/__init__.py +30 -0
- claude_mpm/services/diagnostics/checks/agent_check.py +319 -0
- claude_mpm/services/diagnostics/checks/base_check.py +64 -0
- claude_mpm/services/diagnostics/checks/claude_desktop_check.py +283 -0
- claude_mpm/services/diagnostics/checks/common_issues_check.py +354 -0
- claude_mpm/services/diagnostics/checks/configuration_check.py +300 -0
- claude_mpm/services/diagnostics/checks/filesystem_check.py +233 -0
- claude_mpm/services/diagnostics/checks/installation_check.py +255 -0
- claude_mpm/services/diagnostics/checks/mcp_check.py +315 -0
- claude_mpm/services/diagnostics/checks/monitor_check.py +282 -0
- claude_mpm/services/diagnostics/checks/startup_log_check.py +322 -0
- claude_mpm/services/diagnostics/diagnostic_runner.py +247 -0
- claude_mpm/services/diagnostics/doctor_reporter.py +283 -0
- claude_mpm/services/diagnostics/models.py +120 -0
- claude_mpm/services/mcp_gateway/core/interfaces.py +1 -1
- claude_mpm/services/mcp_gateway/main.py +1 -1
- claude_mpm/services/mcp_gateway/server/mcp_gateway.py +3 -3
- claude_mpm/services/mcp_gateway/server/stdio_handler.py +1 -1
- claude_mpm/services/mcp_gateway/server/stdio_server.py +3 -3
- claude_mpm/services/mcp_gateway/tools/ticket_tools.py +2 -2
- claude_mpm/services/memory/__init__.py +2 -0
- claude_mpm/services/socketio/handlers/connection.py +27 -33
- claude_mpm/services/socketio/handlers/registry.py +39 -7
- claude_mpm/services/socketio/server/core.py +72 -22
- claude_mpm/validation/frontmatter_validator.py +1 -1
- {claude_mpm-4.0.28.dist-info → claude_mpm-4.0.30.dist-info}/METADATA +4 -1
- {claude_mpm-4.0.28.dist-info → claude_mpm-4.0.30.dist-info}/RECORD +89 -67
- /claude_mpm/cli/shared/{command_base.py → base_command.py} +0 -0
- {claude_mpm-4.0.28.dist-info → claude_mpm-4.0.30.dist-info}/WHEEL +0 -0
- {claude_mpm-4.0.28.dist-info → claude_mpm-4.0.30.dist-info}/entry_points.txt +0 -0
- {claude_mpm-4.0.28.dist-info → claude_mpm-4.0.30.dist-info}/licenses/LICENSE +0 -0
- {claude_mpm-4.0.28.dist-info → claude_mpm-4.0.30.dist-info}/top_level.txt +0 -0
|
@@ -70,21 +70,31 @@ class EventHandlerRegistry:
|
|
|
70
70
|
)
|
|
71
71
|
return
|
|
72
72
|
|
|
73
|
+
# Add debug logging for deployment context
|
|
74
|
+
try:
|
|
75
|
+
from ....core.unified_paths import PathContext
|
|
76
|
+
deployment_context = PathContext.detect_deployment_context()
|
|
77
|
+
self.logger.info(f"Initializing event handlers in {deployment_context.value} mode")
|
|
78
|
+
except Exception as e:
|
|
79
|
+
self.logger.debug(f"Could not detect deployment context: {e}")
|
|
80
|
+
|
|
73
81
|
handler_classes = handler_classes or self.DEFAULT_HANDLERS
|
|
82
|
+
self.logger.debug(f"Initializing {len(handler_classes)} handler classes")
|
|
74
83
|
|
|
75
84
|
for handler_class in handler_classes:
|
|
76
85
|
try:
|
|
86
|
+
self.logger.debug(f"Creating instance of {handler_class.__name__}")
|
|
77
87
|
handler = handler_class(self.server)
|
|
78
88
|
self.handlers.append(handler)
|
|
79
|
-
self.logger.info(f"Initialized handler: {handler_class.__name__}")
|
|
89
|
+
self.logger.info(f"✅ Initialized handler: {handler_class.__name__}")
|
|
80
90
|
except Exception as e:
|
|
81
|
-
self.logger.error(f"Failed to initialize {handler_class.__name__}: {e}")
|
|
91
|
+
self.logger.error(f"❌ Failed to initialize {handler_class.__name__}: {e}")
|
|
82
92
|
import traceback
|
|
83
93
|
|
|
84
94
|
self.logger.error(f"Stack trace: {traceback.format_exc()}")
|
|
85
95
|
|
|
86
96
|
self._initialized = True
|
|
87
|
-
self.logger.info(f"Registry initialized with {len(self.handlers)} handlers")
|
|
97
|
+
self.logger.info(f"🎯 Registry initialized with {len(self.handlers)} handlers")
|
|
88
98
|
|
|
89
99
|
def register_all_events(self) -> None:
|
|
90
100
|
"""Register all events from all handlers.
|
|
@@ -97,27 +107,49 @@ class EventHandlerRegistry:
|
|
|
97
107
|
self.logger.error("Registry not initialized. Call initialize() first.")
|
|
98
108
|
raise RuntimeError("EventHandlerRegistry not initialized")
|
|
99
109
|
|
|
110
|
+
self.logger.info(f"🔄 Starting event registration for {len(self.handlers)} handlers")
|
|
111
|
+
|
|
112
|
+
# Verify Socket.IO server is available
|
|
113
|
+
if not hasattr(self.server, 'core') or not self.server.core or not self.server.core.sio:
|
|
114
|
+
self.logger.error("❌ Socket.IO server instance not available for event registration")
|
|
115
|
+
raise RuntimeError("Socket.IO server not available")
|
|
116
|
+
|
|
117
|
+
self.logger.debug(f"Socket.IO server available: {type(self.server.core.sio)}")
|
|
118
|
+
|
|
100
119
|
registered_count = 0
|
|
101
120
|
for handler in self.handlers:
|
|
102
121
|
try:
|
|
122
|
+
self.logger.debug(f"Registering events for {handler.__class__.__name__}")
|
|
123
|
+
|
|
124
|
+
# Get the number of registered events before and after
|
|
125
|
+
sio_events_before = len(getattr(self.server.core.sio, 'handlers', {}))
|
|
126
|
+
|
|
103
127
|
handler.register_events()
|
|
128
|
+
|
|
129
|
+
sio_events_after = len(getattr(self.server.core.sio, 'handlers', {}))
|
|
130
|
+
events_added = sio_events_after - sio_events_before
|
|
131
|
+
|
|
104
132
|
registered_count += 1
|
|
105
|
-
self.logger.info(f"Registered events for {handler.__class__.__name__}")
|
|
133
|
+
self.logger.info(f"✅ Registered {events_added} events for {handler.__class__.__name__}")
|
|
134
|
+
|
|
106
135
|
except NotImplementedError:
|
|
107
136
|
# Handler has no events to register (like ProjectEventHandler)
|
|
108
137
|
self.logger.debug(
|
|
109
|
-
f"No events to register for {handler.__class__.__name__}"
|
|
138
|
+
f"⏭️ No events to register for {handler.__class__.__name__}"
|
|
110
139
|
)
|
|
111
140
|
except Exception as e:
|
|
112
141
|
self.logger.error(
|
|
113
|
-
f"Failed to register events for {handler.__class__.__name__}: {e}"
|
|
142
|
+
f"❌ Failed to register events for {handler.__class__.__name__}: {e}"
|
|
114
143
|
)
|
|
115
144
|
import traceback
|
|
116
145
|
|
|
117
146
|
self.logger.error(f"Stack trace: {traceback.format_exc()}")
|
|
118
147
|
|
|
148
|
+
# Final verification
|
|
149
|
+
total_sio_events = len(getattr(self.server.core.sio, 'handlers', {}))
|
|
119
150
|
self.logger.info(
|
|
120
|
-
f"
|
|
151
|
+
f"🎉 Event registration complete: {registered_count} handlers processed, "
|
|
152
|
+
f"{total_sio_events} total Socket.IO events registered"
|
|
121
153
|
)
|
|
122
154
|
|
|
123
155
|
def add_handler(self, handler_class: Type[BaseEventHandler]):
|
|
@@ -231,15 +231,27 @@ class SocketIOServerCore:
|
|
|
231
231
|
def _setup_static_files(self):
|
|
232
232
|
"""Setup static file serving for the dashboard."""
|
|
233
233
|
try:
|
|
234
|
+
# Add debug logging for deployment context
|
|
235
|
+
try:
|
|
236
|
+
from ....core.unified_paths import PathContext
|
|
237
|
+
deployment_context = PathContext.detect_deployment_context()
|
|
238
|
+
self.logger.debug(f"Setting up static files in {deployment_context.value} mode")
|
|
239
|
+
except Exception as e:
|
|
240
|
+
self.logger.debug(f"Could not detect deployment context: {e}")
|
|
241
|
+
|
|
234
242
|
self.dashboard_path = self._find_static_path()
|
|
235
243
|
|
|
236
244
|
if self.dashboard_path and self.dashboard_path.exists():
|
|
245
|
+
self.logger.info(f"✅ Dashboard found at: {self.dashboard_path}")
|
|
246
|
+
|
|
237
247
|
# Serve index.html at root
|
|
238
248
|
async def index_handler(request):
|
|
239
249
|
index_file = self.dashboard_path / "index.html"
|
|
240
250
|
if index_file.exists():
|
|
251
|
+
self.logger.debug(f"Serving dashboard index from: {index_file}")
|
|
241
252
|
return web.FileResponse(index_file)
|
|
242
253
|
else:
|
|
254
|
+
self.logger.warning(f"Dashboard index.html not found at: {index_file}")
|
|
243
255
|
return web.Response(text="Dashboard not available", status=404)
|
|
244
256
|
|
|
245
257
|
self.app.router.add_get("/", index_handler)
|
|
@@ -252,10 +264,12 @@ class SocketIOServerCore:
|
|
|
252
264
|
self.app.router.add_static(
|
|
253
265
|
"/static/", dashboard_static_path, name="dashboard_static"
|
|
254
266
|
)
|
|
267
|
+
self.logger.info(f"✅ Static assets available at: {dashboard_static_path}")
|
|
255
268
|
else:
|
|
256
|
-
self.logger.
|
|
269
|
+
self.logger.warning(f"⚠️ Static assets directory not found at: {dashboard_static_path}")
|
|
257
270
|
|
|
258
271
|
else:
|
|
272
|
+
self.logger.warning("⚠️ No dashboard found, serving fallback response")
|
|
259
273
|
# Fallback handler
|
|
260
274
|
async def fallback_handler(request):
|
|
261
275
|
return web.Response(
|
|
@@ -266,7 +280,10 @@ class SocketIOServerCore:
|
|
|
266
280
|
self.app.router.add_get("/", fallback_handler)
|
|
267
281
|
|
|
268
282
|
except Exception as e:
|
|
269
|
-
self.logger.
|
|
283
|
+
self.logger.error(f"❌ Error setting up static files: {e}")
|
|
284
|
+
import traceback
|
|
285
|
+
self.logger.debug(f"Static file setup traceback: {traceback.format_exc()}")
|
|
286
|
+
|
|
270
287
|
# Ensure we always have a basic handler
|
|
271
288
|
async def error_handler(request):
|
|
272
289
|
return web.Response(
|
|
@@ -281,40 +298,73 @@ class SocketIOServerCore:
|
|
|
281
298
|
WHY: The static files location varies depending on how the application
|
|
282
299
|
is installed and run. We try multiple common locations to find them.
|
|
283
300
|
"""
|
|
301
|
+
# Get deployment-context-aware paths
|
|
302
|
+
try:
|
|
303
|
+
from ....core.unified_paths import get_path_manager
|
|
304
|
+
path_manager = get_path_manager()
|
|
305
|
+
|
|
306
|
+
# Use package root for installed packages (including pipx)
|
|
307
|
+
package_root = path_manager.package_root
|
|
308
|
+
self.logger.debug(f"Package root: {package_root}")
|
|
309
|
+
|
|
310
|
+
# Use project root for development
|
|
311
|
+
project_root = get_project_root()
|
|
312
|
+
self.logger.debug(f"Project root: {project_root}")
|
|
313
|
+
|
|
314
|
+
except Exception as e:
|
|
315
|
+
self.logger.debug(f"Could not get path manager: {e}")
|
|
316
|
+
package_root = None
|
|
317
|
+
project_root = get_project_root()
|
|
318
|
+
|
|
284
319
|
# Try multiple possible locations for static files and dashboard
|
|
285
320
|
possible_paths = [
|
|
286
|
-
#
|
|
287
|
-
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
|
|
292
|
-
/ "src"
|
|
293
|
-
/ "
|
|
294
|
-
/ "services"
|
|
295
|
-
/ "socketio"
|
|
296
|
-
/ "static",
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
# Package installation locations
|
|
321
|
+
# Package-based paths (for pipx and pip installations)
|
|
322
|
+
package_root / "dashboard" / "templates" if package_root else None,
|
|
323
|
+
package_root / "services" / "socketio" / "static" if package_root else None,
|
|
324
|
+
package_root / "static" if package_root else None,
|
|
325
|
+
|
|
326
|
+
# Project-based paths (for development)
|
|
327
|
+
project_root / "src" / "claude_mpm" / "dashboard" / "templates",
|
|
328
|
+
project_root / "dashboard" / "templates",
|
|
329
|
+
project_root / "src" / "claude_mpm" / "services" / "static",
|
|
330
|
+
project_root / "src" / "claude_mpm" / "services" / "socketio" / "static",
|
|
331
|
+
project_root / "static",
|
|
332
|
+
project_root / "src" / "static",
|
|
333
|
+
|
|
334
|
+
# Package installation locations (fallback)
|
|
300
335
|
Path(__file__).parent.parent / "static",
|
|
301
336
|
Path(__file__).parent / "static",
|
|
337
|
+
|
|
302
338
|
# Scripts directory (for standalone installations)
|
|
303
339
|
get_scripts_dir() / "static",
|
|
304
340
|
get_scripts_dir() / "socketio" / "static",
|
|
341
|
+
|
|
305
342
|
# Current working directory
|
|
306
343
|
Path.cwd() / "static",
|
|
307
344
|
Path.cwd() / "socketio" / "static",
|
|
308
345
|
]
|
|
309
346
|
|
|
347
|
+
# Filter out None values
|
|
348
|
+
possible_paths = [p for p in possible_paths if p is not None]
|
|
349
|
+
self.logger.debug(f"Searching {len(possible_paths)} possible static file locations")
|
|
350
|
+
|
|
310
351
|
for path in possible_paths:
|
|
311
|
-
|
|
312
|
-
|
|
313
|
-
if (
|
|
314
|
-
|
|
315
|
-
|
|
352
|
+
self.logger.debug(f"Checking for static files at: {path}")
|
|
353
|
+
try:
|
|
354
|
+
if path.exists() and path.is_dir():
|
|
355
|
+
# Check if it contains expected files
|
|
356
|
+
if (path / "index.html").exists():
|
|
357
|
+
self.logger.info(f"✅ Found static files at: {path}")
|
|
358
|
+
return path
|
|
359
|
+
else:
|
|
360
|
+
self.logger.debug(f"Directory exists but no index.html: {path}")
|
|
361
|
+
else:
|
|
362
|
+
self.logger.debug(f"Path does not exist: {path}")
|
|
363
|
+
except Exception as e:
|
|
364
|
+
self.logger.debug(f"Error checking path {path}: {e}")
|
|
316
365
|
|
|
317
|
-
self.logger.warning("Static files not found - dashboard will not be available")
|
|
366
|
+
self.logger.warning("⚠️ Static files not found - dashboard will not be available")
|
|
367
|
+
self.logger.debug(f"Searched paths: {[str(p) for p in possible_paths]}")
|
|
318
368
|
return None
|
|
319
369
|
|
|
320
370
|
def get_connection_count(self) -> int:
|
|
@@ -4,7 +4,7 @@ from pathlib import Path
|
|
|
4
4
|
Claude Code Frontmatter Validator
|
|
5
5
|
|
|
6
6
|
Validates agent frontmatter against Claude Code Desktop specification.
|
|
7
|
-
Critical for ensuring agents work correctly with Claude
|
|
7
|
+
Critical for ensuring agents work correctly with Claude Code.
|
|
8
8
|
"""
|
|
9
9
|
|
|
10
10
|
import re
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: claude-mpm
|
|
3
|
-
Version: 4.0.
|
|
3
|
+
Version: 4.0.30
|
|
4
4
|
Summary: Claude Multi-Agent Project Manager - Orchestrate Claude with agent delegation and ticket tracking
|
|
5
5
|
Author-email: Bob Matsuoka <bob@matsuoka.com>
|
|
6
6
|
Maintainer: Claude MPM Team
|
|
@@ -146,6 +146,9 @@ claude-mpm run --monitor
|
|
|
146
146
|
# Use MCP Gateway for external tool integration
|
|
147
147
|
claude-mpm mcp
|
|
148
148
|
|
|
149
|
+
# Run health diagnostics
|
|
150
|
+
claude-mpm doctor
|
|
151
|
+
|
|
149
152
|
# Manage memory for large conversation histories
|
|
150
153
|
claude-mpm cleanup-memory
|
|
151
154
|
```
|