claude-mpm 3.9.9__py3-none-any.whl → 4.0.3__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/VERSION +1 -1
- claude_mpm/__init__.py +2 -2
- claude_mpm/__main__.py +3 -2
- claude_mpm/agents/__init__.py +85 -79
- claude_mpm/agents/agent_loader.py +464 -1003
- claude_mpm/agents/agent_loader_integration.py +45 -45
- claude_mpm/agents/agents_metadata.py +29 -30
- claude_mpm/agents/async_agent_loader.py +156 -138
- claude_mpm/agents/base_agent.json +1 -1
- claude_mpm/agents/base_agent_loader.py +179 -151
- claude_mpm/agents/frontmatter_validator.py +229 -130
- claude_mpm/agents/schema/agent_schema.json +1 -1
- claude_mpm/agents/system_agent_config.py +213 -147
- claude_mpm/agents/templates/__init__.py +13 -13
- claude_mpm/agents/templates/code_analyzer.json +2 -2
- claude_mpm/agents/templates/data_engineer.json +1 -1
- claude_mpm/agents/templates/documentation.json +23 -11
- claude_mpm/agents/templates/engineer.json +22 -6
- claude_mpm/agents/templates/memory_manager.json +155 -0
- claude_mpm/agents/templates/ops.json +2 -2
- claude_mpm/agents/templates/project_organizer.json +1 -1
- claude_mpm/agents/templates/qa.json +1 -1
- claude_mpm/agents/templates/refactoring_engineer.json +222 -0
- claude_mpm/agents/templates/research.json +20 -14
- claude_mpm/agents/templates/security.json +1 -1
- claude_mpm/agents/templates/ticketing.json +1 -1
- claude_mpm/agents/templates/version_control.json +1 -1
- claude_mpm/agents/templates/web_qa.json +3 -1
- claude_mpm/agents/templates/web_ui.json +2 -2
- claude_mpm/cli/__init__.py +90 -49
- claude_mpm/cli/__main__.py +3 -2
- claude_mpm/cli/commands/__init__.py +21 -18
- claude_mpm/cli/commands/agents.py +279 -247
- claude_mpm/cli/commands/aggregate.py +138 -157
- claude_mpm/cli/commands/cleanup.py +147 -147
- claude_mpm/cli/commands/config.py +93 -76
- claude_mpm/cli/commands/info.py +17 -16
- claude_mpm/cli/commands/mcp.py +143 -762
- claude_mpm/cli/commands/mcp_command_router.py +139 -0
- claude_mpm/cli/commands/mcp_config_commands.py +20 -0
- claude_mpm/cli/commands/mcp_install_commands.py +20 -0
- claude_mpm/cli/commands/mcp_server_commands.py +175 -0
- claude_mpm/cli/commands/mcp_tool_commands.py +34 -0
- claude_mpm/cli/commands/memory.py +239 -203
- claude_mpm/cli/commands/monitor.py +203 -81
- claude_mpm/cli/commands/run.py +380 -429
- claude_mpm/cli/commands/run_config_checker.py +160 -0
- claude_mpm/cli/commands/socketio_monitor.py +235 -0
- claude_mpm/cli/commands/tickets.py +305 -197
- claude_mpm/cli/parser.py +24 -1150
- claude_mpm/cli/parsers/__init__.py +29 -0
- claude_mpm/cli/parsers/agents_parser.py +136 -0
- claude_mpm/cli/parsers/base_parser.py +331 -0
- claude_mpm/cli/parsers/config_parser.py +85 -0
- claude_mpm/cli/parsers/mcp_parser.py +152 -0
- claude_mpm/cli/parsers/memory_parser.py +138 -0
- claude_mpm/cli/parsers/monitor_parser.py +104 -0
- claude_mpm/cli/parsers/run_parser.py +147 -0
- claude_mpm/cli/parsers/tickets_parser.py +203 -0
- claude_mpm/cli/ticket_cli.py +7 -3
- claude_mpm/cli/utils.py +55 -37
- claude_mpm/cli_module/__init__.py +6 -6
- claude_mpm/cli_module/args.py +188 -140
- claude_mpm/cli_module/commands.py +79 -70
- claude_mpm/cli_module/migration_example.py +38 -60
- claude_mpm/config/__init__.py +32 -25
- claude_mpm/config/agent_config.py +151 -119
- claude_mpm/config/experimental_features.py +217 -0
- claude_mpm/config/paths.py +94 -208
- claude_mpm/config/socketio_config.py +84 -73
- claude_mpm/constants.py +36 -18
- claude_mpm/core/__init__.py +9 -6
- claude_mpm/core/agent_name_normalizer.py +68 -71
- claude_mpm/core/agent_registry.py +372 -521
- claude_mpm/core/agent_session_manager.py +74 -63
- claude_mpm/core/base_service.py +116 -87
- claude_mpm/core/cache.py +119 -153
- claude_mpm/core/claude_runner.py +425 -1120
- claude_mpm/core/config.py +263 -168
- claude_mpm/core/config_aliases.py +69 -61
- claude_mpm/core/config_constants.py +292 -0
- claude_mpm/core/constants.py +57 -99
- claude_mpm/core/container.py +211 -178
- claude_mpm/core/exceptions.py +233 -89
- claude_mpm/core/factories.py +92 -54
- claude_mpm/core/framework_loader.py +378 -220
- claude_mpm/core/hook_manager.py +198 -83
- claude_mpm/core/hook_performance_config.py +136 -0
- claude_mpm/core/injectable_service.py +61 -55
- claude_mpm/core/interactive_session.py +165 -155
- claude_mpm/core/interfaces.py +221 -195
- claude_mpm/core/lazy.py +96 -96
- claude_mpm/core/logger.py +133 -107
- claude_mpm/core/logging_config.py +185 -157
- claude_mpm/core/minimal_framework_loader.py +20 -15
- claude_mpm/core/mixins.py +30 -29
- claude_mpm/core/oneshot_session.py +215 -181
- claude_mpm/core/optimized_agent_loader.py +134 -138
- claude_mpm/core/optimized_startup.py +159 -157
- claude_mpm/core/pm_hook_interceptor.py +85 -72
- claude_mpm/core/service_registry.py +103 -101
- claude_mpm/core/session_manager.py +97 -87
- claude_mpm/core/socketio_pool.py +212 -158
- claude_mpm/core/tool_access_control.py +58 -51
- claude_mpm/core/types.py +46 -24
- claude_mpm/core/typing_utils.py +166 -82
- claude_mpm/core/unified_agent_registry.py +721 -0
- claude_mpm/core/unified_config.py +550 -0
- claude_mpm/core/unified_paths.py +549 -0
- claude_mpm/dashboard/index.html +1 -1
- claude_mpm/dashboard/open_dashboard.py +51 -17
- claude_mpm/dashboard/static/css/dashboard.css +27 -8
- claude_mpm/dashboard/static/dist/components/agent-inference.js +2 -0
- claude_mpm/dashboard/static/dist/components/event-processor.js +2 -0
- claude_mpm/dashboard/static/dist/components/event-viewer.js +2 -0
- claude_mpm/dashboard/static/dist/components/export-manager.js +2 -0
- claude_mpm/dashboard/static/dist/components/file-tool-tracker.js +2 -0
- claude_mpm/dashboard/static/dist/components/hud-library-loader.js +2 -0
- claude_mpm/dashboard/static/dist/components/hud-manager.js +2 -0
- claude_mpm/dashboard/static/dist/components/hud-visualizer.js +2 -0
- claude_mpm/dashboard/static/dist/components/module-viewer.js +2 -0
- claude_mpm/dashboard/static/dist/components/session-manager.js +2 -0
- claude_mpm/dashboard/static/dist/components/socket-manager.js +2 -0
- claude_mpm/dashboard/static/dist/components/ui-state-manager.js +2 -0
- claude_mpm/dashboard/static/dist/components/working-directory.js +2 -0
- claude_mpm/dashboard/static/dist/dashboard.js +2 -0
- claude_mpm/dashboard/static/dist/socket-client.js +2 -0
- claude_mpm/dashboard/static/js/components/agent-inference.js +80 -76
- claude_mpm/dashboard/static/js/components/event-processor.js +71 -67
- claude_mpm/dashboard/static/js/components/event-viewer.js +74 -70
- claude_mpm/dashboard/static/js/components/export-manager.js +31 -28
- claude_mpm/dashboard/static/js/components/file-tool-tracker.js +106 -92
- claude_mpm/dashboard/static/js/components/hud-library-loader.js +11 -11
- claude_mpm/dashboard/static/js/components/hud-manager.js +73 -73
- claude_mpm/dashboard/static/js/components/hud-visualizer.js +163 -163
- claude_mpm/dashboard/static/js/components/module-viewer.js +305 -233
- claude_mpm/dashboard/static/js/components/session-manager.js +32 -29
- claude_mpm/dashboard/static/js/components/socket-manager.js +27 -20
- claude_mpm/dashboard/static/js/components/ui-state-manager.js +21 -18
- claude_mpm/dashboard/static/js/components/working-directory.js +74 -71
- claude_mpm/dashboard/static/js/dashboard.js +178 -453
- claude_mpm/dashboard/static/js/extension-error-handler.js +164 -0
- claude_mpm/dashboard/static/js/socket-client.js +120 -54
- claude_mpm/dashboard/templates/index.html +40 -50
- claude_mpm/experimental/cli_enhancements.py +60 -58
- claude_mpm/generators/__init__.py +1 -1
- claude_mpm/generators/agent_profile_generator.py +75 -65
- claude_mpm/hooks/__init__.py +1 -1
- claude_mpm/hooks/base_hook.py +33 -28
- claude_mpm/hooks/claude_hooks/__init__.py +1 -1
- claude_mpm/hooks/claude_hooks/connection_pool.py +120 -0
- claude_mpm/hooks/claude_hooks/event_handlers.py +743 -0
- claude_mpm/hooks/claude_hooks/hook_handler.py +415 -1331
- claude_mpm/hooks/claude_hooks/hook_wrapper.sh +4 -4
- claude_mpm/hooks/claude_hooks/memory_integration.py +221 -0
- claude_mpm/hooks/claude_hooks/response_tracking.py +348 -0
- claude_mpm/hooks/claude_hooks/tool_analysis.py +230 -0
- claude_mpm/hooks/memory_integration_hook.py +140 -100
- claude_mpm/hooks/tool_call_interceptor.py +89 -76
- claude_mpm/hooks/validation_hooks.py +57 -49
- claude_mpm/init.py +145 -121
- claude_mpm/models/__init__.py +9 -9
- claude_mpm/models/agent_definition.py +33 -23
- claude_mpm/models/agent_session.py +228 -200
- claude_mpm/scripts/__init__.py +1 -1
- claude_mpm/scripts/socketio_daemon.py +192 -75
- claude_mpm/scripts/socketio_server_manager.py +328 -0
- claude_mpm/scripts/start_activity_logging.py +25 -22
- claude_mpm/services/__init__.py +68 -43
- claude_mpm/services/agent_capabilities_service.py +271 -0
- claude_mpm/services/agents/__init__.py +23 -32
- claude_mpm/services/agents/deployment/__init__.py +3 -3
- claude_mpm/services/agents/deployment/agent_config_provider.py +310 -0
- claude_mpm/services/agents/deployment/agent_configuration_manager.py +359 -0
- claude_mpm/services/agents/deployment/agent_definition_factory.py +84 -0
- claude_mpm/services/agents/deployment/agent_deployment.py +415 -2113
- claude_mpm/services/agents/deployment/agent_discovery_service.py +387 -0
- claude_mpm/services/agents/deployment/agent_environment_manager.py +293 -0
- claude_mpm/services/agents/deployment/agent_filesystem_manager.py +387 -0
- claude_mpm/services/agents/deployment/agent_format_converter.py +453 -0
- claude_mpm/services/agents/deployment/agent_frontmatter_validator.py +161 -0
- claude_mpm/services/agents/deployment/agent_lifecycle_manager.py +345 -495
- claude_mpm/services/agents/deployment/agent_metrics_collector.py +279 -0
- claude_mpm/services/agents/deployment/agent_restore_handler.py +88 -0
- claude_mpm/services/agents/deployment/agent_template_builder.py +406 -0
- claude_mpm/services/agents/deployment/agent_validator.py +352 -0
- claude_mpm/services/agents/deployment/agent_version_manager.py +313 -0
- claude_mpm/services/agents/deployment/agent_versioning.py +6 -9
- claude_mpm/services/agents/deployment/agents_directory_resolver.py +79 -0
- claude_mpm/services/agents/deployment/async_agent_deployment.py +298 -234
- claude_mpm/services/agents/deployment/config/__init__.py +13 -0
- claude_mpm/services/agents/deployment/config/deployment_config.py +182 -0
- claude_mpm/services/agents/deployment/config/deployment_config_manager.py +200 -0
- claude_mpm/services/agents/deployment/deployment_config_loader.py +54 -0
- claude_mpm/services/agents/deployment/deployment_type_detector.py +124 -0
- claude_mpm/services/agents/deployment/facade/__init__.py +18 -0
- claude_mpm/services/agents/deployment/facade/async_deployment_executor.py +159 -0
- claude_mpm/services/agents/deployment/facade/deployment_executor.py +73 -0
- claude_mpm/services/agents/deployment/facade/deployment_facade.py +270 -0
- claude_mpm/services/agents/deployment/facade/sync_deployment_executor.py +178 -0
- claude_mpm/services/agents/deployment/interface_adapter.py +227 -0
- claude_mpm/services/agents/deployment/lifecycle_health_checker.py +85 -0
- claude_mpm/services/agents/deployment/lifecycle_performance_tracker.py +100 -0
- claude_mpm/services/agents/deployment/pipeline/__init__.py +32 -0
- claude_mpm/services/agents/deployment/pipeline/pipeline_builder.py +158 -0
- claude_mpm/services/agents/deployment/pipeline/pipeline_context.py +159 -0
- claude_mpm/services/agents/deployment/pipeline/pipeline_executor.py +169 -0
- claude_mpm/services/agents/deployment/pipeline/steps/__init__.py +19 -0
- claude_mpm/services/agents/deployment/pipeline/steps/agent_processing_step.py +195 -0
- claude_mpm/services/agents/deployment/pipeline/steps/base_step.py +119 -0
- claude_mpm/services/agents/deployment/pipeline/steps/configuration_step.py +79 -0
- claude_mpm/services/agents/deployment/pipeline/steps/target_directory_step.py +90 -0
- claude_mpm/services/agents/deployment/pipeline/steps/validation_step.py +100 -0
- claude_mpm/services/agents/deployment/processors/__init__.py +15 -0
- claude_mpm/services/agents/deployment/processors/agent_deployment_context.py +98 -0
- claude_mpm/services/agents/deployment/processors/agent_deployment_result.py +235 -0
- claude_mpm/services/agents/deployment/processors/agent_processor.py +258 -0
- claude_mpm/services/agents/deployment/refactored_agent_deployment_service.py +318 -0
- claude_mpm/services/agents/deployment/results/__init__.py +13 -0
- claude_mpm/services/agents/deployment/results/deployment_metrics.py +200 -0
- claude_mpm/services/agents/deployment/results/deployment_result_builder.py +249 -0
- claude_mpm/services/agents/deployment/strategies/__init__.py +25 -0
- claude_mpm/services/agents/deployment/strategies/base_strategy.py +119 -0
- claude_mpm/services/agents/deployment/strategies/project_strategy.py +150 -0
- claude_mpm/services/agents/deployment/strategies/strategy_selector.py +117 -0
- claude_mpm/services/agents/deployment/strategies/system_strategy.py +116 -0
- claude_mpm/services/agents/deployment/strategies/user_strategy.py +137 -0
- claude_mpm/services/agents/deployment/system_instructions_deployer.py +108 -0
- claude_mpm/services/agents/deployment/validation/__init__.py +19 -0
- claude_mpm/services/agents/deployment/validation/agent_validator.py +323 -0
- claude_mpm/services/agents/deployment/validation/deployment_validator.py +238 -0
- claude_mpm/services/agents/deployment/validation/template_validator.py +299 -0
- claude_mpm/services/agents/deployment/validation/validation_result.py +226 -0
- claude_mpm/services/agents/loading/__init__.py +2 -2
- claude_mpm/services/agents/loading/agent_profile_loader.py +259 -229
- claude_mpm/services/agents/loading/base_agent_manager.py +90 -81
- claude_mpm/services/agents/loading/framework_agent_loader.py +154 -129
- claude_mpm/services/agents/management/__init__.py +2 -2
- claude_mpm/services/agents/management/agent_capabilities_generator.py +72 -58
- claude_mpm/services/agents/management/agent_management_service.py +209 -156
- claude_mpm/services/agents/memory/__init__.py +9 -6
- claude_mpm/services/agents/memory/agent_memory_manager.py +218 -1152
- claude_mpm/services/agents/memory/agent_persistence_service.py +20 -16
- claude_mpm/services/agents/memory/analyzer.py +430 -0
- claude_mpm/services/agents/memory/content_manager.py +376 -0
- claude_mpm/services/agents/memory/template_generator.py +468 -0
- claude_mpm/services/agents/registry/__init__.py +7 -10
- claude_mpm/services/agents/registry/deployed_agent_discovery.py +122 -97
- claude_mpm/services/agents/registry/modification_tracker.py +351 -285
- claude_mpm/services/async_session_logger.py +187 -153
- claude_mpm/services/claude_session_logger.py +87 -72
- claude_mpm/services/command_handler_service.py +217 -0
- claude_mpm/services/communication/__init__.py +3 -2
- claude_mpm/services/core/__init__.py +50 -97
- claude_mpm/services/core/base.py +60 -53
- claude_mpm/services/core/interfaces/__init__.py +188 -0
- claude_mpm/services/core/interfaces/agent.py +351 -0
- claude_mpm/services/core/interfaces/communication.py +343 -0
- claude_mpm/services/core/interfaces/infrastructure.py +413 -0
- claude_mpm/services/core/interfaces/service.py +434 -0
- claude_mpm/services/core/interfaces.py +19 -944
- claude_mpm/services/event_aggregator.py +208 -170
- claude_mpm/services/exceptions.py +387 -308
- claude_mpm/services/framework_claude_md_generator/__init__.py +75 -79
- claude_mpm/services/framework_claude_md_generator/content_assembler.py +69 -60
- claude_mpm/services/framework_claude_md_generator/content_validator.py +65 -61
- claude_mpm/services/framework_claude_md_generator/deployment_manager.py +68 -49
- claude_mpm/services/framework_claude_md_generator/section_generators/__init__.py +34 -34
- claude_mpm/services/framework_claude_md_generator/section_generators/agents.py +25 -22
- claude_mpm/services/framework_claude_md_generator/section_generators/claude_pm_init.py +10 -10
- claude_mpm/services/framework_claude_md_generator/section_generators/core_responsibilities.py +4 -3
- claude_mpm/services/framework_claude_md_generator/section_generators/delegation_constraints.py +4 -3
- claude_mpm/services/framework_claude_md_generator/section_generators/environment_config.py +4 -3
- claude_mpm/services/framework_claude_md_generator/section_generators/footer.py +6 -5
- claude_mpm/services/framework_claude_md_generator/section_generators/header.py +8 -7
- claude_mpm/services/framework_claude_md_generator/section_generators/orchestration_principles.py +4 -3
- claude_mpm/services/framework_claude_md_generator/section_generators/role_designation.py +6 -5
- claude_mpm/services/framework_claude_md_generator/section_generators/subprocess_validation.py +9 -8
- claude_mpm/services/framework_claude_md_generator/section_generators/todo_task_tools.py +4 -3
- claude_mpm/services/framework_claude_md_generator/section_generators/troubleshooting.py +5 -4
- claude_mpm/services/framework_claude_md_generator/section_manager.py +28 -27
- claude_mpm/services/framework_claude_md_generator/version_manager.py +30 -28
- claude_mpm/services/hook_service.py +106 -114
- claude_mpm/services/infrastructure/__init__.py +7 -5
- claude_mpm/services/infrastructure/context_preservation.py +571 -0
- claude_mpm/services/infrastructure/daemon_manager.py +279 -0
- claude_mpm/services/infrastructure/logging.py +83 -76
- claude_mpm/services/infrastructure/monitoring.py +547 -404
- claude_mpm/services/mcp_gateway/__init__.py +40 -23
- claude_mpm/services/mcp_gateway/config/__init__.py +2 -2
- claude_mpm/services/mcp_gateway/config/config_loader.py +61 -56
- claude_mpm/services/mcp_gateway/config/config_schema.py +50 -41
- claude_mpm/services/mcp_gateway/config/configuration.py +82 -75
- claude_mpm/services/mcp_gateway/core/__init__.py +14 -21
- claude_mpm/services/mcp_gateway/core/base.py +80 -67
- claude_mpm/services/mcp_gateway/core/exceptions.py +60 -46
- claude_mpm/services/mcp_gateway/core/interfaces.py +97 -93
- claude_mpm/services/mcp_gateway/main.py +307 -127
- claude_mpm/services/mcp_gateway/registry/__init__.py +1 -1
- claude_mpm/services/mcp_gateway/registry/service_registry.py +100 -101
- claude_mpm/services/mcp_gateway/registry/tool_registry.py +135 -126
- claude_mpm/services/mcp_gateway/server/__init__.py +4 -4
- claude_mpm/services/mcp_gateway/server/{mcp_server.py → mcp_gateway.py} +149 -153
- claude_mpm/services/mcp_gateway/server/stdio_handler.py +105 -107
- claude_mpm/services/mcp_gateway/server/stdio_server.py +691 -0
- claude_mpm/services/mcp_gateway/tools/__init__.py +4 -2
- claude_mpm/services/mcp_gateway/tools/base_adapter.py +110 -121
- claude_mpm/services/mcp_gateway/tools/document_summarizer.py +283 -215
- claude_mpm/services/mcp_gateway/tools/hello_world.py +122 -120
- claude_mpm/services/mcp_gateway/tools/ticket_tools.py +652 -0
- claude_mpm/services/mcp_gateway/tools/unified_ticket_tool.py +606 -0
- claude_mpm/services/memory/__init__.py +2 -2
- claude_mpm/services/memory/builder.py +451 -362
- claude_mpm/services/memory/cache/__init__.py +2 -2
- claude_mpm/services/memory/cache/shared_prompt_cache.py +232 -194
- claude_mpm/services/memory/cache/simple_cache.py +107 -93
- claude_mpm/services/memory/indexed_memory.py +195 -193
- claude_mpm/services/memory/optimizer.py +267 -234
- claude_mpm/services/memory/router.py +571 -263
- claude_mpm/services/memory_hook_service.py +237 -0
- claude_mpm/services/port_manager.py +223 -0
- claude_mpm/services/project/__init__.py +3 -3
- claude_mpm/services/project/analyzer.py +451 -305
- claude_mpm/services/project/registry.py +262 -240
- claude_mpm/services/recovery_manager.py +287 -231
- claude_mpm/services/response_tracker.py +87 -67
- claude_mpm/services/runner_configuration_service.py +587 -0
- claude_mpm/services/session_management_service.py +304 -0
- claude_mpm/services/socketio/__init__.py +4 -4
- claude_mpm/services/socketio/client_proxy.py +174 -0
- claude_mpm/services/socketio/handlers/__init__.py +3 -3
- claude_mpm/services/socketio/handlers/base.py +44 -30
- claude_mpm/services/socketio/handlers/connection.py +145 -65
- claude_mpm/services/socketio/handlers/file.py +123 -108
- claude_mpm/services/socketio/handlers/git.py +607 -373
- claude_mpm/services/socketio/handlers/hook.py +170 -0
- claude_mpm/services/socketio/handlers/memory.py +4 -4
- claude_mpm/services/socketio/handlers/project.py +4 -4
- claude_mpm/services/socketio/handlers/registry.py +53 -38
- claude_mpm/services/socketio/server/__init__.py +18 -0
- claude_mpm/services/socketio/server/broadcaster.py +252 -0
- claude_mpm/services/socketio/server/core.py +399 -0
- claude_mpm/services/socketio/server/main.py +323 -0
- claude_mpm/services/socketio_client_manager.py +160 -133
- claude_mpm/services/socketio_server.py +36 -1885
- claude_mpm/services/subprocess_launcher_service.py +316 -0
- claude_mpm/services/system_instructions_service.py +258 -0
- claude_mpm/services/ticket_manager.py +20 -534
- claude_mpm/services/utility_service.py +285 -0
- claude_mpm/services/version_control/__init__.py +18 -21
- claude_mpm/services/version_control/branch_strategy.py +20 -10
- claude_mpm/services/version_control/conflict_resolution.py +37 -13
- claude_mpm/services/version_control/git_operations.py +52 -21
- claude_mpm/services/version_control/semantic_versioning.py +92 -53
- claude_mpm/services/version_control/version_parser.py +145 -125
- claude_mpm/services/version_service.py +270 -0
- claude_mpm/storage/__init__.py +9 -0
- claude_mpm/storage/state_storage.py +552 -0
- claude_mpm/ticket_wrapper.py +2 -2
- claude_mpm/utils/__init__.py +2 -2
- claude_mpm/utils/agent_dependency_loader.py +453 -243
- claude_mpm/utils/config_manager.py +157 -118
- claude_mpm/utils/console.py +1 -1
- claude_mpm/utils/dependency_cache.py +102 -107
- claude_mpm/utils/dependency_manager.py +52 -47
- claude_mpm/utils/dependency_strategies.py +131 -96
- claude_mpm/utils/environment_context.py +110 -102
- claude_mpm/utils/error_handler.py +75 -55
- claude_mpm/utils/file_utils.py +80 -67
- claude_mpm/utils/framework_detection.py +12 -11
- claude_mpm/utils/import_migration_example.py +12 -60
- claude_mpm/utils/imports.py +48 -45
- claude_mpm/utils/path_operations.py +100 -93
- claude_mpm/utils/robust_installer.py +172 -164
- claude_mpm/utils/session_logging.py +30 -23
- claude_mpm/utils/subprocess_utils.py +99 -61
- claude_mpm/validation/__init__.py +1 -1
- claude_mpm/validation/agent_validator.py +151 -111
- claude_mpm/validation/frontmatter_validator.py +92 -71
- {claude_mpm-3.9.9.dist-info → claude_mpm-4.0.3.dist-info}/METADATA +51 -2
- claude_mpm-4.0.3.dist-info/RECORD +402 -0
- {claude_mpm-3.9.9.dist-info → claude_mpm-4.0.3.dist-info}/entry_points.txt +1 -0
- {claude_mpm-3.9.9.dist-info → claude_mpm-4.0.3.dist-info}/licenses/LICENSE +1 -1
- claude_mpm/config/memory_guardian_config.py +0 -325
- claude_mpm/core/config_paths.py +0 -150
- claude_mpm/dashboard/static/js/dashboard-original.js +0 -4134
- claude_mpm/deployment_paths.py +0 -261
- claude_mpm/hooks/claude_hooks/hook_handler_fixed.py +0 -454
- claude_mpm/models/state_models.py +0 -433
- claude_mpm/services/agent/__init__.py +0 -24
- claude_mpm/services/agent/deployment.py +0 -2548
- claude_mpm/services/agent/management.py +0 -598
- claude_mpm/services/agent/registry.py +0 -813
- claude_mpm/services/agents/registry/agent_registry.py +0 -813
- claude_mpm/services/communication/socketio.py +0 -1935
- claude_mpm/services/communication/websocket.py +0 -479
- claude_mpm/services/framework_claude_md_generator.py +0 -624
- claude_mpm/services/health_monitor.py +0 -893
- claude_mpm/services/infrastructure/memory_guardian.py +0 -770
- claude_mpm/services/mcp_gateway/server/mcp_server_simple.py +0 -444
- claude_mpm/services/optimized_hook_service.py +0 -542
- claude_mpm/services/project_analyzer.py +0 -864
- claude_mpm/services/project_registry.py +0 -608
- claude_mpm/services/standalone_socketio_server.py +0 -1300
- claude_mpm/services/ticket_manager_di.py +0 -318
- claude_mpm/services/ticketing_service_original.py +0 -510
- claude_mpm/utils/paths.py +0 -395
- claude_mpm/utils/platform_memory.py +0 -524
- claude_mpm-3.9.9.dist-info/RECORD +0 -293
- {claude_mpm-3.9.9.dist-info → claude_mpm-4.0.3.dist-info}/WHEEL +0 -0
- {claude_mpm-3.9.9.dist-info → claude_mpm-4.0.3.dist-info}/top_level.txt +0 -0
| @@ -9,30 +9,30 @@ Part of ISS-0035: MCP Server Implementation - Core Server and Tool Registry | |
| 9 9 | 
             
            """
         | 
| 10 10 |  | 
| 11 11 | 
             
            import asyncio
         | 
| 12 | 
            -
            from typing import Dict, List, Optional, Set, Any
         | 
| 13 | 
            -
            from datetime import datetime
         | 
| 14 12 | 
             
            import re
         | 
| 15 13 | 
             
            import traceback
         | 
| 14 | 
            +
            from datetime import datetime
         | 
| 16 15 | 
             
            from threading import RLock
         | 
| 16 | 
            +
            from typing import Any, Dict, List, Optional, Set
         | 
| 17 17 |  | 
| 18 | 
            +
            from claude_mpm.services.mcp_gateway.core.base import BaseMCPService
         | 
| 18 19 | 
             
            from claude_mpm.services.mcp_gateway.core.interfaces import (
         | 
| 19 | 
            -
                IMCPToolRegistry,
         | 
| 20 20 | 
             
                IMCPToolAdapter,
         | 
| 21 | 
            +
                IMCPToolRegistry,
         | 
| 21 22 | 
             
                MCPToolDefinition,
         | 
| 22 23 | 
             
                MCPToolInvocation,
         | 
| 23 24 | 
             
                MCPToolResult,
         | 
| 24 25 | 
             
            )
         | 
| 25 | 
            -
            from claude_mpm.services.mcp_gateway.core.base import BaseMCPService
         | 
| 26 26 |  | 
| 27 27 |  | 
| 28 28 | 
             
            class ToolRegistry(BaseMCPService, IMCPToolRegistry):
         | 
| 29 29 | 
             
                """
         | 
