claude-mpm 3.9.11__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.
Files changed (419) hide show
  1. claude_mpm/VERSION +1 -1
  2. claude_mpm/__init__.py +2 -2
  3. claude_mpm/__main__.py +3 -2
  4. claude_mpm/agents/__init__.py +85 -79
  5. claude_mpm/agents/agent_loader.py +464 -1003
  6. claude_mpm/agents/agent_loader_integration.py +45 -45
  7. claude_mpm/agents/agents_metadata.py +29 -30
  8. claude_mpm/agents/async_agent_loader.py +156 -138
  9. claude_mpm/agents/base_agent.json +1 -1
  10. claude_mpm/agents/base_agent_loader.py +179 -151
  11. claude_mpm/agents/frontmatter_validator.py +229 -130
  12. claude_mpm/agents/schema/agent_schema.json +1 -1
  13. claude_mpm/agents/system_agent_config.py +213 -147
  14. claude_mpm/agents/templates/__init__.py +13 -13
  15. claude_mpm/agents/templates/code_analyzer.json +2 -2
  16. claude_mpm/agents/templates/data_engineer.json +1 -1
  17. claude_mpm/agents/templates/documentation.json +23 -11
  18. claude_mpm/agents/templates/engineer.json +22 -6
  19. claude_mpm/agents/templates/memory_manager.json +1 -1
  20. claude_mpm/agents/templates/ops.json +2 -2
  21. claude_mpm/agents/templates/project_organizer.json +1 -1
  22. claude_mpm/agents/templates/qa.json +1 -1
  23. claude_mpm/agents/templates/refactoring_engineer.json +222 -0
  24. claude_mpm/agents/templates/research.json +20 -14
  25. claude_mpm/agents/templates/security.json +1 -1
  26. claude_mpm/agents/templates/ticketing.json +1 -1
  27. claude_mpm/agents/templates/version_control.json +1 -1
  28. claude_mpm/agents/templates/web_qa.json +3 -1
  29. claude_mpm/agents/templates/web_ui.json +2 -2
  30. claude_mpm/cli/__init__.py +79 -51
  31. claude_mpm/cli/__main__.py +3 -2
  32. claude_mpm/cli/commands/__init__.py +20 -20
  33. claude_mpm/cli/commands/agents.py +279 -247
  34. claude_mpm/cli/commands/aggregate.py +138 -157
  35. claude_mpm/cli/commands/cleanup.py +147 -147
  36. claude_mpm/cli/commands/config.py +93 -76
  37. claude_mpm/cli/commands/info.py +17 -16
  38. claude_mpm/cli/commands/mcp.py +140 -905
  39. claude_mpm/cli/commands/mcp_command_router.py +139 -0
  40. claude_mpm/cli/commands/mcp_config_commands.py +20 -0
  41. claude_mpm/cli/commands/mcp_install_commands.py +20 -0
  42. claude_mpm/cli/commands/mcp_server_commands.py +175 -0
  43. claude_mpm/cli/commands/mcp_tool_commands.py +34 -0
  44. claude_mpm/cli/commands/memory.py +239 -203
  45. claude_mpm/cli/commands/monitor.py +203 -81
  46. claude_mpm/cli/commands/run.py +380 -429
  47. claude_mpm/cli/commands/run_config_checker.py +160 -0
  48. claude_mpm/cli/commands/socketio_monitor.py +235 -0
  49. claude_mpm/cli/commands/tickets.py +305 -197
  50. claude_mpm/cli/parser.py +24 -1156
  51. claude_mpm/cli/parsers/__init__.py +29 -0
  52. claude_mpm/cli/parsers/agents_parser.py +136 -0
  53. claude_mpm/cli/parsers/base_parser.py +331 -0
  54. claude_mpm/cli/parsers/config_parser.py +85 -0
  55. claude_mpm/cli/parsers/mcp_parser.py +152 -0
  56. claude_mpm/cli/parsers/memory_parser.py +138 -0
  57. claude_mpm/cli/parsers/monitor_parser.py +104 -0
  58. claude_mpm/cli/parsers/run_parser.py +147 -0
  59. claude_mpm/cli/parsers/tickets_parser.py +203 -0
  60. claude_mpm/cli/ticket_cli.py +7 -3
  61. claude_mpm/cli/utils.py +55 -37
  62. claude_mpm/cli_module/__init__.py +6 -6
  63. claude_mpm/cli_module/args.py +188 -140
  64. claude_mpm/cli_module/commands.py +79 -70
  65. claude_mpm/cli_module/migration_example.py +38 -60
  66. claude_mpm/config/__init__.py +32 -25
  67. claude_mpm/config/agent_config.py +151 -119
  68. claude_mpm/config/experimental_features.py +71 -73
  69. claude_mpm/config/paths.py +94 -208
  70. claude_mpm/config/socketio_config.py +84 -73
  71. claude_mpm/constants.py +35 -18
  72. claude_mpm/core/__init__.py +9 -6
  73. claude_mpm/core/agent_name_normalizer.py +68 -71
  74. claude_mpm/core/agent_registry.py +372 -521
  75. claude_mpm/core/agent_session_manager.py +74 -63
  76. claude_mpm/core/base_service.py +116 -87
  77. claude_mpm/core/cache.py +119 -153
  78. claude_mpm/core/claude_runner.py +425 -1120
  79. claude_mpm/core/config.py +263 -168
  80. claude_mpm/core/config_aliases.py +69 -61
  81. claude_mpm/core/config_constants.py +292 -0
  82. claude_mpm/core/constants.py +57 -99
  83. claude_mpm/core/container.py +211 -178
  84. claude_mpm/core/exceptions.py +233 -89
  85. claude_mpm/core/factories.py +92 -54
  86. claude_mpm/core/framework_loader.py +378 -220
  87. claude_mpm/core/hook_manager.py +198 -83
  88. claude_mpm/core/hook_performance_config.py +136 -0
  89. claude_mpm/core/injectable_service.py +61 -55
  90. claude_mpm/core/interactive_session.py +165 -155
  91. claude_mpm/core/interfaces.py +221 -195
  92. claude_mpm/core/lazy.py +96 -96
  93. claude_mpm/core/logger.py +133 -107
  94. claude_mpm/core/logging_config.py +185 -157
  95. claude_mpm/core/minimal_framework_loader.py +20 -15
  96. claude_mpm/core/mixins.py +30 -29
  97. claude_mpm/core/oneshot_session.py +215 -181
  98. claude_mpm/core/optimized_agent_loader.py +134 -138
  99. claude_mpm/core/optimized_startup.py +159 -157
  100. claude_mpm/core/pm_hook_interceptor.py +85 -72
  101. claude_mpm/core/service_registry.py +103 -101
  102. claude_mpm/core/session_manager.py +97 -87
  103. claude_mpm/core/socketio_pool.py +212 -158
  104. claude_mpm/core/tool_access_control.py +58 -51
  105. claude_mpm/core/types.py +46 -24
  106. claude_mpm/core/typing_utils.py +166 -82
  107. claude_mpm/core/unified_agent_registry.py +721 -0
  108. claude_mpm/core/unified_config.py +550 -0
  109. claude_mpm/core/unified_paths.py +549 -0
  110. claude_mpm/dashboard/index.html +1 -1
  111. claude_mpm/dashboard/open_dashboard.py +51 -17
  112. claude_mpm/dashboard/static/css/dashboard.css +27 -8
  113. claude_mpm/dashboard/static/dist/components/agent-inference.js +2 -0
  114. claude_mpm/dashboard/static/dist/components/event-processor.js +2 -0
  115. claude_mpm/dashboard/static/dist/components/event-viewer.js +2 -0
  116. claude_mpm/dashboard/static/dist/components/export-manager.js +2 -0
  117. claude_mpm/dashboard/static/dist/components/file-tool-tracker.js +2 -0
  118. claude_mpm/dashboard/static/dist/components/hud-library-loader.js +2 -0
  119. claude_mpm/dashboard/static/dist/components/hud-manager.js +2 -0
  120. claude_mpm/dashboard/static/dist/components/hud-visualizer.js +2 -0
  121. claude_mpm/dashboard/static/dist/components/module-viewer.js +2 -0
  122. claude_mpm/dashboard/static/dist/components/session-manager.js +2 -0
  123. claude_mpm/dashboard/static/dist/components/socket-manager.js +2 -0
  124. claude_mpm/dashboard/static/dist/components/ui-state-manager.js +2 -0
  125. claude_mpm/dashboard/static/dist/components/working-directory.js +2 -0
  126. claude_mpm/dashboard/static/dist/dashboard.js +2 -0
  127. claude_mpm/dashboard/static/dist/socket-client.js +2 -0
  128. claude_mpm/dashboard/static/js/components/agent-inference.js +80 -76
  129. claude_mpm/dashboard/static/js/components/event-processor.js +71 -67
  130. claude_mpm/dashboard/static/js/components/event-viewer.js +74 -70
  131. claude_mpm/dashboard/static/js/components/export-manager.js +31 -28
  132. claude_mpm/dashboard/static/js/components/file-tool-tracker.js +106 -92
  133. claude_mpm/dashboard/static/js/components/hud-library-loader.js +11 -11
  134. claude_mpm/dashboard/static/js/components/hud-manager.js +73 -73
  135. claude_mpm/dashboard/static/js/components/hud-visualizer.js +163 -163
  136. claude_mpm/dashboard/static/js/components/module-viewer.js +305 -233
  137. claude_mpm/dashboard/static/js/components/session-manager.js +32 -29
  138. claude_mpm/dashboard/static/js/components/socket-manager.js +27 -20
  139. claude_mpm/dashboard/static/js/components/ui-state-manager.js +21 -18
  140. claude_mpm/dashboard/static/js/components/working-directory.js +74 -71
  141. claude_mpm/dashboard/static/js/dashboard.js +178 -453
  142. claude_mpm/dashboard/static/js/extension-error-handler.js +164 -0
  143. claude_mpm/dashboard/static/js/socket-client.js +120 -54
  144. claude_mpm/dashboard/templates/index.html +40 -50
  145. claude_mpm/experimental/cli_enhancements.py +60 -58
  146. claude_mpm/generators/__init__.py +1 -1
  147. claude_mpm/generators/agent_profile_generator.py +75 -65
  148. claude_mpm/hooks/__init__.py +1 -1
  149. claude_mpm/hooks/base_hook.py +33 -28
  150. claude_mpm/hooks/claude_hooks/__init__.py +1 -1
  151. claude_mpm/hooks/claude_hooks/connection_pool.py +120 -0
  152. claude_mpm/hooks/claude_hooks/event_handlers.py +743 -0
  153. claude_mpm/hooks/claude_hooks/hook_handler.py +415 -1331
  154. claude_mpm/hooks/claude_hooks/hook_wrapper.sh +4 -4
  155. claude_mpm/hooks/claude_hooks/memory_integration.py +221 -0
  156. claude_mpm/hooks/claude_hooks/response_tracking.py +348 -0
  157. claude_mpm/hooks/claude_hooks/tool_analysis.py +230 -0
  158. claude_mpm/hooks/memory_integration_hook.py +140 -100
  159. claude_mpm/hooks/tool_call_interceptor.py +89 -76
  160. claude_mpm/hooks/validation_hooks.py +57 -49
  161. claude_mpm/init.py +145 -121
  162. claude_mpm/models/__init__.py +9 -9
  163. claude_mpm/models/agent_definition.py +33 -23
  164. claude_mpm/models/agent_session.py +228 -200
  165. claude_mpm/scripts/__init__.py +1 -1
  166. claude_mpm/scripts/socketio_daemon.py +192 -75
  167. claude_mpm/scripts/socketio_server_manager.py +328 -0
  168. claude_mpm/scripts/start_activity_logging.py +25 -22
  169. claude_mpm/services/__init__.py +68 -43
  170. claude_mpm/services/agent_capabilities_service.py +271 -0
  171. claude_mpm/services/agents/__init__.py +23 -32
  172. claude_mpm/services/agents/deployment/__init__.py +3 -3
  173. claude_mpm/services/agents/deployment/agent_config_provider.py +310 -0
  174. claude_mpm/services/agents/deployment/agent_configuration_manager.py +359 -0
  175. claude_mpm/services/agents/deployment/agent_definition_factory.py +84 -0
  176. claude_mpm/services/agents/deployment/agent_deployment.py +415 -2113
  177. claude_mpm/services/agents/deployment/agent_discovery_service.py +387 -0
  178. claude_mpm/services/agents/deployment/agent_environment_manager.py +293 -0
  179. claude_mpm/services/agents/deployment/agent_filesystem_manager.py +387 -0
  180. claude_mpm/services/agents/deployment/agent_format_converter.py +453 -0
  181. claude_mpm/services/agents/deployment/agent_frontmatter_validator.py +161 -0
  182. claude_mpm/services/agents/deployment/agent_lifecycle_manager.py +345 -495
  183. claude_mpm/services/agents/deployment/agent_metrics_collector.py +279 -0
  184. claude_mpm/services/agents/deployment/agent_restore_handler.py +88 -0
  185. claude_mpm/services/agents/deployment/agent_template_builder.py +406 -0
  186. claude_mpm/services/agents/deployment/agent_validator.py +352 -0
  187. claude_mpm/services/agents/deployment/agent_version_manager.py +313 -0
  188. claude_mpm/services/agents/deployment/agent_versioning.py +6 -9
  189. claude_mpm/services/agents/deployment/agents_directory_resolver.py +79 -0
  190. claude_mpm/services/agents/deployment/async_agent_deployment.py +298 -234
  191. claude_mpm/services/agents/deployment/config/__init__.py +13 -0
  192. claude_mpm/services/agents/deployment/config/deployment_config.py +182 -0
  193. claude_mpm/services/agents/deployment/config/deployment_config_manager.py +200 -0
  194. claude_mpm/services/agents/deployment/deployment_config_loader.py +54 -0
  195. claude_mpm/services/agents/deployment/deployment_type_detector.py +124 -0
  196. claude_mpm/services/agents/deployment/facade/__init__.py +18 -0
  197. claude_mpm/services/agents/deployment/facade/async_deployment_executor.py +159 -0
  198. claude_mpm/services/agents/deployment/facade/deployment_executor.py +73 -0
  199. claude_mpm/services/agents/deployment/facade/deployment_facade.py +270 -0
  200. claude_mpm/services/agents/deployment/facade/sync_deployment_executor.py +178 -0
  201. claude_mpm/services/agents/deployment/interface_adapter.py +227 -0
  202. claude_mpm/services/agents/deployment/lifecycle_health_checker.py +85 -0
  203. claude_mpm/services/agents/deployment/lifecycle_performance_tracker.py +100 -0
  204. claude_mpm/services/agents/deployment/pipeline/__init__.py +32 -0
  205. claude_mpm/services/agents/deployment/pipeline/pipeline_builder.py +158 -0
  206. claude_mpm/services/agents/deployment/pipeline/pipeline_context.py +159 -0
  207. claude_mpm/services/agents/deployment/pipeline/pipeline_executor.py +169 -0
  208. claude_mpm/services/agents/deployment/pipeline/steps/__init__.py +19 -0
  209. claude_mpm/services/agents/deployment/pipeline/steps/agent_processing_step.py +195 -0
  210. claude_mpm/services/agents/deployment/pipeline/steps/base_step.py +119 -0
  211. claude_mpm/services/agents/deployment/pipeline/steps/configuration_step.py +79 -0
  212. claude_mpm/services/agents/deployment/pipeline/steps/target_directory_step.py +90 -0
  213. claude_mpm/services/agents/deployment/pipeline/steps/validation_step.py +100 -0
  214. claude_mpm/services/agents/deployment/processors/__init__.py +15 -0
  215. claude_mpm/services/agents/deployment/processors/agent_deployment_context.py +98 -0
  216. claude_mpm/services/agents/deployment/processors/agent_deployment_result.py +235 -0
  217. claude_mpm/services/agents/deployment/processors/agent_processor.py +258 -0
  218. claude_mpm/services/agents/deployment/refactored_agent_deployment_service.py +318 -0
  219. claude_mpm/services/agents/deployment/results/__init__.py +13 -0
  220. claude_mpm/services/agents/deployment/results/deployment_metrics.py +200 -0
  221. claude_mpm/services/agents/deployment/results/deployment_result_builder.py +249 -0
  222. claude_mpm/services/agents/deployment/strategies/__init__.py +25 -0
  223. claude_mpm/services/agents/deployment/strategies/base_strategy.py +119 -0
  224. claude_mpm/services/agents/deployment/strategies/project_strategy.py +150 -0
  225. claude_mpm/services/agents/deployment/strategies/strategy_selector.py +117 -0
  226. claude_mpm/services/agents/deployment/strategies/system_strategy.py +116 -0
  227. claude_mpm/services/agents/deployment/strategies/user_strategy.py +137 -0
  228. claude_mpm/services/agents/deployment/system_instructions_deployer.py +108 -0
  229. claude_mpm/services/agents/deployment/validation/__init__.py +19 -0
  230. claude_mpm/services/agents/deployment/validation/agent_validator.py +323 -0
  231. claude_mpm/services/agents/deployment/validation/deployment_validator.py +238 -0
  232. claude_mpm/services/agents/deployment/validation/template_validator.py +299 -0
  233. claude_mpm/services/agents/deployment/validation/validation_result.py +226 -0
  234. claude_mpm/services/agents/loading/__init__.py +2 -2
  235. claude_mpm/services/agents/loading/agent_profile_loader.py +259 -229
  236. claude_mpm/services/agents/loading/base_agent_manager.py +90 -81
  237. claude_mpm/services/agents/loading/framework_agent_loader.py +154 -129
  238. claude_mpm/services/agents/management/__init__.py +2 -2
  239. claude_mpm/services/agents/management/agent_capabilities_generator.py +72 -58
  240. claude_mpm/services/agents/management/agent_management_service.py +209 -156
  241. claude_mpm/services/agents/memory/__init__.py +9 -6
  242. claude_mpm/services/agents/memory/agent_memory_manager.py +218 -1152
  243. claude_mpm/services/agents/memory/agent_persistence_service.py +20 -16
  244. claude_mpm/services/agents/memory/analyzer.py +430 -0
  245. claude_mpm/services/agents/memory/content_manager.py +376 -0
  246. claude_mpm/services/agents/memory/template_generator.py +468 -0
  247. claude_mpm/services/agents/registry/__init__.py +7 -10
  248. claude_mpm/services/agents/registry/deployed_agent_discovery.py +122 -97
  249. claude_mpm/services/agents/registry/modification_tracker.py +351 -285
  250. claude_mpm/services/async_session_logger.py +187 -153
  251. claude_mpm/services/claude_session_logger.py +87 -72
  252. claude_mpm/services/command_handler_service.py +217 -0
  253. claude_mpm/services/communication/__init__.py +3 -2
  254. claude_mpm/services/core/__init__.py +50 -97
  255. claude_mpm/services/core/base.py +60 -53
  256. claude_mpm/services/core/interfaces/__init__.py +188 -0
  257. claude_mpm/services/core/interfaces/agent.py +351 -0
  258. claude_mpm/services/core/interfaces/communication.py +343 -0
  259. claude_mpm/services/core/interfaces/infrastructure.py +413 -0
  260. claude_mpm/services/core/interfaces/service.py +434 -0
  261. claude_mpm/services/core/interfaces.py +19 -944
  262. claude_mpm/services/event_aggregator.py +208 -170
  263. claude_mpm/services/exceptions.py +387 -308
  264. claude_mpm/services/framework_claude_md_generator/__init__.py +75 -79
  265. claude_mpm/services/framework_claude_md_generator/content_assembler.py +69 -60
  266. claude_mpm/services/framework_claude_md_generator/content_validator.py +65 -61
  267. claude_mpm/services/framework_claude_md_generator/deployment_manager.py +68 -49
  268. claude_mpm/services/framework_claude_md_generator/section_generators/__init__.py +34 -34
  269. claude_mpm/services/framework_claude_md_generator/section_generators/agents.py +25 -22
  270. claude_mpm/services/framework_claude_md_generator/section_generators/claude_pm_init.py +10 -10
  271. claude_mpm/services/framework_claude_md_generator/section_generators/core_responsibilities.py +4 -3
  272. claude_mpm/services/framework_claude_md_generator/section_generators/delegation_constraints.py +4 -3
  273. claude_mpm/services/framework_claude_md_generator/section_generators/environment_config.py +4 -3
  274. claude_mpm/services/framework_claude_md_generator/section_generators/footer.py +6 -5
  275. claude_mpm/services/framework_claude_md_generator/section_generators/header.py +8 -7
  276. claude_mpm/services/framework_claude_md_generator/section_generators/orchestration_principles.py +4 -3
  277. claude_mpm/services/framework_claude_md_generator/section_generators/role_designation.py +6 -5
  278. claude_mpm/services/framework_claude_md_generator/section_generators/subprocess_validation.py +9 -8
  279. claude_mpm/services/framework_claude_md_generator/section_generators/todo_task_tools.py +4 -3
  280. claude_mpm/services/framework_claude_md_generator/section_generators/troubleshooting.py +5 -4
  281. claude_mpm/services/framework_claude_md_generator/section_manager.py +28 -27
  282. claude_mpm/services/framework_claude_md_generator/version_manager.py +30 -28
  283. claude_mpm/services/hook_service.py +106 -114
  284. claude_mpm/services/infrastructure/__init__.py +7 -5
  285. claude_mpm/services/infrastructure/context_preservation.py +233 -199
  286. claude_mpm/services/infrastructure/daemon_manager.py +279 -0
  287. claude_mpm/services/infrastructure/logging.py +83 -76
  288. claude_mpm/services/infrastructure/monitoring.py +547 -404
  289. claude_mpm/services/mcp_gateway/__init__.py +30 -13
  290. claude_mpm/services/mcp_gateway/config/__init__.py +2 -2
  291. claude_mpm/services/mcp_gateway/config/config_loader.py +61 -56
  292. claude_mpm/services/mcp_gateway/config/config_schema.py +50 -41
  293. claude_mpm/services/mcp_gateway/config/configuration.py +82 -75
  294. claude_mpm/services/mcp_gateway/core/__init__.py +13 -20
  295. claude_mpm/services/mcp_gateway/core/base.py +80 -67
  296. claude_mpm/services/mcp_gateway/core/exceptions.py +60 -46
  297. claude_mpm/services/mcp_gateway/core/interfaces.py +87 -84
  298. claude_mpm/services/mcp_gateway/main.py +287 -137
  299. claude_mpm/services/mcp_gateway/registry/__init__.py +1 -1
  300. claude_mpm/services/mcp_gateway/registry/service_registry.py +97 -94
  301. claude_mpm/services/mcp_gateway/registry/tool_registry.py +135 -126
  302. claude_mpm/services/mcp_gateway/server/__init__.py +2 -2
  303. claude_mpm/services/mcp_gateway/server/mcp_gateway.py +105 -110
  304. claude_mpm/services/mcp_gateway/server/stdio_handler.py +105 -107
  305. claude_mpm/services/mcp_gateway/server/stdio_server.py +691 -0
  306. claude_mpm/services/mcp_gateway/tools/__init__.py +4 -2
  307. claude_mpm/services/mcp_gateway/tools/base_adapter.py +109 -119
  308. claude_mpm/services/mcp_gateway/tools/document_summarizer.py +283 -215
  309. claude_mpm/services/mcp_gateway/tools/hello_world.py +122 -120
  310. claude_mpm/services/mcp_gateway/tools/ticket_tools.py +652 -0
  311. claude_mpm/services/mcp_gateway/tools/unified_ticket_tool.py +606 -0
  312. claude_mpm/services/memory/__init__.py +2 -2
  313. claude_mpm/services/memory/builder.py +451 -362
  314. claude_mpm/services/memory/cache/__init__.py +2 -2
  315. claude_mpm/services/memory/cache/shared_prompt_cache.py +232 -194
  316. claude_mpm/services/memory/cache/simple_cache.py +107 -93
  317. claude_mpm/services/memory/indexed_memory.py +195 -193
  318. claude_mpm/services/memory/optimizer.py +267 -234
  319. claude_mpm/services/memory/router.py +571 -263
  320. claude_mpm/services/memory_hook_service.py +237 -0
  321. claude_mpm/services/port_manager.py +223 -0
  322. claude_mpm/services/project/__init__.py +3 -3
  323. claude_mpm/services/project/analyzer.py +451 -305
  324. claude_mpm/services/project/registry.py +262 -240
  325. claude_mpm/services/recovery_manager.py +287 -231
  326. claude_mpm/services/response_tracker.py +87 -67
  327. claude_mpm/services/runner_configuration_service.py +587 -0
  328. claude_mpm/services/session_management_service.py +304 -0
  329. claude_mpm/services/socketio/__init__.py +4 -4
  330. claude_mpm/services/socketio/client_proxy.py +174 -0
  331. claude_mpm/services/socketio/handlers/__init__.py +3 -3
  332. claude_mpm/services/socketio/handlers/base.py +44 -30
  333. claude_mpm/services/socketio/handlers/connection.py +145 -65
  334. claude_mpm/services/socketio/handlers/file.py +123 -108
  335. claude_mpm/services/socketio/handlers/git.py +607 -373
  336. claude_mpm/services/socketio/handlers/hook.py +170 -0
  337. claude_mpm/services/socketio/handlers/memory.py +4 -4
  338. claude_mpm/services/socketio/handlers/project.py +4 -4
  339. claude_mpm/services/socketio/handlers/registry.py +53 -38
  340. claude_mpm/services/socketio/server/__init__.py +18 -0
  341. claude_mpm/services/socketio/server/broadcaster.py +252 -0
  342. claude_mpm/services/socketio/server/core.py +399 -0
  343. claude_mpm/services/socketio/server/main.py +323 -0
  344. claude_mpm/services/socketio_client_manager.py +160 -133
  345. claude_mpm/services/socketio_server.py +36 -1885
  346. claude_mpm/services/subprocess_launcher_service.py +316 -0
  347. claude_mpm/services/system_instructions_service.py +258 -0
  348. claude_mpm/services/ticket_manager.py +19 -533
  349. claude_mpm/services/utility_service.py +285 -0
  350. claude_mpm/services/version_control/__init__.py +18 -21
  351. claude_mpm/services/version_control/branch_strategy.py +20 -10
  352. claude_mpm/services/version_control/conflict_resolution.py +37 -13
  353. claude_mpm/services/version_control/git_operations.py +52 -21
  354. claude_mpm/services/version_control/semantic_versioning.py +92 -53
  355. claude_mpm/services/version_control/version_parser.py +145 -125
  356. claude_mpm/services/version_service.py +270 -0
  357. claude_mpm/storage/__init__.py +2 -2
  358. claude_mpm/storage/state_storage.py +177 -181
  359. claude_mpm/ticket_wrapper.py +2 -2
  360. claude_mpm/utils/__init__.py +2 -2
  361. claude_mpm/utils/agent_dependency_loader.py +453 -243
  362. claude_mpm/utils/config_manager.py +157 -118
  363. claude_mpm/utils/console.py +1 -1
  364. claude_mpm/utils/dependency_cache.py +102 -107
  365. claude_mpm/utils/dependency_manager.py +52 -47
  366. claude_mpm/utils/dependency_strategies.py +131 -96
  367. claude_mpm/utils/environment_context.py +110 -102
  368. claude_mpm/utils/error_handler.py +75 -55
  369. claude_mpm/utils/file_utils.py +80 -67
  370. claude_mpm/utils/framework_detection.py +12 -11
  371. claude_mpm/utils/import_migration_example.py +12 -60
  372. claude_mpm/utils/imports.py +48 -45
  373. claude_mpm/utils/path_operations.py +100 -93
  374. claude_mpm/utils/robust_installer.py +172 -164
  375. claude_mpm/utils/session_logging.py +30 -23
  376. claude_mpm/utils/subprocess_utils.py +99 -61
  377. claude_mpm/validation/__init__.py +1 -1
  378. claude_mpm/validation/agent_validator.py +151 -111
  379. claude_mpm/validation/frontmatter_validator.py +92 -71
  380. {claude_mpm-3.9.11.dist-info → claude_mpm-4.0.3.dist-info}/METADATA +27 -1
  381. claude_mpm-4.0.3.dist-info/RECORD +402 -0
  382. {claude_mpm-3.9.11.dist-info → claude_mpm-4.0.3.dist-info}/entry_points.txt +1 -0
  383. {claude_mpm-3.9.11.dist-info → claude_mpm-4.0.3.dist-info}/licenses/LICENSE +1 -1
  384. claude_mpm/cli/commands/run_guarded.py +0 -511
  385. claude_mpm/config/memory_guardian_config.py +0 -325
  386. claude_mpm/config/memory_guardian_yaml.py +0 -335
  387. claude_mpm/core/config_paths.py +0 -150
  388. claude_mpm/core/memory_aware_runner.py +0 -353
  389. claude_mpm/dashboard/static/js/dashboard-original.js +0 -4134
  390. claude_mpm/deployment_paths.py +0 -261
  391. claude_mpm/hooks/claude_hooks/hook_handler_fixed.py +0 -454
  392. claude_mpm/models/state_models.py +0 -433
  393. claude_mpm/services/agent/__init__.py +0 -24
  394. claude_mpm/services/agent/deployment.py +0 -2548
  395. claude_mpm/services/agent/management.py +0 -598
  396. claude_mpm/services/agent/registry.py +0 -813
  397. claude_mpm/services/agents/registry/agent_registry.py +0 -813
  398. claude_mpm/services/communication/socketio.py +0 -1935
  399. claude_mpm/services/communication/websocket.py +0 -479
  400. claude_mpm/services/framework_claude_md_generator.py +0 -624
  401. claude_mpm/services/health_monitor.py +0 -893
  402. claude_mpm/services/infrastructure/graceful_degradation.py +0 -616
  403. claude_mpm/services/infrastructure/health_monitor.py +0 -775
  404. claude_mpm/services/infrastructure/memory_dashboard.py +0 -479
  405. claude_mpm/services/infrastructure/memory_guardian.py +0 -944
  406. claude_mpm/services/infrastructure/restart_protection.py +0 -642
  407. claude_mpm/services/infrastructure/state_manager.py +0 -774
  408. claude_mpm/services/mcp_gateway/manager.py +0 -334
  409. claude_mpm/services/optimized_hook_service.py +0 -542
  410. claude_mpm/services/project_analyzer.py +0 -864
  411. claude_mpm/services/project_registry.py +0 -608
  412. claude_mpm/services/standalone_socketio_server.py +0 -1300
  413. claude_mpm/services/ticket_manager_di.py +0 -318
  414. claude_mpm/services/ticketing_service_original.py +0 -510
  415. claude_mpm/utils/paths.py +0 -395
  416. claude_mpm/utils/platform_memory.py +0 -524
  417. claude_mpm-3.9.11.dist-info/RECORD +0 -306
  418. {claude_mpm-3.9.11.dist-info → claude_mpm-4.0.3.dist-info}/WHEEL +0 -0
  419. {claude_mpm-3.9.11.dist-info → claude_mpm-4.0.3.dist-info}/top_level.txt +0 -0