| 30 30 | 
             
                Thread-safe tool registry implementation.
         | 
| 31 | 
            -
             | 
| 31 | 
            +
             | 
| 32 32 | 
             
                WHY: We need a centralized registry to manage all MCP tools, ensuring
         | 
| 33 33 | 
             
                thread safety for concurrent access, efficient tool discovery, and
         | 
| 34 34 | 
             
                proper lifecycle management.
         | 
| 35 | 
            -
             | 
| 35 | 
            +
             | 
| 36 36 | 
             
                DESIGN DECISIONS:
         | 
| 37 37 | 
             
                - Use RLock for thread safety to allow recursive locking
         | 
| 38 38 | 
             
                - Maintain both adapters and definitions for fast access
         | 
| @@ -40,49 +40,49 @@ class ToolRegistry(BaseMCPService, IMCPToolRegistry): | |
| 40 40 | 
             
                - Track metrics for monitoring and optimization
         | 
| 41 41 | 
             
                - Support pattern-based search for tool discovery
         | 
| 42 42 | 
             
                """
         | 
| 43 | 
            -
             | 
| 43 | 
            +
             | 
| 44 44 | 
             
                def __init__(self):
         | 
| 45 45 | 
             
                    """Initialize the tool registry."""
         | 
| 46 46 | 
             
                    super().__init__("ToolRegistry")
         | 
| 47 | 
            -
             | 
| 47 | 
            +
             | 
| 48 48 | 
             
                    # Thread safety
         | 
| 49 49 | 
             
                    self._lock = RLock()
         | 
| 50 | 
            -
             | 
| 50 | 
            +
             | 
| 51 51 | 
             
                    # Tool storage
         | 
| 52 52 | 
             
                    self._adapters: Dict[str, IMCPToolAdapter] = {}
         | 
| 53 53 | 
             
                    self._definitions: Dict[str, MCPToolDefinition] = {}
         | 
| 54 | 
            -
             | 
| 54 | 
            +
             | 
| 55 55 | 
             
                    # Tool categories for organization
         | 
| 56 56 | 
             
                    self._categories: Dict[str, Set[str]] = {
         | 
| 57 57 | 
             
                        "system": set(),
         | 
| 58 58 | 
             
                        "user": set(),
         | 
| 59 59 | 
             
                        "builtin": set(),
         | 
| 60 | 
            -
                        "external": set()
         | 
| 60 | 
            +
                        "external": set(),
         | 
| 61 61 | 
             
                    }
         | 
| 62 | 
            -
             | 
| 62 | 
            +
             | 
| 63 63 | 
             
                    # Metrics
         | 
| 64 64 | 
             
                    self._metrics = {
         | 
| 65 65 | 
             
                        "total_tools": 0,
         | 
| 66 66 | 
             
                        "invocations": {},  # Per-tool invocation counts
         | 
| 67 67 | 
             
                        "errors": {},  # Per-tool error counts
         | 
| 68 68 | 
             
                        "last_invocation": {},  # Per-tool last invocation time
         | 
| 69 | 
            -
                        "registration_time": {}  # Per-tool registration time
         | 
| 69 | 
            +
                        "registration_time": {},  # Per-tool registration time
         | 
| 70 70 | 
             
                    }
         | 
| 71 | 
            -
             | 
| 71 | 
            +
             | 
| 72 72 | 
             
                    # Cache for frequently used tools (LRU-style)
         | 
| 73 73 | 
             
                    self._cache_size = 10
         | 
| 74 74 | 
             
                    self._tool_cache: List[str] = []
         | 
| 75 | 
            -
             | 
| 75 | 
            +
             | 
| 76 76 | 
             
                async def _do_initialize(self) -> bool:
         | 
| 77 77 | 
             
                    """
         | 
| 78 78 | 
             
                    Initialize the tool registry.
         | 
| 79 | 
            -
             | 
| 79 | 
            +
             | 
| 80 80 | 
             
                    Returns:
         | 
| 81 81 | 
             
                        True if initialization successful
         | 
| 82 82 | 
             
                    """
         | 
| 83 83 | 
             
                    try:
         | 
| 84 84 | 
             
                        self.log_info("Initializing tool registry")
         | 
| 85 | 
            -
             | 
| 85 | 
            +
             | 
| 86 86 | 
             
                        # Clear any existing data
         | 
| 87 87 | 
             
                        with self._lock:
         | 
| 88 88 | 
             
                            self._adapters.clear()
         | 
| @@ -90,18 +90,18 @@ class ToolRegistry(BaseMCPService, IMCPToolRegistry): | |
| 90 90 | 
             
                            for category in self._categories.values():
         | 
| 91 91 | 
             
                                category.clear()
         | 
| 92 92 | 
             
                            self._tool_cache.clear()
         | 
| 93 | 
            -
             | 
| 93 | 
            +
             | 
| 94 94 | 
             
                        self.log_info("Tool registry initialized")
         | 
| 95 95 | 
             
                        return True
         | 
| 96 | 
            -
             | 
| 96 | 
            +
             | 
| 97 97 | 
             
                    except Exception as e:
         | 
| 98 98 | 
             
                        self.log_error(f"Failed to initialize tool registry: {e}")
         | 
| 99 99 | 
             
                        return False
         | 
| 100 | 
            -
             | 
| 100 | 
            +
             | 
| 101 101 | 
             
                async def _do_shutdown(self) -> None:
         | 
| 102 102 | 
             
                    """Shutdown the tool registry and clean up resources."""
         | 
| 103 103 | 
             
                    self.log_info("Shutting down tool registry")
         | 
| 104 | 
            -
             | 
| 104 | 
            +
             | 
| 105 105 | 
             
                    # Shutdown all tool adapters
         | 
| 106 106 | 
             
                    with self._lock:
         | 
| 107 107 | 
             
                        for tool_name, adapter in self._adapters.items():
         | 
| @@ -110,27 +110,27 @@ class ToolRegistry(BaseMCPService, IMCPToolRegistry): | |
| 110 110 | 
             
                                await adapter.shutdown()
         | 
| 111 111 | 
             
                            except Exception as e:
         | 
| 112 112 | 
             
                                self.log_error(f"Error shutting down tool {tool_name}: {e}")
         | 
| 113 | 
            -
             | 
| 113 | 
            +
             | 
| 114 114 | 
             
                        # Clear all data
         | 
| 115 115 | 
             
                        self._adapters.clear()
         | 
| 116 116 | 
             
                        self._definitions.clear()
         | 
| 117 117 | 
             
                        for category in self._categories.values():
         | 
| 118 118 | 
             
                            category.clear()
         | 
| 119 119 | 
             
                        self._tool_cache.clear()
         | 
| 120 | 
            -
             | 
| 120 | 
            +
             | 
| 121 121 | 
             
                    self.log_info("Tool registry shutdown complete")
         | 
| 122 | 
            -
             | 
| 122 | 
            +
             | 
| 123 123 | 
             
                def register_tool(self, adapter: IMCPToolAdapter, category: str = "user") -> bool:
         | 
| 124 124 | 
             
                    """
         | 