@@ -1,137 +1,147 @@
1
+ from pathlib import Path
2
+
1
3
  """
2
4
  Agent profile generator using template system.
3
5
 
4
6
  Inspired by awesome-claude-code's template generation approach.
5
7
  """
6
8
 
7
- import yaml
8
- from pathlib import Path
9
- from datetime import datetime
10
- from typing import Dict, Any, Optional
11
9
  import re
10
+ from datetime import datetime
11
+ from typing import Any, Dict, Optional
12
+
13
+ import yaml
12
14
 
13
15
 
14
16
  class AgentProfileGenerator:
15
17
  """Generates agent profiles from templates."""
16
-
18
+
17
19
  def __init__(self, template_path: Optional[Path] = None):
18
20
  """Initialize the generator with a template path."""
19
- self.template_path = template_path or Path(__file__).parent.parent / "agents" / "agent-template.yaml"
21
+ self.template_path = (
22
+ template_path
23
+ or Path(__file__).parent.parent / "agents" / "agent-template.yaml"
24
+ )
20
25
  self.template = self._load_template()
21
-
26
+
22
27
  def _load_template(self) -> Dict[str, Any]:
23
28
  """Load the agent profile template."""
24
29
  if not self.template_path.exists():
25
30
  raise FileNotFoundError(f"Template not found: {self.template_path}")