| 125 125 | 
             
                    Register a tool adapter.
         | 
| 126 | 
            -
             | 
| 126 | 
            +
             | 
| 127 127 | 
             
                    Args:
         | 
| 128 128 | 
             
                        adapter: Tool adapter to register
         | 
| 129 129 | 
             
                        category: Tool category (system, user, builtin, external)
         | 
| 130 | 
            -
             | 
| 130 | 
            +
             | 
| 131 131 | 
             
                    Returns:
         | 
| 132 132 | 
             
                        True if registration successful
         | 
| 133 | 
            -
             | 
| 133 | 
            +
             | 
| 134 134 | 
             
                    WHY: We validate the adapter and its definition before registration
         | 
| 135 135 | 
             
                    to ensure only valid tools are added to the registry.
         | 
| 136 136 | 
             
                    """
         | 
| @@ -138,238 +138,242 @@ class ToolRegistry(BaseMCPService, IMCPToolRegistry): | |
| 138 138 | 
             
                        # Get tool definition
         | 
| 139 139 | 
             
                        definition = adapter.get_definition()
         | 
| 140 140 | 
             
                        tool_name = definition.name
         | 
| 141 | 
            -
             | 
| 141 | 
            +
             | 
| 142 142 | 
             
                        self.log_info(f"Registering tool: {tool_name} (category: {category})")
         | 
| 143 | 
            -
             | 
| 143 | 
            +
             | 
| 144 144 | 
             
                        with self._lock:
         | 
| 145 145 | 
             
                            # Check if tool already registered
         | 
| 146 146 | 
             
                            if tool_name in self._adapters:
         | 
| 147 147 | 
             
                                self.log_warning(f"Tool already registered: {tool_name}")
         | 
| 148 148 | 
             
                                return False
         | 
| 149 | 
            -
             | 
| 149 | 
            +
             | 
| 150 150 | 
             
                            # Validate category
         | 
| 151 151 | 
             
                            if category not in self._categories:
         | 
| 152 152 | 
             
                                self.log_warning(f"Invalid category: {category}, using 'user'")
         | 
| 153 153 | 
             
                                category = "user"
         | 
| 154 | 
            -
             | 
| 154 | 
            +
             | 
| 155 155 | 
             
                            # Register the tool
         | 
| 156 156 | 
             
                            self._adapters[tool_name] = adapter
         | 
| 157 157 | 
             
                            self._definitions[tool_name] = definition
         | 
| 158 158 | 
             
                            self._categories[category].add(tool_name)
         | 
| 159 | 
            -
             | 
| 159 | 
            +
             | 
| 160 160 | 
             
                            # Update metrics
         | 
| 161 161 | 
             
                            self._metrics["total_tools"] = len(self._adapters)
         | 
| 162 | 
            -
                            self._metrics["registration_time"][ | 
| 162 | 
            +
                            self._metrics["registration_time"][
         | 
| 163 | 
            +
                                tool_name
         | 
| 164 | 
            +
                            ] = datetime.now().isoformat()
         | 
| 163 165 | 
             
                            self._metrics["invocations"][tool_name] = 0
         | 
| 164 166 | 
             
                            self._metrics["errors"][tool_name] = 0
         | 
| 165 | 
            -
             | 
| 167 | 
            +
             | 
| 166 168 | 
             
                        self.log_info(f"Tool registered successfully: {tool_name}")
         | 
| 167 | 
            -
                        self.log_mcp_event( | 
| 168 | 
            -
             | 
| 169 | 
            +
                        self.log_mcp_event(
         | 
| 170 | 
            +
                            "tool_registered", {"tool": tool_name, "category": category}
         | 
| 171 | 
            +
                        )
         | 
| 172 | 
            +
             | 
| 169 173 | 
             
                        return True
         | 
| 170 | 
            -
             | 
| 174 | 
            +
             | 
| 171 175 | 
             
                    except Exception as e:
         | 
| 172 176 | 
             
                        self.log_error(f"Failed to register tool: {e}")
         | 
| 173 177 | 
             
                        self.log_error(f"Traceback: {traceback.format_exc()}")
         | 
| 174 178 | 
             
                        return False
         | 
| 175 | 
            -
             | 
| 179 | 
            +
             | 
| 176 180 | 
             
                def unregister_tool(self, tool_name: str) -> bool:
         | 
| 177 181 | 
             
                    """
         | 
| 178 182 | 
             
                    Unregister a tool by name.
         | 
| 179 | 
            -
             | 
| 183 | 
            +
             | 
| 180 184 | 
             
                    Args:
         | 
| 181 185 | 
             
                        tool_name: Name of tool to unregister
         | 
| 182 | 
            -
             | 
| 186 | 
            +
             | 
| 183 187 | 
             
                    Returns:
         | 
| 184 188 | 
             
                        True if unregistration successful
         | 
| 185 189 | 
             
                    """
         | 
| 186 190 | 
             
                    try:
         | 
| 187 191 | 
             
                        self.log_info(f"Unregistering tool: {tool_name}")
         | 
| 188 | 
            -
             | 
| 192 | 
            +
             | 
| 189 193 | 
             
                        with self._lock:
         | 
| 190 194 | 
             
                            # Check if tool exists
         | 
| 191 195 | 
             
                            if tool_name not in self._adapters:
         | 
| 192 196 | 
             
                                self.log_warning(f"Tool not found: {tool_name}")
         | 
| 193 197 | 
             
                                return False
         | 
| 194 | 
            -
             | 
| 198 | 
            +
             | 
| 195 199 | 
             
                            # Get the adapter for shutdown
         | 
| 196 200 | 
             
                            adapter = self._adapters[tool_name]
         | 
| 197 | 
            -
             | 
| 201 | 
            +
             | 
| 198 202 | 
             
                            # Remove from all storage
         | 
| 199 203 | 
             
                            del self._adapters[tool_name]
         | 
| 200 204 | 
             
                            del self._definitions[tool_name]
         | 
| 201 | 
            -
             | 
| 205 | 
            +
             | 
| 202 206 | 
             
                            # Remove from categories
         | 
| 203 207 | 
             
                            for category_tools in self._categories.values():
         | 
| 204 208 | 
             
                                category_tools.discard(tool_name)
         | 
| 205 | 
            -
             | 
| 209 | 
            +
             | 
| 206 210 | 
             
                            # Remove from cache
         | 
| 207 211 | 
             
                            if tool_name in self._tool_cache:
         | 
| 208 212 | 
             
                                self._tool_cache.remove(tool_name)
         | 
| 209 | 
            -
             | 
| 213 | 
            +
             | 
| 210 214 | 
             
                            # Update metrics
         | 
| 211 215 | 
             
                            self._metrics["total_tools"] = len(self._adapters)
         | 
| 212 | 
            -
             | 
| 216 | 
            +
             | 
| 213 217 | 
             
                        # Shutdown adapter (outside lock to avoid deadlock)
         | 
| 214 218 | 
             
                        try:
         | 
| 215 219 | 
             
                            asyncio.create_task(adapter.shutdown())
         | 
| 216 220 | 
             
                        except Exception as e:
         | 
| 217 221 | 
             
                            self.log_warning(f"Error shutting down tool adapter {tool_name}: {e}")
         | 
| 218 | 
            -
             | 
| 222 | 
            +
             | 
| 219 223 | 
             
                        self.log_info(f"Tool unregistered successfully: {tool_name}")
         | 
| 220 224 | 
             
                        self.log_mcp_event("tool_unregistered", {"tool": tool_name})
         | 
| 221 | 
            -
             | 
| 225 | 
            +
             | 
| 222 226 | 
             
                        return True
         | 
| 223 | 
            -
             | 
| 227 | 
            +
             | 
| 224 228 | 
             
                    except Exception as e:
         | 
| 225 229 | 
             
                        self.log_error(f"Failed to unregister tool {tool_name}: {e}")
         | 
| 226 230 | 
             
                        return False
         | 
| 227 | 
            -
             | 
| 231 | 
            +
             | 
| 228 232 | 
             
                def get_tool(self, tool_name: str) -> Optional[IMCPToolAdapter]:
         | 
| 229 233 | 
             
                    """
         | 