26
-
27
- with open(self.template_path, 'r') as f:
31
+
32
+ with open(self.template_path, "r") as f:
28
33
  return yaml.safe_load(f)
29
-
34
+
30
35
  def generate_profile(self, config: Dict[str, Any]) -> str:
31
36
  """Generate an agent profile from configuration."""
32
37
  # Set default values
33
- config.setdefault('VERSION', '1.0.0')
34
- config.setdefault('CREATED_DATE', datetime.now().strftime('%Y-%m-%d'))
35
- config.setdefault('AUTHOR', 'claude-mpm')
36
-
38
+ config.setdefault("VERSION", "1.0.0")
39
+ config.setdefault("CREATED_DATE", datetime.now().strftime("%Y-%m-%d"))
40
+ config.setdefault("AUTHOR", "claude-mpm")
41
+
37
42
  # Convert template to string
38
43
  template_str = yaml.dump(self.template, default_flow_style=False)
39
-
44
+
40
45
  # Replace placeholders
41
46
  result = self._replace_placeholders(template_str, config)
42
-
47
+
43
48
  # Clean up any remaining placeholders
44
- result = re.sub(r'\{\{[^}]+\}\}', '', result)
45
-
49
+ result = re.sub(r"\{\{[^}]+\}\}", "", result)
50
+
46
51
  return result