| 230 234 | 
             
                    Get a tool adapter by name.
         | 
| 231 | 
            -
             | 
| 235 | 
            +
             | 
| 232 236 | 
             
                    Args:
         | 
| 233 237 | 
             
                        tool_name: Name of the tool
         | 
| 234 | 
            -
             | 
| 238 | 
            +
             | 
| 235 239 | 
             
                    Returns:
         | 
| 236 240 | 
             
                        Tool adapter if found, None otherwise
         | 
| 237 241 | 
             
                    """
         | 
| 238 242 | 
             
                    with self._lock:
         | 
| 239 243 | 
             
                        adapter = self._adapters.get(tool_name)
         | 
| 240 | 
            -
             | 
| 244 | 
            +
             | 
| 241 245 | 
             
                        # Update cache if tool found
         | 
| 242 246 | 
             
                        if adapter and tool_name not in self._tool_cache:
         | 
| 243 247 | 
             
                            self._update_cache(tool_name)
         | 
| 244 | 
            -
             | 
| 248 | 
            +
             | 
| 245 249 | 
             
                        return adapter
         | 
| 246 | 
            -
             | 
| 250 | 
            +
             | 
| 247 251 | 
             
                def list_tools(self) -> List[MCPToolDefinition]:
         | 
| 248 252 | 
             
                    """
         | 
| 249 253 | 
             
                    List all registered tools.
         | 
| 250 | 
            -
             | 
| 254 | 
            +
             | 
| 251 255 | 
             
                    Returns:
         | 
| 252 256 | 
             
                        List of tool definitions
         | 
| 253 257 | 
             
                    """
         | 
| 254 258 | 
             
                    with self._lock:
         | 
| 255 259 | 
             
                        return list(self._definitions.values())
         | 
| 256 | 
            -
             | 
| 260 | 
            +
             | 
| 257 261 | 
             
                async def invoke_tool(self, invocation: MCPToolInvocation) -> MCPToolResult:
         | 
| 258 262 | 
             
                    """
         | 
| 259 263 | 
             
                    Invoke a tool through the registry.
         | 
| 260 | 
            -
             | 
| 264 | 
            +
             | 
| 261 265 | 
             
                    Args:
         | 
| 262 266 | 
             
                        invocation: Tool invocation request
         | 
| 263 | 
            -
             | 
| 267 | 
            +
             | 
| 264 268 | 
             
                    Returns:
         | 
| 265 269 | 
             
                        Tool execution result
         | 
| 266 | 
            -
             | 
| 270 | 
            +
             | 
| 267 271 | 
             
                    WHY: We handle invocation through the registry to provide centralized
         | 
| 268 272 | 
             
                    error handling, metrics tracking, and validation.
         | 