47
-
52
+
48
53
  def _replace_placeholders(self, template: str, values: Dict[str, Any]) -> str:
49
54
  """Replace template placeholders with actual values."""
50
55
  for key, value in values.items():
51
56
  placeholder = f"{{{{{key}}}}}"
52
57
  if isinstance(value, list):
53
58
  # Format lists nicely
54
- formatted_list = '\n'.join(f" - \"{item}\"" for item in value)
59
+ formatted_list = "\n".join(f' - "{item}"' for item in value)
55
60
  template = template.replace(placeholder, formatted_list)
56
61
  else:
57
62
  template = template.replace(placeholder, str(value))
58
-
63
+
59
64
  return template
60
-
65
+
61
66
  def generate_agent_documentation(self, agent_config: Dict[str, Any]) -> str:
62
67
  """Generate markdown documentation for an agent."""
63
68
  doc_lines = []
64
-
69
+
65
70
  # Header
66
71
  doc_lines.append(f"# {agent_config.get('name', 'Agent')} Documentation")
67
72
  doc_lines.append("")
68
-
73
+
69
74
  # Description
70
- if 'description' in agent_config:
75
+ if "description" in agent_config:
71
76
  doc_lines.append("## Description")
72
- doc_lines.append(agent_config['description'])
77
+ doc_lines.append(agent_config["description"])
73
78
  doc_lines.append("")
74
-
79
+
75
80
  # Capabilities
76
- if 'capabilities' in agent_config:
81
+ if "capabilities" in agent_config:
77
82
  doc_lines.append("## Capabilities")
78
- for capability in agent_config['capabilities']:
83
+ for capability in agent_config["capabilities"]:
79
84
  doc_lines.append(f"- {capability}")
80
85
  doc_lines.append("")
81
-
86
+
82
87
  # Tools
83
- if 'tools' in agent_config:
88
+ if "tools" in agent_config:
84
89
  doc_lines.append("## Required Tools")
85
- for tool in agent_config['tools']:
90
+ for tool in agent_config["tools"]:
86
91
  if isinstance(tool, dict):
87
- doc_lines.append(f"- **{tool['name']}**: {tool.get('description', '')}")
92
+ doc_lines.append(
93
+ f"- **{tool['name']}**: {tool.get('description', '')}"
94
+ )
88
95
  else:
89
96
  doc_lines.append(f"- {tool}")
90
97
  doc_lines.append("")
91
-
98
+
92
99
  # Examples
93
- if 'examples' in agent_config:
100
+ if "examples" in agent_config:
94
101
  doc_lines.append("## Usage Examples")
95
- for i, example in enumerate(agent_config['examples'], 1):
96
- doc_lines.append(f"### Example {i}: {example.get('scenario', 'Scenario')}")
102
+ for i, example in enumerate(agent_config["examples"], 1):
103
+ doc_lines.append(
104
+ f"### Example {i}: {example.get('scenario', 'Scenario')}"
105
+ )
97
106
  doc_lines.append("```")