| 269 273 | 
             
                    """
         | 
| 270 274 | 
             
                    tool_name = invocation.tool_name
         | 
| 271 275 | 
             
                    start_time = datetime.now()
         | 
| 272 | 
            -
             | 
| 276 | 
            +
             | 
| 273 277 | 
             
                    try:
         | 
| 274 278 | 
             
                        self.log_info(f"Invoking tool: {tool_name}")
         | 
| 275 | 
            -
             | 
| 279 | 
            +
             | 
| 276 280 | 
             
                        # Get the adapter
         | 
| 277 281 | 
             
                        adapter = self.get_tool(tool_name)
         | 
| 278 282 | 
             
                        if not adapter:
         | 
| 279 283 | 
             
                            error_msg = f"Tool not found: {tool_name}"
         | 
| 280 284 | 
             
                            self.log_error(error_msg)
         | 
| 281 | 
            -
                            return MCPToolResult(
         | 
| 282 | 
            -
             | 
| 283 | 
            -
                                error=error_msg
         | 
| 284 | 
            -
                            )
         | 
| 285 | 
            -
                        
         | 
| 285 | 
            +
                            return MCPToolResult(success=False, error=error_msg)
         | 
| 286 | 
            +
             | 
| 286 287 | 
             
                        # Validate parameters
         | 
| 287 288 | 
             
                        if not adapter.validate_parameters(invocation.parameters):
         | 
| 288 289 | 
             
                            error_msg = f"Invalid parameters for tool {tool_name}"
         | 
| 289 290 | 
             
                            self.log_error(error_msg)
         | 
| 290 | 
            -
             | 
| 291 | 
            +
             | 
| 291 292 | 
             
                            with self._lock:
         | 
| 292 | 
            -
                                self._metrics["errors"][tool_name] =  | 
| 293 | 
            -
             | 
| 294 | 
            -
             | 
| 295 | 
            -
             | 
| 296 | 
            -
             | 
| 297 | 
            -
             | 
| 298 | 
            -
                        
         | 
| 293 | 
            +
                                self._metrics["errors"][tool_name] = (
         | 
| 294 | 
            +
                                    self._metrics["errors"].get(tool_name, 0) + 1
         | 
| 295 | 
            +
                                )
         | 
| 296 | 
            +
             | 
| 297 | 
            +
                            return MCPToolResult(success=False, error=error_msg)
         | 
| 298 | 
            +
             | 
| 299 299 | 
             
                        # Invoke the tool
         | 
| 300 300 | 
             
                        result = await adapter.invoke(invocation)
         | 
| 301 | 
            -
             | 
| 301 | 
            +
             | 
| 302 302 | 
             
                        # Calculate execution time
         | 
| 303 303 | 
             
                        execution_time = (datetime.now() - start_time).total_seconds()
         | 
| 304 304 | 
             
                        result.execution_time = execution_time
         | 
| 305 | 
            -
             | 
| 305 | 
            +
             | 
| 306 306 | 
             
                        # Update metrics
         | 
| 307 307 | 
             
                        with self._lock:
         | 
| 308 | 
            -
                            self._metrics["invocations"][tool_name] =  | 
| 308 | 
            +
                            self._metrics["invocations"][tool_name] = (
         | 
| 309 | 
            +
                                self._metrics["invocations"].get(tool_name, 0) + 1
         | 
| 310 | 
            +
                            )
         | 
| 309 311 | 
             
                            self._metrics["last_invocation"][tool_name] = datetime.now().isoformat()
         | 
| 310 | 
            -
             | 
| 312 | 
            +
             | 
| 311 313 | 
             
                            if not result.success:
         | 
| 312 | 
            -
                                self._metrics["errors"][tool_name] =  | 
| 313 | 
            -
             | 
| 314 | 
            +
                                self._metrics["errors"][tool_name] = (
         | 
| 315 | 
            +
                                    self._metrics["errors"].get(tool_name, 0) + 1
         | 
| 316 | 
            +
                                )
         | 
| 317 | 
            +
             | 
| 314 318 | 
             
                        # Log the invocation
         | 
| 315 319 | 
             
                        self.log_tool_invocation(tool_name, result.success, execution_time)
         | 
| 316 | 
            -
             | 
| 320 | 
            +
             | 
| 317 321 | 
             
                        return result
         | 
| 318 | 
            -
             | 
| 322 | 
            +
             | 
| 319 323 | 
             
                    except Exception as e:
         | 
| 320 324 | 
             
                        error_msg = f"Exception invoking tool {tool_name}: {str(e)}"
         | 
| 321 325 | 
             
                        self.log_error(error_msg)
         | 
| 322 326 | 
             
                        self.log_error(f"Traceback: {traceback.format_exc()}")
         | 
| 323 | 
            -
             | 
| 327 | 
            +
             | 
| 324 328 | 
             
                        # Update error metrics
         | 
| 325 329 | 
             
                        with self._lock:
         | 
| 326 | 
            -
                            self._metrics["errors"][tool_name] =  | 
| 327 | 
            -
             | 
| 330 | 
            +
                            self._metrics["errors"][tool_name] = (
         | 
| 331 | 
            +
                                self._metrics["errors"].get(tool_name, 0) + 1
         | 
| 332 | 
            +
                            )
         | 
| 333 | 
            +
             | 
| 328 334 | 
             
                        execution_time = (datetime.now() - start_time).total_seconds()
         | 
| 329 | 
            -
             | 
| 335 | 
            +
             | 
| 330 336 | 
             
                        return MCPToolResult(
         | 
| 331 | 
            -
                            success=False,
         | 
| 332 | 
            -
                            error=error_msg,
         | 
| 333 | 
            -
                            execution_time=execution_time
         | 
| 337 | 
            +
                            success=False, error=error_msg, execution_time=execution_time
         | 
| 334 338 | 
             
                        )
         | 
| 335 | 
            -
             | 
| 339 | 
            +
             | 
| 336 340 | 
             
                def search_tools(self, query: str) -> List[MCPToolDefinition]:
         | 
| 337 341 | 
             
                    """
         | 
| 338 342 | 
             
                    Search for tools by query.
         | 
| 339 | 
            -
             | 
| 343 | 
            +
             | 
| 340 344 | 
             
                    Supports:
         | 
| 341 345 | 
             
                    - Exact name matching
         | 
| 342 346 | 
             
                    - Partial name matching
         | 
| 343 347 | 
             
                    - Description keyword matching
         | 
| 344 348 | 
             
                    - Regex patterns
         | 
| 345 | 
            -
             | 
| 349 | 
            +
             | 
| 346 350 | 
             
                    Args:
         | 
| 347 351 | 
             
                        query: Search query
         | 
| 348 | 
            -
             | 
| 352 | 
            +
             | 
| 349 353 | 
             
                    Returns:
         | 
| 350 354 | 
             
                        List of matching tool definitions
         | 
| 351 355 | 
             
                    """
         | 
| 352 356 | 
             
                    try:
         | 
| 353 357 | 
             
                        query_lower = query.lower()
         | 
| 354 358 | 
             
                        matching_tools = []
         | 
| 355 | 
            -
             | 
| 359 | 
            +
             | 
| 356 360 | 
             
                        with self._lock:
         | 
| 357 361 | 
             
                            for name, definition in self._definitions.items():
         | 
| 358 362 | 
             
                                # Exact match
         | 
| 359 363 | 
             
                                if name.lower() == query_lower:
         | 
| 360 364 | 
             
                                    matching_tools.append(definition)
         | 
| 361 365 | 
             
                                    continue
         | 
| 362 | 
            -
             | 
| 366 | 
            +
             | 
| 363 367 | 
             
                                # Partial name match
         | 
| 364 368 | 
             
                                if query_lower in name.lower():
         | 
| 365 369 | 
             
                                    matching_tools.append(definition)
         | 
| 366 370 | 
             
                                    continue
         | 
| 367 | 
            -
             | 
| 371 | 
            +
             | 
| 368 372 | 
             
                                # Description match
         | 
| 369 373 | 
             
                                if query_lower in definition.description.lower():
         | 
| 370 374 | 
             
                                    matching_tools.append(definition)
         | 
| 371 375 | 
             
                                    continue
         | 
| 372 | 
            -
             | 
| 376 | 
            +
             | 
| 373 377 | 
             
                                # Try regex match
         | 
| 374 378 | 
             
                                try:
         | 
| 375 379 | 
             
                                    if re.search(query, name, re.IGNORECASE):
         | 
| @@ -378,21 +382,23 @@ class ToolRegistry(BaseMCPService, IMCPToolRegistry): | |
| 378 382 | 
             
                                except re.error:
         | 
| 379 383 | 
             
                                    # Not a valid regex, skip
         | 
| 380 384 | 
             
                                    pass
         | 
| 381 | 
            -
             | 
| 382 | 
            -
                        self.log_info( | 
| 385 | 
            +
             | 
| 386 | 
            +
                        self.log_info(
         | 
| 387 | 
            +
                            f"Search query '{query}' returned {len(matching_tools)} tools"
         | 
| 388 | 
            +
                        )
         | 
| 383 389 | 
             
                        return matching_tools
         | 
| 384 | 
            -
             | 
| 390 | 
            +
             | 
| 385 391 | 
             
                    except Exception as e:
         | 
| 386 392 | 
             
                        self.log_error(f"Error searching tools: {e}")
         | 
| 387 393 | 
             
                        return []
         | 
| 388 | 
            -
             | 
| 394 | 
            +
             | 
| 389 395 | 
             
                def get_tools_by_category(self, category: str) -> List[MCPToolDefinition]:
         | 
| 390 396 | 
             
                    """
         | 