98
107
  doc_lines.append(f"Input: {example.get('input', '')}")
99
108
  doc_lines.append("```")
100
109
  doc_lines.append("Expected Output:")
101
110
  doc_lines.append("```")
102
- doc_lines.append(example.get('expected_output', ''))
111
+ doc_lines.append(example.get("expected_output", ""))
103
112
  doc_lines.append("```")
104
113
  doc_lines.append("")
105
-
114
+
106
115
  # Best Practices
107
- if 'best_practices' in agent_config:
116
+ if "best_practices" in agent_config:
108
117
  doc_lines.append("## Best Practices")
109
- for practice in agent_config['best_practices']:
118
+ for practice in agent_config["best_practices"]:
110
119
  doc_lines.append(f"- {practice}")
111
120
  doc_lines.append("")
112
-
113
- return '\n'.join(doc_lines)
114
-
115
- def create_agent_from_template(self, agent_name: str, role: str,
116
- category: str = "analysis") -> Dict[str, Any]:
121
+
122
+ return "\n".join(doc_lines)
123
+
124
+ def create_agent_from_template(
125
+ self, agent_name: str, role: str, category: str = "analysis"
126
+ ) -> Dict[str, Any]:
117
127
  """Create a new agent configuration from template."""
118
128
  return {
119
- 'AGENT_NAME': agent_name,
120
- 'AGENT_ID': agent_name.lower().replace(' ', '_'),
121
- 'ROLE': role,
122
- 'CATEGORY': category,
123
- 'DESCRIPTION': f"Agent profile for {agent_name}",
124
- 'AGENT_DESCRIPTION': f"Specialized {role} agent",
125
- 'SPECIALIZATION': role.lower(),
126
- 'CAPABILITIES_LIST': "- Analyze code structure\n- Identify patterns\n- Generate reports",
127
- 'CONSTRAINTS_LIST': "- Read-only operations\n- Respect file permissions",
128
- 'TOOL_NAME': 'code_analysis',
129
- 'TOOL_DESCRIPTION': 'Analyzes code structure and patterns',
130
- 'EXAMPLE_SCENARIO': 'Analyzing a Python project',
131
- 'EXAMPLE_INPUT': 'Analyze the architecture of this codebase',
132
- 'EXAMPLE_OUTPUT': 'Detailed analysis report with recommendations',
133
- 'BEST_PRACTICE_1': 'Always validate input parameters',
134
- 'BEST_PRACTICE_2': 'Provide clear, actionable insights',
135
- 'BEST_PRACTICE_3': 'Include examples in reports',
136
- 'ADDITIONAL_INSTRUCTIONS': 'Be thorough but concise in your analysis.'
137
- }
129
+ "AGENT_NAME": agent_name,
130
+ "AGENT_ID": agent_name.lower().replace(" ", "_"),
131
+ "ROLE": role,
132
+ "CATEGORY": category,
133
+ "DESCRIPTION": f"Agent profile for {agent_name}",
134
+ "AGENT_DESCRIPTION": f"Specialized {role} agent",
135
+ "SPECIALIZATION": role.lower(),
136
+ "CAPABILITIES_LIST": "- Analyze code structure\n- Identify patterns\n- Generate reports",
137
+ "CONSTRAINTS_LIST": "- Read-only operations\n- Respect file permissions",
138
+ "TOOL_NAME": "code_analysis",
139
+ "TOOL_DESCRIPTION": "Analyzes code structure and patterns",
140
+ "EXAMPLE_SCENARIO": "Analyzing a Python project",
141
+ "EXAMPLE_INPUT": "Analyze the architecture of this codebase",
142
+ "EXAMPLE_OUTPUT": "Detailed analysis report with recommendations",
143
+ "BEST_PRACTICE_1": "Always validate input parameters",
144
+ "BEST_PRACTICE_2": "Provide clear, actionable insights",
145
+ "BEST_PRACTICE_3": "Include examples in reports",
146
+ "ADDITIONAL_INSTRUCTIONS": "Be thorough but concise in your analysis.",
147
+ }
@@ -2,4 +2,4 @@
2
2
 
3
3
  from .base_hook import BaseHook, HookContext, HookResult, HookType
4
4
 
5
- __all__ = ["BaseHook", "HookContext", "HookResult", "HookType"]
5
+ __all__ = ["BaseHook", "HookContext", "HookResult", "HookType"]
@@ -1,18 +1,19 @@
1
1
  """Base hook class and types for claude-mpm hook system."""
2
2
 
3
+ import asyncio
4
+ import logging
3
5
  from abc import ABC, abstractmethod
4
6
  from dataclasses import dataclass
7
+ from datetime import datetime
5
8
  from enum import Enum
6
9
  from typing import Any, Dict, List, Optional, Union
7
- import asyncio
8
- import logging
9
- from datetime import datetime
10
10
 
11
11
  logger = logging.getLogger(__name__)
12
12
 
13
13
 
14
14
  class HookType(Enum):
15
15
  """Types of hooks available in the system."""
16
+
16
17
  SUBMIT = "submit" # Process user prompts
17
18
  PRE_DELEGATION = "pre_delegation" # Filter context before delegation
18
19
  POST_DELEGATION = "post_delegation" # Process results after delegation
@@ -23,22 +24,24 @@ class HookType(Enum):
23
24
  @dataclass
24
25
  class HookContext:
25
26
  """Context passed to hooks for processing."""
27
+
26
28
  hook_type: HookType
27
29
  data: Dict[str, Any]
28
30
  metadata: Dict[str, Any]
29
31
  timestamp: datetime
30
32
  session_id: Optional[str] = None
31
33
  user_id: Optional[str] = None
32
-
34
+
33
35
  def __post_init__(self):
34
36
  """Ensure timestamp is set."""
35
- if not hasattr(self, 'timestamp') or self.timestamp is None:
37
+ if not hasattr(self, "timestamp") or self.timestamp is None:
36
38
  self.timestamp = datetime.now()
37
39
 
38
40
 
39
41
  @dataclass
40
42
  class HookResult:
41
43
  """Result returned from hook execution."""
44
+
42
45
  success: bool
43
46
  data: Optional[Dict[str, Any]] = None
44
47
  error: Optional[str] = None
@@ -49,10 +52,10 @@ class HookResult:
49
52
 
50
53
  class BaseHook(ABC):
51
54
  """Base class for all hooks."""
52
-
55
+
53
56
  def __init__(self, name: str, priority: int = 50):
54
57
  """Initialize hook with name and priority.
55
-
58
+
56
59
  Args:
57
60
  name: Unique name for the hook
58
61
  priority: Execution priority (0-100, lower executes first)
@@ -61,40 +64,40 @@ class BaseHook(ABC):
61
64
  self.priority = max(0, min(100, priority)) # Clamp to 0-100
62
65
  self.enabled = True
63
66
  self._async = False
64
-
67
+
65
68
  @abstractmethod
66
69
  def execute(self, context: HookContext) -> HookResult:
67
70
  """Execute the hook with given context.
68
-
71
+
69
72
  Args:
70
73
  context: Hook context containing data and metadata
71
-
74
+
72
75
  Returns:
73
76
  HookResult with execution results
74
77
  """
75
78
  pass
76
-
79
+
77
80
  async def async_execute(self, context: HookContext) -> HookResult:
78
81
  """Async version of execute. Override for async hooks."""
79
82
  # Default implementation calls sync execute in executor
80
83
  loop = asyncio.get_event_loop()
81
84
  return await loop.run_in_executor(None, self.execute, context)
82
-
85
+
83
86
  def validate(self, context: HookContext) -> bool:
84
87
  """Validate if hook should run for given context.
85
-
88
+
86
89
  Args:
87
90
  context: Hook context to validate
88
-
91
+
89
92
  Returns:
90
93
  True if hook should execute, False otherwise