| 391 397 | 
             
                    Get all tools in a specific category.
         | 
| 392 | 
            -
             | 
| 398 | 
            +
             | 
| 393 399 | 
             
                    Args:
         | 
| 394 400 | 
             
                        category: Category name (system, user, builtin, external)
         | 
| 395 | 
            -
             | 
| 401 | 
            +
             | 
| 396 402 | 
             
                    Returns:
         | 
| 397 403 | 
             
                        List of tool definitions in the category
         | 
| 398 404 | 
             
                    """
         | 
| @@ -400,32 +406,36 @@ class ToolRegistry(BaseMCPService, IMCPToolRegistry): | |
| 400 406 | 
             
                        if category not in self._categories:
         | 
| 401 407 | 
             
                            self.log_warning(f"Invalid category: {category}")
         | 
| 402 408 | 
             
                            return []
         | 
| 403 | 
            -
             | 
| 409 | 
            +
             | 
| 404 410 | 
             
                        tool_names = self._categories[category]
         | 
| 405 | 
            -
                        return [ | 
| 406 | 
            -
             | 
| 411 | 
            +
                        return [
         | 
| 412 | 
            +
                            self._definitions[name]
         | 
| 413 | 
            +
                            for name in tool_names
         | 
| 414 | 
            +
                            if name in self._definitions
         | 
| 415 | 
            +
                        ]
         | 
| 416 | 
            +
             | 
| 407 417 | 
             
                def _update_cache(self, tool_name: str) -> None:
         | 
| 408 418 | 
             
                    """
         | 
| 409 419 | 
             
                    Update the tool cache (LRU-style).
         | 
| 410 | 
            -
             | 
| 420 | 
            +
             | 
| 411 421 | 
             
                    Args:
         | 
| 412 422 | 
             
                        tool_name: Name of tool to add to cache
         | 
| 413 423 | 
             
                    """
         | 
| 414 424 | 
             
                    # Remove if already in cache
         | 
| 415 425 | 
             
                    if tool_name in self._tool_cache:
         | 
| 416 426 | 
             
                        self._tool_cache.remove(tool_name)
         | 
| 417 | 
            -
             | 
| 427 | 
            +
             | 
| 418 428 | 
             
                    # Add to front
         | 
| 419 429 | 
             
                    self._tool_cache.insert(0, tool_name)
         | 
| 420 | 
            -
             | 
| 430 | 
            +
             | 
| 421 431 | 
             
                    # Trim cache if needed
         | 
| 422 432 | 
             
                    if len(self._tool_cache) > self._cache_size:
         | 
| 423 | 
            -
                        self._tool_cache = self._tool_cache[:self._cache_size]
         | 
| 424 | 
            -
             | 
| 433 | 
            +
                        self._tool_cache = self._tool_cache[: self._cache_size]
         | 
| 434 | 
            +
             | 
| 425 435 | 
             
                def get_metrics(self) -> Dict[str, Any]:
         | 
| 426 436 | 
             
                    """
         | 
| 427 437 | 
             
                    Get registry metrics.
         | 
| 428 | 
            -
             | 
| 438 | 
            +
             | 
| 429 439 | 
             
                    Returns:
         | 
| 430 440 | 
             
                        Metrics dictionary
         | 
| 431 441 | 
             
                    """
         | 
| @@ -433,12 +443,11 @@ class ToolRegistry(BaseMCPService, IMCPToolRegistry): | |
| 433 443 | 
             
                        return {
         | 
| 434 444 | 
             
                            **self._metrics,
         | 
| 435 445 | 
             
                            "categories": {
         | 
| 436 | 
            -
                                category: len(tools) 
         | 
| 437 | 
            -
                                for category, tools in self._categories.items()
         | 
| 446 | 
            +
                                category: len(tools) for category, tools in self._categories.items()
         | 
| 438 447 | 
             
                            },
         | 
| 439 | 
            -
                            "cached_tools": list(self._tool_cache)
         | 
| 448 | 
            +
                            "cached_tools": list(self._tool_cache),
         | 
| 440 449 | 
             
                        }
         | 
| 441 | 
            -
             | 
| 450 | 
            +
             | 
| 442 451 | 
             
                def clear_metrics(self) -> None:
         | 
| 443 452 | 
             
                    """Clear all metrics except registration data."""
         | 
| 444 453 | 
             
                    with self._lock:
         | 
| @@ -446,32 +455,32 @@ class ToolRegistry(BaseMCPService, IMCPToolRegistry): | |
| 446 455 | 
             
                            self._metrics["invocations"][tool_name] = 0
         | 
| 447 456 | 
             
                            self._metrics["errors"][tool_name] = 0
         | 
| 448 457 | 
             
                        self._metrics["last_invocation"].clear()
         | 
| 449 | 
            -
             | 
| 458 | 
            +
             | 
| 450 459 | 
             
                async def initialize_all_tools(self) -> Dict[str, bool]:
         | 
| 451 460 | 
             
                    """
         | 
| 452 461 | 
             
                    Initialize all registered tool adapters.
         | 
| 453 | 
            -
             | 
| 462 | 
            +
             | 
| 454 463 | 
             
                    Returns:
         | 
| 455 464 | 
             
                        Dictionary mapping tool names to initialization success
         | 
| 456 465 | 
             
                    """
         | 
| 457 466 | 
             
                    results = {}
         | 
| 458 | 
            -
             | 
| 467 | 
            +
             | 
| 459 468 | 
             
                    with self._lock:
         | 
| 460 469 | 
             
                        adapters_copy = dict(self._adapters)
         | 
| 461 | 
            -
             | 
| 470 | 
            +
             | 
| 462 471 | 
             
                    for tool_name, adapter in adapters_copy.items():
         | 
| 463 472 | 
             
                        try:
         | 
| 464 473 | 
             
                            self.log_info(f"Initializing tool: {tool_name}")
         | 
| 465 474 | 
             
                            success = await adapter.initialize()
         | 
| 466 475 | 
             
                            results[tool_name] = success
         | 
| 467 | 
            -
             | 
| 476 | 
            +
             | 
| 468 477 | 
             
                            if success:
         | 
| 469 478 | 
             
                                self.log_info(f"Tool initialized successfully: {tool_name}")
         | 
| 470 479 | 
             
                            else:
         | 
| 471 480 | 
             
                                self.log_warning(f"Tool initialization failed: {tool_name}")
         | 
| 472 | 
            -
             | 
| 481 | 
            +
             | 
| 473 482 | 
             
                        except Exception as e:
         | 
| 474 483 | 
             
                            self.log_error(f"Exception initializing tool {tool_name}: {e}")
         | 
| 475 484 | 
             
                            results[tool_name] = False
         | 
| 476 | 
            -
             | 
| 477 | 
            -
                    return results
         | 
| 485 | 
            +
             | 
| 486 | 
            +
                    return results
         | 
| @@ -5,11 +5,11 @@ MCP Gateway Server Module | |
| 5 5 | 
             
            Server components for the MCP Gateway service.
         | 
| 6 6 | 
             
            """
         | 
| 7 7 |  | 
| 8 | 
            -
            from . | 
| 9 | 
            -
            from .stdio_handler import  | 
| 8 | 
            +
            from .mcp_gateway import MCPGateway
         | 
| 9 | 
            +
            from .stdio_handler import AlternativeStdioHandler, StdioHandler
         | 
| 10 10 |  | 
| 11 11 | 
             
            __all__ = [
         | 
| 12 | 
            -
                " | 
| 12 | 
            +
                "MCPGateway",
         | 
| 13 13 | 
             
                "StdioHandler",
         | 
| 14 14 | 
             
                "AlternativeStdioHandler",
         | 
| 15 | 
            -
            ]
         | 
| 15 | 
            +
            ]
         |