91
94
  """
92
95
  return self.enabled
93
-
96
+
94
97
  def __repr__(self):
95
98
  """String representation of hook."""
96
99
  return f"{self.__class__.__name__}(name='{self.name}', priority={self.priority}, enabled={self.enabled})"
97
-
100
+
98
101
  def __lt__(self, other):
99
102
  """Compare hooks by priority for sorting."""
100
103
  if not isinstance(other, BaseHook):
@@ -104,51 +107,53 @@ class BaseHook(ABC):
104
107
 
105
108
  class SubmitHook(BaseHook):
106
109
  """Base class for hooks that process user prompts."""
107
-
110
+
108
111
  def __init__(self, name: str, priority: int = 50):
109
112
  super().__init__(name, priority)
110
-
113
+
111
114
  def validate(self, context: HookContext) -> bool:
112
115
  """Validate submit hook context."""
113
116
  if not super().validate(context):
114
117
  return False
115
- return context.hook_type == HookType.SUBMIT and 'prompt' in context.data
118
+ return context.hook_type == HookType.SUBMIT and "prompt" in context.data
116
119
 
117
120
 
118
121
  class PreDelegationHook(BaseHook):
119
122
  """Base class for hooks that filter context before delegation."""
120
-
123
+
121
124
  def __init__(self, name: str, priority: int = 50):
122
125
  super().__init__(name, priority)
123
-
126
+
124
127
  def validate(self, context: HookContext) -> bool:
125
128
  """Validate pre-delegation hook context."""
126
129
  if not super().validate(context):
127
130
  return False
128
- return context.hook_type == HookType.PRE_DELEGATION and 'agent' in context.data
131
+ return context.hook_type == HookType.PRE_DELEGATION and "agent" in context.data
129
132
 
130
133
 
131
134
  class PostDelegationHook(BaseHook):
132
135
  """Base class for hooks that process results after delegation."""
133
-
136
+
134
137
  def __init__(self, name: str, priority: int = 50):
135
138
  super().__init__(name, priority)
136
-
139
+
137
140
  def validate(self, context: HookContext) -> bool:
138
141
  """Validate post-delegation hook context."""
139
142
  if not super().validate(context):
140
143
  return False
141
- return context.hook_type == HookType.POST_DELEGATION and 'result' in context.data
144
+ return (
145
+ context.hook_type == HookType.POST_DELEGATION and "result" in context.data
146
+ )
142
147
 
143
148
 
144
149
  class TicketExtractionHook(BaseHook):
145
150
  """Base class for hooks that extract and create tickets."""
146
-
151
+
147
152
  def __init__(self, name: str, priority: int = 50):
148
153
  super().__init__(name, priority)
149
-
154
+
150
155
  def validate(self, context: HookContext) -> bool:
151
156
  """Validate ticket extraction hook context."""
152
157
  if not super().validate(context):
153
158
  return False
154
- return context.hook_type == HookType.TICKET_EXTRACTION
159
+ return context.hook_type == HookType.TICKET_EXTRACTION
@@ -2,4 +2,4 @@
2
2
 
3
3
  from .hook_handler import ClaudeHookHandler
4
4
 
5
- __all__ = ['ClaudeHookHandler']
5
+ __all__ = ["ClaudeHookHandler"]
@@ -0,0 +1,120 @@
1
+ #!/usr/bin/env python3
2
+ """Socket.IO connection pool for Claude Code hook handler.
3
+
4
+ This module provides connection pooling for Socket.IO clients to reduce
5
+ connection overhead and implement circuit breaker patterns.
6
+ """
7
+
8
+ import time
9
+ from typing import Any, Dict, List, Optional
10
+
11
+ # Import constants for configuration
12
+ try:
13
+ from claude_mpm.core.constants import NetworkConfig
14
+ except ImportError:
15
+ # Fallback values if constants module not available
16
+ class NetworkConfig:
17
+ SOCKETIO_PORT_RANGE = (8080, 8099)
18
+ RECONNECTION_DELAY = 0.5
19
+ SOCKET_WAIT_TIMEOUT = 1.0
20
+
21
+
22
+ # Socket.IO import
23
+ try:
24
+ import socketio
25
+
26
+ SOCKETIO_AVAILABLE = True
27
+ except ImportError:
28
+ SOCKETIO_AVAILABLE = False
29
+ socketio = None
30
+
31
+
32
+ class SocketIOConnectionPool:
33
+ """Connection pool for Socket.IO clients to prevent connection leaks."""
34
+
35
+ def __init__(self, max_connections: int = 3):
36
+ self.max_connections = max_connections
37
+ self.connections: List[Dict[str, Any]] = []
38
+ self.last_cleanup = time.time()
39
+
40
+ def get_connection(self, port: int) -> Optional[Any]:
41
+ """Get or create a connection to the specified port."""
42
+ if time.time() - self.last_cleanup > 60:
43
+ self._cleanup_dead_connections()
44
+ self.last_cleanup = time.time()
45
+
46
+ for conn in self.connections:
47
+ if conn.get("port") == port and conn.get("client"):
48
+ client = conn["client"]
49
+ if self._is_connection_alive(client):
50
+ return client
51
+ else:
52
+ self.connections.remove(conn)
53
+
54
+ if len(self.connections) < self.max_connections:
55
+ client = self._create_connection(port)
56
+ if client:
57
+ self.connections.append(
58
+ {"port": port, "client": client, "created": time.time()}
59
+ )
60
+ return client
61
+
62
+ if self.connections:
63
+ oldest = min(self.connections, key=lambda x: x["created"])
64
+ self._close_connection(oldest["client"])
65
+ oldest["client"] = self._create_connection(port)
66
+ oldest["port"] = port
67
+ oldest["created"] = time.time()
68
+ return oldest["client"]
69
+
70
+ return None
71
+
72
+ def _create_connection(self, port: int) -> Optional[Any]:
73
+ """Create a new Socket.IO connection."""
74
+ if not SOCKETIO_AVAILABLE:
75
+ return None
76
+ try:
77
+ client = socketio.Client(
78
+ reconnection=False,
79
+ logger=False,
80
+ engineio_logger=False, # Disable auto-reconnect
81
+ )
82
+ client.connect(
83
+ f"http://localhost:{port}",
84
+ wait=True,
85
+ wait_timeout=NetworkConfig.SOCKET_WAIT_TIMEOUT,
86
+ )
87
+ if client.connected:
88
+ return client
89
+ except Exception:
90
+ pass
91
+ return None
92
+
93
+ def _is_connection_alive(self, client: Any) -> bool:
94
+ """Check if a connection is still alive."""
95
+ try:
96
+ return client and client.connected
97
+ except:
98
+ return False
99
+
100
+ def _close_connection(self, client: Any) -> None:
101
+ """Safely close a connection."""
102
+ try:
103
+ if client:
104
+ client.disconnect()
105
+ except:
106
+ pass
107
+
108
+ def _cleanup_dead_connections(self) -> None:
109
+ """Remove dead connections from the pool."""
110
+ self.connections = [
111
+ conn
112
+ for conn in self.connections
113
+ if self._is_connection_alive(conn.get("client"))
114
+ ]
115
+
116
+ def close_all(self) -> None:
117
+ """Close all connections in the pool."""
118
+ for conn in self.connections:
119
+ self._close_connection(conn.get("client"))
120
+ self.connections.clear()