claude-mpm 4.24.0__py3-none-any.whl → 5.4.41__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.

Potentially problematic release.


This version of claude-mpm might be problematic. Click here for more details.

Files changed (623) hide show
  1. claude_mpm/VERSION +1 -1
  2. claude_mpm/__init__.py +4 -0
  3. claude_mpm/agents/BASE_AGENT.md +164 -0
  4. claude_mpm/agents/{OUTPUT_STYLE.md → CLAUDE_MPM_OUTPUT_STYLE.md} +3 -48
  5. claude_mpm/agents/CLAUDE_MPM_TEACHER_OUTPUT_STYLE.md +2002 -0
  6. claude_mpm/agents/MEMORY.md +1 -1
  7. claude_mpm/agents/PM_INSTRUCTIONS.md +735 -925
  8. claude_mpm/agents/WORKFLOW.md +5 -254
  9. claude_mpm/agents/__init__.py +6 -0
  10. claude_mpm/agents/agent_loader.py +14 -48
  11. claude_mpm/agents/base_agent.json +7 -4
  12. claude_mpm/agents/frontmatter_validator.py +71 -3
  13. claude_mpm/agents/templates/circuit-breakers.md +1391 -0
  14. claude_mpm/agents/templates/context-management-examples.md +544 -0
  15. claude_mpm/agents/templates/{pm_red_flags.md → pm-red-flags.md} +48 -0
  16. claude_mpm/agents/templates/pr-workflow-examples.md +427 -0
  17. claude_mpm/agents/templates/research-gate-examples.md +669 -0
  18. claude_mpm/agents/templates/structured-questions-examples.md +615 -0
  19. claude_mpm/agents/templates/ticket-completeness-examples.md +139 -0
  20. claude_mpm/agents/templates/ticketing-examples.md +277 -0
  21. claude_mpm/cli/__init__.py +37 -2
  22. claude_mpm/cli/__main__.py +4 -0
  23. claude_mpm/cli/chrome_devtools_installer.py +175 -0
  24. claude_mpm/cli/commands/__init__.py +2 -0
  25. claude_mpm/cli/commands/agent_source.py +774 -0
  26. claude_mpm/cli/commands/agent_state_manager.py +180 -31
  27. claude_mpm/cli/commands/agents.py +1116 -55
  28. claude_mpm/cli/commands/agents_cleanup.py +210 -0
  29. claude_mpm/cli/commands/agents_discover.py +338 -0
  30. claude_mpm/cli/commands/aggregate.py +1 -1
  31. claude_mpm/cli/commands/analyze.py +3 -3
  32. claude_mpm/cli/commands/auto_configure.py +725 -242
  33. claude_mpm/cli/commands/config.py +95 -6
  34. claude_mpm/cli/commands/configure.py +1875 -46
  35. claude_mpm/cli/commands/configure_agent_display.py +29 -10
  36. claude_mpm/cli/commands/configure_navigation.py +63 -46
  37. claude_mpm/cli/commands/debug.py +12 -12
  38. claude_mpm/cli/commands/doctor.py +10 -2
  39. claude_mpm/cli/commands/hook_errors.py +277 -0
  40. claude_mpm/cli/commands/local_deploy.py +1 -4
  41. claude_mpm/cli/commands/mcp_install_commands.py +1 -1
  42. claude_mpm/cli/commands/mpm_init/core.py +229 -2
  43. claude_mpm/cli/commands/mpm_init/git_activity.py +10 -10
  44. claude_mpm/cli/commands/mpm_init/knowledge_extractor.py +481 -0
  45. claude_mpm/cli/commands/mpm_init/prompts.py +286 -6
  46. claude_mpm/cli/commands/postmortem.py +401 -0
  47. claude_mpm/cli/commands/profile.py +277 -0
  48. claude_mpm/cli/commands/run.py +123 -165
  49. claude_mpm/cli/commands/skill_source.py +694 -0
  50. claude_mpm/cli/commands/skills.py +782 -20
  51. claude_mpm/cli/commands/summarize.py +413 -0
  52. claude_mpm/cli/executor.py +96 -3
  53. claude_mpm/cli/interactive/agent_wizard.py +1030 -45
  54. claude_mpm/cli/parsers/agent_source_parser.py +171 -0
  55. claude_mpm/cli/parsers/agents_parser.py +307 -10
  56. claude_mpm/cli/parsers/auto_configure_parser.py +13 -138
  57. claude_mpm/cli/parsers/base_parser.py +65 -0
  58. claude_mpm/cli/parsers/config_parser.py +162 -39
  59. claude_mpm/cli/parsers/profile_parser.py +148 -0
  60. claude_mpm/cli/parsers/skill_source_parser.py +169 -0
  61. claude_mpm/cli/parsers/skills_parser.py +146 -0
  62. claude_mpm/cli/parsers/source_parser.py +138 -0
  63. claude_mpm/cli/startup.py +1280 -118
  64. claude_mpm/cli/startup_display.py +480 -0
  65. claude_mpm/cli/utils.py +1 -1
  66. claude_mpm/cli_module/commands.py +1 -1
  67. claude_mpm/commands/mpm-config.md +21 -134
  68. claude_mpm/commands/mpm-doctor.md +16 -20
  69. claude_mpm/commands/mpm-help.md +13 -283
  70. claude_mpm/commands/mpm-init.md +88 -489
  71. claude_mpm/commands/mpm-monitor.md +23 -401
  72. claude_mpm/commands/mpm-organize.md +72 -247
  73. claude_mpm/commands/mpm-postmortem.md +21 -0
  74. claude_mpm/commands/mpm-session-resume.md +30 -0
  75. claude_mpm/commands/mpm-status.md +13 -68
  76. claude_mpm/commands/mpm-ticket-view.md +109 -0
  77. claude_mpm/commands/mpm-version.md +13 -106
  78. claude_mpm/commands/mpm.md +10 -0
  79. claude_mpm/config/agent_presets.py +488 -0
  80. claude_mpm/config/agent_sources.py +352 -0
  81. claude_mpm/config/skill_presets.py +392 -0
  82. claude_mpm/config/skill_sources.py +590 -0
  83. claude_mpm/constants.py +13 -0
  84. claude_mpm/core/claude_runner.py +5 -34
  85. claude_mpm/core/config.py +15 -1
  86. claude_mpm/core/constants.py +1 -1
  87. claude_mpm/core/framework/__init__.py +3 -16
  88. claude_mpm/core/framework/formatters/content_formatter.py +3 -13
  89. claude_mpm/core/framework/loaders/agent_loader.py +8 -5
  90. claude_mpm/core/framework/loaders/file_loader.py +54 -101
  91. claude_mpm/core/framework/loaders/instruction_loader.py +66 -5
  92. claude_mpm/core/framework_loader.py +4 -2
  93. claude_mpm/core/hook_error_memory.py +381 -0
  94. claude_mpm/core/hook_manager.py +41 -2
  95. claude_mpm/core/interactive_session.py +91 -10
  96. claude_mpm/core/logger.py +16 -1
  97. claude_mpm/core/oneshot_session.py +71 -8
  98. claude_mpm/core/optimized_startup.py +59 -0
  99. claude_mpm/core/output_style_manager.py +173 -43
  100. claude_mpm/core/protocols/__init__.py +23 -0
  101. claude_mpm/core/protocols/runner_protocol.py +103 -0
  102. claude_mpm/core/protocols/session_protocol.py +131 -0
  103. claude_mpm/core/shared/config_loader.py +1 -1
  104. claude_mpm/core/shared/singleton_manager.py +11 -4
  105. claude_mpm/core/socketio_pool.py +3 -3
  106. claude_mpm/core/system_context.py +38 -0
  107. claude_mpm/core/unified_agent_registry.py +134 -16
  108. claude_mpm/core/unified_config.py +22 -0
  109. claude_mpm/dashboard/static/svelte-build/_app/env.js +1 -0
  110. claude_mpm/dashboard/static/svelte-build/_app/immutable/assets/0.B_FtCwCQ.css +1 -0
  111. claude_mpm/dashboard/static/svelte-build/_app/immutable/assets/2.Cl_eSA4x.css +1 -0
  112. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/BgChzWQ1.js +1 -0
  113. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/CIXEwuWe.js +1 -0
  114. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/CWc5urbQ.js +1 -0
  115. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/DMkZpdF2.js +2 -0
  116. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/DjhvlsAc.js +1 -0
  117. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/N4qtv3Hx.js +2 -0
  118. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/uj46x2Wr.js +1 -0
  119. claude_mpm/dashboard/static/svelte-build/_app/immutable/entry/app.DTL5mJO-.js +2 -0
  120. claude_mpm/dashboard/static/svelte-build/_app/immutable/entry/start.DzuEhzqh.js +1 -0
  121. claude_mpm/dashboard/static/svelte-build/_app/immutable/nodes/0.CAGBuiOw.js +1 -0
  122. claude_mpm/dashboard/static/svelte-build/_app/immutable/nodes/1.DFLC8jdE.js +1 -0
  123. claude_mpm/dashboard/static/svelte-build/_app/immutable/nodes/2.DPvEihJJ.js +10 -0
  124. claude_mpm/dashboard/static/svelte-build/_app/version.json +1 -0
  125. claude_mpm/dashboard/static/svelte-build/favicon.svg +7 -0
  126. claude_mpm/dashboard/static/svelte-build/index.html +36 -0
  127. claude_mpm/experimental/cli_enhancements.py +1 -5
  128. claude_mpm/hooks/claude_hooks/__pycache__/__init__.cpython-311.pyc +0 -0
  129. claude_mpm/hooks/claude_hooks/__pycache__/correlation_manager.cpython-311.pyc +0 -0
  130. claude_mpm/hooks/claude_hooks/__pycache__/event_handlers.cpython-311.pyc +0 -0
  131. claude_mpm/hooks/claude_hooks/__pycache__/hook_handler.cpython-311.pyc +0 -0
  132. claude_mpm/hooks/claude_hooks/__pycache__/installer.cpython-311.pyc +0 -0
  133. claude_mpm/hooks/claude_hooks/__pycache__/memory_integration.cpython-311.pyc +0 -0
  134. claude_mpm/hooks/claude_hooks/__pycache__/response_tracking.cpython-311.pyc +0 -0
  135. claude_mpm/hooks/claude_hooks/__pycache__/tool_analysis.cpython-311.pyc +0 -0
  136. claude_mpm/hooks/claude_hooks/correlation_manager.py +60 -0
  137. claude_mpm/hooks/claude_hooks/event_handlers.py +214 -79
  138. claude_mpm/hooks/claude_hooks/hook_handler.py +155 -1
  139. claude_mpm/hooks/claude_hooks/installer.py +33 -10
  140. claude_mpm/hooks/claude_hooks/memory_integration.py +28 -0
  141. claude_mpm/hooks/claude_hooks/response_tracking.py +2 -3
  142. claude_mpm/hooks/claude_hooks/services/__pycache__/__init__.cpython-311.pyc +0 -0
  143. claude_mpm/hooks/claude_hooks/services/__pycache__/connection_manager.cpython-311.pyc +0 -0
  144. claude_mpm/hooks/claude_hooks/services/__pycache__/connection_manager_http.cpython-311.pyc +0 -0
  145. claude_mpm/hooks/claude_hooks/services/__pycache__/duplicate_detector.cpython-311.pyc +0 -0
  146. claude_mpm/hooks/claude_hooks/services/__pycache__/state_manager.cpython-311.pyc +0 -0
  147. claude_mpm/hooks/claude_hooks/services/__pycache__/subagent_processor.cpython-311.pyc +0 -0
  148. claude_mpm/hooks/claude_hooks/services/connection_manager.py +30 -6
  149. claude_mpm/hooks/failure_learning/__init__.py +2 -8
  150. claude_mpm/hooks/failure_learning/failure_detection_hook.py +1 -6
  151. claude_mpm/hooks/failure_learning/fix_detection_hook.py +1 -6
  152. claude_mpm/hooks/failure_learning/learning_extraction_hook.py +1 -6
  153. claude_mpm/hooks/kuzu_response_hook.py +1 -5
  154. claude_mpm/hooks/memory_integration_hook.py +46 -1
  155. claude_mpm/init.py +63 -19
  156. claude_mpm/models/agent_definition.py +7 -0
  157. claude_mpm/models/git_repository.py +198 -0
  158. claude_mpm/scripts/claude-hook-handler.sh +60 -20
  159. claude_mpm/scripts/launch_monitor.py +93 -13
  160. claude_mpm/scripts/start_activity_logging.py +3 -1
  161. claude_mpm/services/agents/agent_builder.py +48 -12
  162. claude_mpm/services/agents/agent_preset_service.py +238 -0
  163. claude_mpm/services/agents/agent_recommendation_service.py +278 -0
  164. claude_mpm/services/agents/agent_review_service.py +280 -0
  165. claude_mpm/services/agents/agent_selection_service.py +484 -0
  166. claude_mpm/services/agents/auto_deploy_index_parser.py +569 -0
  167. claude_mpm/services/agents/cache_git_manager.py +621 -0
  168. claude_mpm/services/agents/deployment/agent_deployment.py +148 -2
  169. claude_mpm/services/agents/deployment/agent_discovery_service.py +104 -73
  170. claude_mpm/services/agents/deployment/agent_format_converter.py +1 -1
  171. claude_mpm/services/agents/deployment/agent_lifecycle_manager.py +1 -5
  172. claude_mpm/services/agents/deployment/agent_metrics_collector.py +3 -3
  173. claude_mpm/services/agents/deployment/agent_restore_handler.py +1 -4
  174. claude_mpm/services/agents/deployment/agent_template_builder.py +238 -15
  175. claude_mpm/services/agents/deployment/agents_directory_resolver.py +101 -15
  176. claude_mpm/services/agents/deployment/async_agent_deployment.py +2 -1
  177. claude_mpm/services/agents/deployment/facade/deployment_facade.py +3 -3
  178. claude_mpm/services/agents/deployment/multi_source_deployment_service.py +422 -31
  179. claude_mpm/services/agents/deployment/pipeline/pipeline_executor.py +2 -2
  180. claude_mpm/services/agents/deployment/refactored_agent_deployment_service.py +1 -4
  181. claude_mpm/services/agents/deployment/remote_agent_discovery_service.py +841 -0
  182. claude_mpm/services/agents/deployment/single_agent_deployer.py +2 -2
  183. claude_mpm/services/agents/deployment/system_instructions_deployer.py +168 -46
  184. claude_mpm/services/agents/deployment/validation/deployment_validator.py +2 -2
  185. claude_mpm/services/agents/git_source_manager.py +663 -0
  186. claude_mpm/services/agents/loading/base_agent_manager.py +1 -13
  187. claude_mpm/services/agents/loading/framework_agent_loader.py +9 -12
  188. claude_mpm/services/agents/local_template_manager.py +50 -10
  189. claude_mpm/services/agents/recommender.py +5 -3
  190. claude_mpm/services/agents/single_tier_deployment_service.py +696 -0
  191. claude_mpm/services/agents/sources/__init__.py +13 -0
  192. claude_mpm/services/agents/sources/agent_sync_state.py +516 -0
  193. claude_mpm/services/agents/sources/git_source_sync_service.py +1094 -0
  194. claude_mpm/services/agents/startup_sync.py +259 -0
  195. claude_mpm/services/agents/toolchain_detector.py +478 -0
  196. claude_mpm/services/analysis/__init__.py +35 -0
  197. claude_mpm/services/analysis/clone_detector.py +1030 -0
  198. claude_mpm/services/analysis/postmortem_reporter.py +474 -0
  199. claude_mpm/services/analysis/postmortem_service.py +765 -0
  200. claude_mpm/services/cli/session_pause_manager.py +1 -1
  201. claude_mpm/services/command_deployment_service.py +271 -6
  202. claude_mpm/services/core/base.py +7 -2
  203. claude_mpm/services/core/interfaces/__init__.py +1 -3
  204. claude_mpm/services/core/interfaces/health.py +1 -4
  205. claude_mpm/services/core/models/__init__.py +2 -11
  206. claude_mpm/services/diagnostics/checks/__init__.py +4 -0
  207. claude_mpm/services/diagnostics/checks/agent_check.py +2 -4
  208. claude_mpm/services/diagnostics/checks/agent_sources_check.py +577 -0
  209. claude_mpm/services/diagnostics/checks/instructions_check.py +1 -2
  210. claude_mpm/services/diagnostics/checks/mcp_check.py +0 -1
  211. claude_mpm/services/diagnostics/checks/mcp_services_check.py +7 -15
  212. claude_mpm/services/diagnostics/checks/monitor_check.py +0 -1
  213. claude_mpm/services/diagnostics/checks/skill_sources_check.py +587 -0
  214. claude_mpm/services/diagnostics/diagnostic_runner.py +9 -0
  215. claude_mpm/services/diagnostics/doctor_reporter.py +40 -10
  216. claude_mpm/services/event_bus/config.py +3 -1
  217. claude_mpm/services/event_bus/direct_relay.py +3 -3
  218. claude_mpm/services/events/consumers/logging.py +1 -2
  219. claude_mpm/services/git/__init__.py +21 -0
  220. claude_mpm/services/git/git_operations_service.py +579 -0
  221. claude_mpm/services/github/__init__.py +21 -0
  222. claude_mpm/services/github/github_cli_service.py +397 -0
  223. claude_mpm/services/infrastructure/monitoring/__init__.py +1 -5
  224. claude_mpm/services/infrastructure/monitoring/aggregator.py +1 -6
  225. claude_mpm/services/instructions/__init__.py +9 -0
  226. claude_mpm/services/instructions/instruction_cache_service.py +374 -0
  227. claude_mpm/services/local_ops/__init__.py +3 -13
  228. claude_mpm/services/local_ops/health_checks/__init__.py +1 -3
  229. claude_mpm/services/local_ops/health_manager.py +1 -4
  230. claude_mpm/services/local_ops/resource_monitor.py +1 -1
  231. claude_mpm/services/mcp_config_manager.py +75 -145
  232. claude_mpm/services/mcp_service_verifier.py +6 -3
  233. claude_mpm/services/model/model_router.py +1 -2
  234. claude_mpm/services/monitor/daemon.py +38 -11
  235. claude_mpm/services/monitor/daemon_manager.py +134 -21
  236. claude_mpm/services/monitor/management/lifecycle.py +8 -1
  237. claude_mpm/services/monitor/server.py +700 -24
  238. claude_mpm/services/pm_skills_deployer.py +676 -0
  239. claude_mpm/services/port_manager.py +1 -1
  240. claude_mpm/services/pr/__init__.py +14 -0
  241. claude_mpm/services/pr/pr_template_service.py +329 -0
  242. claude_mpm/services/profile_manager.py +331 -0
  243. claude_mpm/services/project/documentation_manager.py +2 -1
  244. claude_mpm/services/project/project_organizer.py +4 -0
  245. claude_mpm/services/project/toolchain_analyzer.py +3 -1
  246. claude_mpm/services/runner_configuration_service.py +16 -3
  247. claude_mpm/services/self_upgrade_service.py +120 -12
  248. claude_mpm/services/session_management_service.py +16 -4
  249. claude_mpm/services/skills/__init__.py +21 -0
  250. claude_mpm/services/skills/git_skill_source_manager.py +1297 -0
  251. claude_mpm/services/skills/selective_skill_deployer.py +704 -0
  252. claude_mpm/services/skills/skill_discovery_service.py +568 -0
  253. claude_mpm/services/skills/skill_to_agent_mapper.py +406 -0
  254. claude_mpm/services/skills_config.py +547 -0
  255. claude_mpm/services/skills_deployer.py +1072 -0
  256. claude_mpm/services/socketio/dashboard_server.py +1 -0
  257. claude_mpm/services/socketio/event_normalizer.py +51 -6
  258. claude_mpm/services/socketio/handlers/connection.py +1 -1
  259. claude_mpm/services/socketio/handlers/git.py +1 -1
  260. claude_mpm/services/socketio/server/core.py +387 -112
  261. claude_mpm/services/socketio/server/main.py +1 -3
  262. claude_mpm/services/system_instructions_service.py +1 -3
  263. claude_mpm/services/unified/analyzer_strategies/performance_analyzer.py +0 -3
  264. claude_mpm/services/unified/analyzer_strategies/security_analyzer.py +0 -1
  265. claude_mpm/services/unified/deployment_strategies/vercel.py +1 -5
  266. claude_mpm/services/unified/unified_deployment.py +1 -5
  267. claude_mpm/services/version_control/conflict_resolution.py +6 -4
  268. claude_mpm/services/version_control/git_operations.py +103 -0
  269. claude_mpm/services/visualization/__init__.py +1 -5
  270. claude_mpm/services/visualization/mermaid_generator.py +2 -3
  271. claude_mpm/skills/bundled/testing/webapp-testing/scripts/with_server.py +2 -2
  272. claude_mpm/skills/skill_manager.py +92 -3
  273. claude_mpm/skills/skills_registry.py +0 -1
  274. claude_mpm/templates/questions/__init__.py +38 -0
  275. claude_mpm/templates/questions/base.py +193 -0
  276. claude_mpm/templates/questions/pr_strategy.py +311 -0
  277. claude_mpm/templates/questions/project_init.py +385 -0
  278. claude_mpm/templates/questions/ticket_mgmt.py +394 -0
  279. claude_mpm/tools/__main__.py +8 -8
  280. claude_mpm/utils/agent_dependency_loader.py +91 -12
  281. claude_mpm/utils/agent_filters.py +261 -0
  282. claude_mpm/utils/dependency_cache.py +3 -1
  283. claude_mpm/utils/gitignore.py +244 -0
  284. claude_mpm/utils/migration.py +372 -0
  285. claude_mpm/utils/progress.py +387 -0
  286. claude_mpm/utils/robust_installer.py +49 -7
  287. claude_mpm/utils/structured_questions.py +619 -0
  288. {claude_mpm-4.24.0.dist-info → claude_mpm-5.4.41.dist-info}/METADATA +445 -122
  289. {claude_mpm-4.24.0.dist-info → claude_mpm-5.4.41.dist-info}/RECORD +298 -503
  290. claude_mpm-5.4.41.dist-info/entry_points.txt +5 -0
  291. claude_mpm-5.4.41.dist-info/licenses/LICENSE +94 -0
  292. claude_mpm-5.4.41.dist-info/licenses/LICENSE-FAQ.md +153 -0
  293. claude_mpm/agents/BASE_AGENT_TEMPLATE.md +0 -292
  294. claude_mpm/agents/BASE_DOCUMENTATION.md +0 -53
  295. claude_mpm/agents/BASE_OPS.md +0 -219
  296. claude_mpm/agents/BASE_PM.md +0 -468
  297. claude_mpm/agents/BASE_PROMPT_ENGINEER.md +0 -787
  298. claude_mpm/agents/BASE_QA.md +0 -167
  299. claude_mpm/agents/BASE_RESEARCH.md +0 -53
  300. claude_mpm/agents/base_agent_loader.py +0 -626
  301. claude_mpm/agents/templates/.claude-mpm/memories/README.md +0 -17
  302. claude_mpm/agents/templates/.claude-mpm/memories/engineer_memories.md +0 -3
  303. claude_mpm/agents/templates/agent-manager.json +0 -273
  304. claude_mpm/agents/templates/agentic-coder-optimizer.json +0 -248
  305. claude_mpm/agents/templates/api_qa.json +0 -183
  306. claude_mpm/agents/templates/circuit_breakers.md +0 -638
  307. claude_mpm/agents/templates/clerk-ops.json +0 -235
  308. claude_mpm/agents/templates/code_analyzer.json +0 -101
  309. claude_mpm/agents/templates/content-agent.json +0 -358
  310. claude_mpm/agents/templates/dart_engineer.json +0 -307
  311. claude_mpm/agents/templates/data_engineer.json +0 -225
  312. claude_mpm/agents/templates/documentation.json +0 -238
  313. claude_mpm/agents/templates/engineer.json +0 -210
  314. claude_mpm/agents/templates/gcp_ops_agent.json +0 -253
  315. claude_mpm/agents/templates/golang_engineer.json +0 -270
  316. claude_mpm/agents/templates/imagemagick.json +0 -264
  317. claude_mpm/agents/templates/java_engineer.json +0 -346
  318. claude_mpm/agents/templates/javascript_engineer_agent.json +0 -380
  319. claude_mpm/agents/templates/local_ops_agent.json +0 -1840
  320. claude_mpm/agents/templates/logs/prompts/agent_engineer_20250826_014258_728.md +0 -39
  321. claude_mpm/agents/templates/logs/prompts/agent_engineer_20250901_010124_142.md +0 -400
  322. claude_mpm/agents/templates/memory_manager.json +0 -158
  323. claude_mpm/agents/templates/nextjs_engineer.json +0 -285
  324. claude_mpm/agents/templates/ops.json +0 -185
  325. claude_mpm/agents/templates/php-engineer.json +0 -287
  326. claude_mpm/agents/templates/product_owner.json +0 -338
  327. claude_mpm/agents/templates/project_organizer.json +0 -144
  328. claude_mpm/agents/templates/prompt-engineer.json +0 -737
  329. claude_mpm/agents/templates/python_engineer.json +0 -387
  330. claude_mpm/agents/templates/qa.json +0 -243
  331. claude_mpm/agents/templates/react_engineer.json +0 -239
  332. claude_mpm/agents/templates/refactoring_engineer.json +0 -276
  333. claude_mpm/agents/templates/research.json +0 -188
  334. claude_mpm/agents/templates/ruby-engineer.json +0 -280
  335. claude_mpm/agents/templates/rust_engineer.json +0 -275
  336. claude_mpm/agents/templates/security.json +0 -202
  337. claude_mpm/agents/templates/svelte-engineer.json +0 -225
  338. claude_mpm/agents/templates/tauri_engineer.json +0 -274
  339. claude_mpm/agents/templates/ticketing.json +0 -178
  340. claude_mpm/agents/templates/typescript_engineer.json +0 -285
  341. claude_mpm/agents/templates/vercel_ops_agent.json +0 -412
  342. claude_mpm/agents/templates/version_control.json +0 -159
  343. claude_mpm/agents/templates/web_qa.json +0 -400
  344. claude_mpm/agents/templates/web_ui.json +0 -189
  345. claude_mpm/cli/commands/agents_detect.py +0 -380
  346. claude_mpm/cli/commands/agents_recommend.py +0 -309
  347. claude_mpm/cli/ticket_cli.py +0 -35
  348. claude_mpm/commands/mpm-agents-detect.md +0 -168
  349. claude_mpm/commands/mpm-agents-recommend.md +0 -214
  350. claude_mpm/commands/mpm-agents.md +0 -122
  351. claude_mpm/commands/mpm-auto-configure.md +0 -269
  352. claude_mpm/commands/mpm-resume.md +0 -372
  353. claude_mpm/commands/mpm-tickets.md +0 -151
  354. claude_mpm/dashboard/.claude-mpm/socketio-instances.json +0 -1
  355. claude_mpm/dashboard/analysis_runner.py +0 -455
  356. claude_mpm/dashboard/index.html +0 -13
  357. claude_mpm/dashboard/open_dashboard.py +0 -66
  358. claude_mpm/dashboard/react/components/DataInspector/DataInspector.module.css +0 -188
  359. claude_mpm/dashboard/react/components/EventViewer/EventViewer.module.css +0 -156
  360. claude_mpm/dashboard/react/components/shared/ConnectionStatus.module.css +0 -38
  361. claude_mpm/dashboard/react/components/shared/FilterBar.module.css +0 -92
  362. claude_mpm/dashboard/static/archive/activity_dashboard_fixed.html +0 -248
  363. claude_mpm/dashboard/static/archive/activity_dashboard_test.html +0 -61
  364. claude_mpm/dashboard/static/archive/test_activity_connection.html +0 -179
  365. claude_mpm/dashboard/static/archive/test_claude_tree_tab.html +0 -68
  366. claude_mpm/dashboard/static/archive/test_dashboard.html +0 -409
  367. claude_mpm/dashboard/static/archive/test_dashboard_fixed.html +0 -519
  368. claude_mpm/dashboard/static/archive/test_dashboard_verification.html +0 -181
  369. claude_mpm/dashboard/static/archive/test_file_data.html +0 -315
  370. claude_mpm/dashboard/static/archive/test_file_tree_empty_state.html +0 -243
  371. claude_mpm/dashboard/static/archive/test_file_tree_fix.html +0 -234
  372. claude_mpm/dashboard/static/archive/test_file_tree_rename.html +0 -117
  373. claude_mpm/dashboard/static/archive/test_file_tree_tab.html +0 -115
  374. claude_mpm/dashboard/static/archive/test_file_viewer.html +0 -224
  375. claude_mpm/dashboard/static/archive/test_final_activity.html +0 -220
  376. claude_mpm/dashboard/static/archive/test_tab_fix.html +0 -139
  377. claude_mpm/dashboard/static/built/assets/events.DjpNxWNo.css +0 -1
  378. claude_mpm/dashboard/static/built/components/activity-tree.js +0 -2
  379. claude_mpm/dashboard/static/built/components/agent-hierarchy.js +0 -777
  380. claude_mpm/dashboard/static/built/components/agent-inference.js +0 -2
  381. claude_mpm/dashboard/static/built/components/build-tracker.js +0 -333
  382. claude_mpm/dashboard/static/built/components/code-simple.js +0 -857
  383. claude_mpm/dashboard/static/built/components/code-tree/tree-breadcrumb.js +0 -353
  384. claude_mpm/dashboard/static/built/components/code-tree/tree-constants.js +0 -235
  385. claude_mpm/dashboard/static/built/components/code-tree/tree-search.js +0 -409
  386. claude_mpm/dashboard/static/built/components/code-tree/tree-utils.js +0 -435
  387. claude_mpm/dashboard/static/built/components/code-tree.js +0 -2
  388. claude_mpm/dashboard/static/built/components/code-viewer.js +0 -2
  389. claude_mpm/dashboard/static/built/components/connection-debug.js +0 -654
  390. claude_mpm/dashboard/static/built/components/diff-viewer.js +0 -891
  391. claude_mpm/dashboard/static/built/components/event-processor.js +0 -2
  392. claude_mpm/dashboard/static/built/components/event-viewer.js +0 -2
  393. claude_mpm/dashboard/static/built/components/export-manager.js +0 -2
  394. claude_mpm/dashboard/static/built/components/file-change-tracker.js +0 -443
  395. claude_mpm/dashboard/static/built/components/file-change-viewer.js +0 -690
  396. claude_mpm/dashboard/static/built/components/file-tool-tracker.js +0 -2
  397. claude_mpm/dashboard/static/built/components/file-viewer.js +0 -2
  398. claude_mpm/dashboard/static/built/components/hud-library-loader.js +0 -2
  399. claude_mpm/dashboard/static/built/components/hud-manager.js +0 -2
  400. claude_mpm/dashboard/static/built/components/hud-visualizer.js +0 -2
  401. claude_mpm/dashboard/static/built/components/module-viewer.js +0 -2
  402. claude_mpm/dashboard/static/built/components/nav-bar.js +0 -145
  403. claude_mpm/dashboard/static/built/components/page-structure.js +0 -429
  404. claude_mpm/dashboard/static/built/components/session-manager.js +0 -2
  405. claude_mpm/dashboard/static/built/components/socket-manager.js +0 -2
  406. claude_mpm/dashboard/static/built/components/ui-state-manager.js +0 -2
  407. claude_mpm/dashboard/static/built/components/unified-data-viewer.js +0 -2
  408. claude_mpm/dashboard/static/built/components/working-directory.js +0 -2
  409. claude_mpm/dashboard/static/built/connection-manager.js +0 -536
  410. claude_mpm/dashboard/static/built/dashboard.js +0 -2
  411. claude_mpm/dashboard/static/built/extension-error-handler.js +0 -164
  412. claude_mpm/dashboard/static/built/react/events.js +0 -30
  413. claude_mpm/dashboard/static/built/shared/dom-helpers.js +0 -396
  414. claude_mpm/dashboard/static/built/shared/event-bus.js +0 -330
  415. claude_mpm/dashboard/static/built/shared/event-filter-service.js +0 -540
  416. claude_mpm/dashboard/static/built/shared/logger.js +0 -385
  417. claude_mpm/dashboard/static/built/shared/page-structure.js +0 -249
  418. claude_mpm/dashboard/static/built/shared/tooltip-service.js +0 -253
  419. claude_mpm/dashboard/static/built/socket-client.js +0 -2
  420. claude_mpm/dashboard/static/built/tab-isolation-fix.js +0 -185
  421. claude_mpm/dashboard/static/css/activity.css +0 -1958
  422. claude_mpm/dashboard/static/css/connection-status.css +0 -370
  423. claude_mpm/dashboard/static/css/dashboard.css +0 -4701
  424. claude_mpm/dashboard/static/dist/assets/events.DjpNxWNo.css +0 -1
  425. claude_mpm/dashboard/static/dist/components/activity-tree.js +0 -2
  426. claude_mpm/dashboard/static/dist/components/agent-inference.js +0 -2
  427. claude_mpm/dashboard/static/dist/components/code-tree.js +0 -2
  428. claude_mpm/dashboard/static/dist/components/code-viewer.js +0 -2
  429. claude_mpm/dashboard/static/dist/components/event-processor.js +0 -2
  430. claude_mpm/dashboard/static/dist/components/event-viewer.js +0 -2
  431. claude_mpm/dashboard/static/dist/components/export-manager.js +0 -2
  432. claude_mpm/dashboard/static/dist/components/file-tool-tracker.js +0 -2
  433. claude_mpm/dashboard/static/dist/components/file-viewer.js +0 -2
  434. claude_mpm/dashboard/static/dist/components/hud-library-loader.js +0 -2
  435. claude_mpm/dashboard/static/dist/components/hud-manager.js +0 -2
  436. claude_mpm/dashboard/static/dist/components/hud-visualizer.js +0 -2
  437. claude_mpm/dashboard/static/dist/components/module-viewer.js +0 -2
  438. claude_mpm/dashboard/static/dist/components/session-manager.js +0 -2
  439. claude_mpm/dashboard/static/dist/components/socket-manager.js +0 -2
  440. claude_mpm/dashboard/static/dist/components/ui-state-manager.js +0 -2
  441. claude_mpm/dashboard/static/dist/components/unified-data-viewer.js +0 -2
  442. claude_mpm/dashboard/static/dist/components/working-directory.js +0 -2
  443. claude_mpm/dashboard/static/dist/dashboard.js +0 -2
  444. claude_mpm/dashboard/static/dist/react/events.js +0 -30
  445. claude_mpm/dashboard/static/dist/socket-client.js +0 -2
  446. claude_mpm/dashboard/static/events.html +0 -607
  447. claude_mpm/dashboard/static/index.html +0 -635
  448. claude_mpm/dashboard/static/js/components/activity-tree.js +0 -1871
  449. claude_mpm/dashboard/static/js/components/agent-hierarchy.js +0 -777
  450. claude_mpm/dashboard/static/js/components/agent-inference.js +0 -956
  451. claude_mpm/dashboard/static/js/components/build-tracker.js +0 -333
  452. claude_mpm/dashboard/static/js/components/code-simple.js +0 -857
  453. claude_mpm/dashboard/static/js/components/connection-debug.js +0 -654
  454. claude_mpm/dashboard/static/js/components/diff-viewer.js +0 -891
  455. claude_mpm/dashboard/static/js/components/event-processor.js +0 -542
  456. claude_mpm/dashboard/static/js/components/event-viewer.js +0 -1155
  457. claude_mpm/dashboard/static/js/components/export-manager.js +0 -368
  458. claude_mpm/dashboard/static/js/components/file-change-tracker.js +0 -443
  459. claude_mpm/dashboard/static/js/components/file-change-viewer.js +0 -690
  460. claude_mpm/dashboard/static/js/components/file-tool-tracker.js +0 -724
  461. claude_mpm/dashboard/static/js/components/file-viewer.js +0 -580
  462. claude_mpm/dashboard/static/js/components/hud-library-loader.js +0 -211
  463. claude_mpm/dashboard/static/js/components/hud-manager.js +0 -671
  464. claude_mpm/dashboard/static/js/components/hud-visualizer.js +0 -1718
  465. claude_mpm/dashboard/static/js/components/module-viewer.js +0 -2764
  466. claude_mpm/dashboard/static/js/components/session-manager.js +0 -579
  467. claude_mpm/dashboard/static/js/components/socket-manager.js +0 -368
  468. claude_mpm/dashboard/static/js/components/ui-state-manager.js +0 -749
  469. claude_mpm/dashboard/static/js/components/unified-data-viewer.js +0 -1824
  470. claude_mpm/dashboard/static/js/components/working-directory.js +0 -920
  471. claude_mpm/dashboard/static/js/connection-manager.js +0 -536
  472. claude_mpm/dashboard/static/js/dashboard.js +0 -1896
  473. claude_mpm/dashboard/static/js/extension-error-handler.js +0 -164
  474. claude_mpm/dashboard/static/js/shared/dom-helpers.js +0 -396
  475. claude_mpm/dashboard/static/js/shared/event-bus.js +0 -330
  476. claude_mpm/dashboard/static/js/shared/logger.js +0 -385
  477. claude_mpm/dashboard/static/js/shared/tooltip-service.js +0 -253
  478. claude_mpm/dashboard/static/js/socket-client.js +0 -1457
  479. claude_mpm/dashboard/static/js/stores/dashboard-store.js +0 -562
  480. claude_mpm/dashboard/static/js/tab-isolation-fix.js +0 -185
  481. claude_mpm/dashboard/static/legacy/activity.html +0 -736
  482. claude_mpm/dashboard/static/legacy/agents.html +0 -786
  483. claude_mpm/dashboard/static/legacy/files.html +0 -747
  484. claude_mpm/dashboard/static/legacy/tools.html +0 -831
  485. claude_mpm/dashboard/static/monitors.html +0 -431
  486. claude_mpm/dashboard/static/production/events.html +0 -659
  487. claude_mpm/dashboard/static/production/main.html +0 -698
  488. claude_mpm/dashboard/static/production/monitors.html +0 -483
  489. claude_mpm/dashboard/static/socket.io.min.js +0 -7
  490. claude_mpm/dashboard/static/socket.io.v4.8.1.backup.js +0 -7
  491. claude_mpm/dashboard/static/test-archive/dashboard.html +0 -635
  492. claude_mpm/dashboard/static/test-archive/debug-events.html +0 -147
  493. claude_mpm/dashboard/static/test-archive/test-navigation.html +0 -256
  494. claude_mpm/dashboard/static/test-archive/test-react-exports.html +0 -180
  495. claude_mpm/dashboard/static/test-archive/test_debug.html +0 -25
  496. claude_mpm/dashboard/templates/code_simple.html +0 -153
  497. claude_mpm/dashboard/templates/index.html +0 -606
  498. claude_mpm/dashboard/test_dashboard.html +0 -372
  499. claude_mpm/scripts/mcp_server.py +0 -75
  500. claude_mpm/scripts/mcp_wrapper.py +0 -39
  501. claude_mpm/services/mcp_gateway/__init__.py +0 -159
  502. claude_mpm/services/mcp_gateway/auto_configure.py +0 -369
  503. claude_mpm/services/mcp_gateway/config/__init__.py +0 -17
  504. claude_mpm/services/mcp_gateway/config/config_loader.py +0 -296
  505. claude_mpm/services/mcp_gateway/config/config_schema.py +0 -243
  506. claude_mpm/services/mcp_gateway/config/configuration.py +0 -429
  507. claude_mpm/services/mcp_gateway/core/__init__.py +0 -43
  508. claude_mpm/services/mcp_gateway/core/base.py +0 -312
  509. claude_mpm/services/mcp_gateway/core/exceptions.py +0 -253
  510. claude_mpm/services/mcp_gateway/core/interfaces.py +0 -443
  511. claude_mpm/services/mcp_gateway/core/process_pool.py +0 -971
  512. claude_mpm/services/mcp_gateway/core/singleton_manager.py +0 -315
  513. claude_mpm/services/mcp_gateway/core/startup_verification.py +0 -316
  514. claude_mpm/services/mcp_gateway/main.py +0 -589
  515. claude_mpm/services/mcp_gateway/registry/__init__.py +0 -12
  516. claude_mpm/services/mcp_gateway/registry/service_registry.py +0 -412
  517. claude_mpm/services/mcp_gateway/registry/tool_registry.py +0 -489
  518. claude_mpm/services/mcp_gateway/server/__init__.py +0 -15
  519. claude_mpm/services/mcp_gateway/server/mcp_gateway.py +0 -419
  520. claude_mpm/services/mcp_gateway/server/stdio_handler.py +0 -372
  521. claude_mpm/services/mcp_gateway/server/stdio_server.py +0 -714
  522. claude_mpm/services/mcp_gateway/tools/__init__.py +0 -36
  523. claude_mpm/services/mcp_gateway/tools/base_adapter.py +0 -485
  524. claude_mpm/services/mcp_gateway/tools/document_summarizer.py +0 -789
  525. claude_mpm/services/mcp_gateway/tools/external_mcp_services.py +0 -654
  526. claude_mpm/services/mcp_gateway/tools/health_check_tool.py +0 -456
  527. claude_mpm/services/mcp_gateway/tools/hello_world.py +0 -551
  528. claude_mpm/services/mcp_gateway/tools/kuzu_memory_service.py +0 -551
  529. claude_mpm/services/mcp_gateway/utils/__init__.py +0 -14
  530. claude_mpm/services/mcp_gateway/utils/package_version_checker.py +0 -160
  531. claude_mpm/services/mcp_gateway/utils/update_preferences.py +0 -170
  532. claude_mpm/skills/bundled/collaboration/brainstorming/SKILL.md +0 -79
  533. claude_mpm/skills/bundled/collaboration/dispatching-parallel-agents/SKILL.md +0 -178
  534. claude_mpm/skills/bundled/collaboration/dispatching-parallel-agents/references/agent-prompts.md +0 -577
  535. claude_mpm/skills/bundled/collaboration/dispatching-parallel-agents/references/coordination-patterns.md +0 -467
  536. claude_mpm/skills/bundled/collaboration/dispatching-parallel-agents/references/examples.md +0 -537
  537. claude_mpm/skills/bundled/collaboration/dispatching-parallel-agents/references/troubleshooting.md +0 -730
  538. claude_mpm/skills/bundled/collaboration/requesting-code-review/SKILL.md +0 -112
  539. claude_mpm/skills/bundled/collaboration/requesting-code-review/references/code-reviewer-template.md +0 -146
  540. claude_mpm/skills/bundled/collaboration/requesting-code-review/references/review-examples.md +0 -412
  541. claude_mpm/skills/bundled/collaboration/writing-plans/SKILL.md +0 -81
  542. claude_mpm/skills/bundled/collaboration/writing-plans/references/best-practices.md +0 -362
  543. claude_mpm/skills/bundled/collaboration/writing-plans/references/plan-structure-templates.md +0 -312
  544. claude_mpm/skills/bundled/debugging/root-cause-tracing/SKILL.md +0 -152
  545. claude_mpm/skills/bundled/debugging/root-cause-tracing/references/advanced-techniques.md +0 -668
  546. claude_mpm/skills/bundled/debugging/root-cause-tracing/references/examples.md +0 -587
  547. claude_mpm/skills/bundled/debugging/root-cause-tracing/references/integration.md +0 -438
  548. claude_mpm/skills/bundled/debugging/root-cause-tracing/references/tracing-techniques.md +0 -391
  549. claude_mpm/skills/bundled/debugging/systematic-debugging/CREATION-LOG.md +0 -119
  550. claude_mpm/skills/bundled/debugging/systematic-debugging/SKILL.md +0 -148
  551. claude_mpm/skills/bundled/debugging/systematic-debugging/references/anti-patterns.md +0 -483
  552. claude_mpm/skills/bundled/debugging/systematic-debugging/references/examples.md +0 -452
  553. claude_mpm/skills/bundled/debugging/systematic-debugging/references/troubleshooting.md +0 -449
  554. claude_mpm/skills/bundled/debugging/systematic-debugging/references/workflow.md +0 -411
  555. claude_mpm/skills/bundled/debugging/systematic-debugging/test-academic.md +0 -14
  556. claude_mpm/skills/bundled/debugging/systematic-debugging/test-pressure-1.md +0 -58
  557. claude_mpm/skills/bundled/debugging/systematic-debugging/test-pressure-2.md +0 -68
  558. claude_mpm/skills/bundled/debugging/systematic-debugging/test-pressure-3.md +0 -69
  559. claude_mpm/skills/bundled/debugging/verification-before-completion/SKILL.md +0 -131
  560. claude_mpm/skills/bundled/debugging/verification-before-completion/references/gate-function.md +0 -325
  561. claude_mpm/skills/bundled/debugging/verification-before-completion/references/integration-and-workflows.md +0 -490
  562. claude_mpm/skills/bundled/debugging/verification-before-completion/references/red-flags-and-failures.md +0 -425
  563. claude_mpm/skills/bundled/debugging/verification-before-completion/references/verification-patterns.md +0 -499
  564. claude_mpm/skills/bundled/main/artifacts-builder/SKILL.md +0 -86
  565. claude_mpm/skills/bundled/main/internal-comms/SKILL.md +0 -43
  566. claude_mpm/skills/bundled/main/internal-comms/examples/3p-updates.md +0 -47
  567. claude_mpm/skills/bundled/main/internal-comms/examples/company-newsletter.md +0 -65
  568. claude_mpm/skills/bundled/main/internal-comms/examples/faq-answers.md +0 -30
  569. claude_mpm/skills/bundled/main/internal-comms/examples/general-comms.md +0 -16
  570. claude_mpm/skills/bundled/main/mcp-builder/SKILL.md +0 -160
  571. claude_mpm/skills/bundled/main/mcp-builder/reference/design_principles.md +0 -412
  572. claude_mpm/skills/bundled/main/mcp-builder/reference/evaluation.md +0 -602
  573. claude_mpm/skills/bundled/main/mcp-builder/reference/mcp_best_practices.md +0 -915
  574. claude_mpm/skills/bundled/main/mcp-builder/reference/node_mcp_server.md +0 -916
  575. claude_mpm/skills/bundled/main/mcp-builder/reference/python_mcp_server.md +0 -752
  576. claude_mpm/skills/bundled/main/mcp-builder/reference/workflow.md +0 -1237
  577. claude_mpm/skills/bundled/main/skill-creator/SKILL.md +0 -189
  578. claude_mpm/skills/bundled/main/skill-creator/references/best-practices.md +0 -500
  579. claude_mpm/skills/bundled/main/skill-creator/references/creation-workflow.md +0 -464
  580. claude_mpm/skills/bundled/main/skill-creator/references/examples.md +0 -619
  581. claude_mpm/skills/bundled/main/skill-creator/references/progressive-disclosure.md +0 -437
  582. claude_mpm/skills/bundled/main/skill-creator/references/skill-structure.md +0 -231
  583. claude_mpm/skills/bundled/php/espocrm-development/SKILL.md +0 -170
  584. claude_mpm/skills/bundled/php/espocrm-development/references/architecture.md +0 -602
  585. claude_mpm/skills/bundled/php/espocrm-development/references/common-tasks.md +0 -821
  586. claude_mpm/skills/bundled/php/espocrm-development/references/development-workflow.md +0 -742
  587. claude_mpm/skills/bundled/php/espocrm-development/references/frontend-customization.md +0 -726
  588. claude_mpm/skills/bundled/php/espocrm-development/references/hooks-and-services.md +0 -764
  589. claude_mpm/skills/bundled/php/espocrm-development/references/testing-debugging.md +0 -831
  590. claude_mpm/skills/bundled/rust/desktop-applications/SKILL.md +0 -226
  591. claude_mpm/skills/bundled/rust/desktop-applications/references/architecture-patterns.md +0 -901
  592. claude_mpm/skills/bundled/rust/desktop-applications/references/native-gui-frameworks.md +0 -901
  593. claude_mpm/skills/bundled/rust/desktop-applications/references/platform-integration.md +0 -775
  594. claude_mpm/skills/bundled/rust/desktop-applications/references/state-management.md +0 -937
  595. claude_mpm/skills/bundled/rust/desktop-applications/references/tauri-framework.md +0 -770
  596. claude_mpm/skills/bundled/rust/desktop-applications/references/testing-deployment.md +0 -961
  597. claude_mpm/skills/bundled/testing/condition-based-waiting/SKILL.md +0 -119
  598. claude_mpm/skills/bundled/testing/condition-based-waiting/references/patterns-and-implementation.md +0 -253
  599. claude_mpm/skills/bundled/testing/test-driven-development/SKILL.md +0 -145
  600. claude_mpm/skills/bundled/testing/test-driven-development/references/anti-patterns.md +0 -543
  601. claude_mpm/skills/bundled/testing/test-driven-development/references/examples.md +0 -741
  602. claude_mpm/skills/bundled/testing/test-driven-development/references/integration.md +0 -470
  603. claude_mpm/skills/bundled/testing/test-driven-development/references/philosophy.md +0 -458
  604. claude_mpm/skills/bundled/testing/test-driven-development/references/workflow.md +0 -639
  605. claude_mpm/skills/bundled/testing/testing-anti-patterns/SKILL.md +0 -140
  606. claude_mpm/skills/bundled/testing/testing-anti-patterns/references/completeness-anti-patterns.md +0 -572
  607. claude_mpm/skills/bundled/testing/testing-anti-patterns/references/core-anti-patterns.md +0 -411
  608. claude_mpm/skills/bundled/testing/testing-anti-patterns/references/detection-guide.md +0 -569
  609. claude_mpm/skills/bundled/testing/testing-anti-patterns/references/tdd-connection.md +0 -695
  610. claude_mpm/skills/bundled/testing/webapp-testing/SKILL.md +0 -184
  611. claude_mpm/skills/bundled/testing/webapp-testing/decision-tree.md +0 -459
  612. claude_mpm/skills/bundled/testing/webapp-testing/playwright-patterns.md +0 -479
  613. claude_mpm/skills/bundled/testing/webapp-testing/reconnaissance-pattern.md +0 -687
  614. claude_mpm/skills/bundled/testing/webapp-testing/server-management.md +0 -758
  615. claude_mpm/skills/bundled/testing/webapp-testing/troubleshooting.md +0 -868
  616. claude_mpm-4.24.0.dist-info/entry_points.txt +0 -10
  617. claude_mpm-4.24.0.dist-info/licenses/LICENSE +0 -21
  618. /claude_mpm/agents/templates/{git_file_tracking.md → git-file-tracking.md} +0 -0
  619. /claude_mpm/agents/templates/{pm_examples.md → pm-examples.md} +0 -0
  620. /claude_mpm/agents/templates/{response_format.md → response-format.md} +0 -0
  621. /claude_mpm/agents/templates/{validation_templates.md → validation-templates.md} +0 -0
  622. {claude_mpm-4.24.0.dist-info → claude_mpm-5.4.41.dist-info}/WHEEL +0 -0
  623. {claude_mpm-4.24.0.dist-info → claude_mpm-5.4.41.dist-info}/top_level.txt +0 -0
claude_mpm/cli/startup.py CHANGED
@@ -10,6 +10,128 @@ Part of cli/__init__.py refactoring to reduce file size and improve modularity.
10
10
 
11
11
  import os
12
12
  import sys
13
+ from pathlib import Path
14
+
15
+
16
+ def sync_hooks_on_startup(quiet: bool = False) -> bool:
17
+ """Ensure hooks are up-to-date on startup.
18
+
19
+ WHY: Users can have stale hook configurations in settings.json that cause errors.
20
+ Reinstalling hooks ensures the hook format matches the current code.
21
+
22
+ DESIGN DECISION: Shows brief status message on success for user awareness.
23
+ Failures are logged but don't prevent startup to ensure claude-mpm remains functional.
24
+
25
+ Args:
26
+ quiet: If True, suppress all output (used internally)
27
+
28
+ Returns:
29
+ bool: True if hooks were synced successfully, False otherwise
30
+ """
31
+ try:
32
+ from ..hooks.claude_hooks.installer import HookInstaller
33
+
34
+ installer = HookInstaller()
35
+
36
+ # Show brief status (hooks sync is fast)
37
+ if not quiet:
38
+ print("Syncing Claude Code hooks...", end=" ", flush=True)
39
+
40
+ # Reinstall hooks (force=True ensures update)
41
+ success = installer.install_hooks(force=True)
42
+
43
+ if not quiet:
44
+ if success:
45
+ print("✓")
46
+ else:
47
+ print("(skipped)")
48
+
49
+ return success
50
+
51
+ except Exception as e:
52
+ if not quiet:
53
+ print("(error)")
54
+ # Log but don't fail startup
55
+ from ..core.logger import get_logger
56
+
57
+ logger = get_logger("startup")
58
+ logger.warning(f"Hook sync failed (non-fatal): {e}")
59
+ return False
60
+
61
+
62
+ def cleanup_legacy_agent_cache() -> None:
63
+ """Remove legacy hierarchical agent cache directories.
64
+
65
+ WHY: Old agent cache used category-based directory structure directly in cache.
66
+ New structure uses remote source paths. This cleanup prevents confusion from
67
+ stale cache directories.
68
+
69
+ Old structure (removed):
70
+ ~/.claude-mpm/cache/agents/engineer/
71
+ ~/.claude-mpm/cache/agents/ops/
72
+ ~/.claude-mpm/cache/agents/qa/
73
+ ...
74
+
75
+ New structure (kept):
76
+ ~/.claude-mpm/cache/agents/bobmatnyc/claude-mpm-agents/agents/...
77
+
78
+ DESIGN DECISION: Runs early in startup before agent deployment to ensure
79
+ clean cache state. Removes only known legacy directories to avoid deleting
80
+ user data.
81
+ """
82
+ import shutil
83
+ from pathlib import Path
84
+
85
+ from ..core.logger import get_logger
86
+
87
+ logger = get_logger("startup")
88
+
89
+ cache_dir = Path.home() / ".claude-mpm" / "cache" / "agents"
90
+ if not cache_dir.exists():
91
+ return
92
+
93
+ # Known legacy category directories (from old hierarchical structure)
94
+ legacy_dirs = [
95
+ "claude-mpm",
96
+ "documentation",
97
+ "engineer",
98
+ "ops",
99
+ "qa",
100
+ "security",
101
+ "universal",
102
+ ]
103
+
104
+ removed = []
105
+
106
+ # Remove legacy category directories
107
+ for dir_name in legacy_dirs:
108
+ legacy_path = cache_dir / dir_name
109
+ if legacy_path.exists() and legacy_path.is_dir():
110
+ try:
111
+ shutil.rmtree(legacy_path)
112
+ removed.append(dir_name)
113
+ except Exception as e:
114
+ logger.debug(f"Failed to remove legacy directory {dir_name}: {e}")
115
+
116
+ # Also remove stray BASE-AGENT.md in cache root
117
+ base_agent = cache_dir / "BASE-AGENT.md"
118
+ if base_agent.exists():
119
+ try:
120
+ base_agent.unlink()
121
+ removed.append("BASE-AGENT.md")
122
+ except Exception as e:
123
+ logger.debug(f"Failed to remove BASE-AGENT.md: {e}")
124
+
125
+ if removed:
126
+ logger.info(f"Cleaned up legacy agent cache: {', '.join(removed)}")
127
+
128
+
129
+ def check_legacy_cache() -> None:
130
+ """Deprecated: Legacy cache checking is no longer needed.
131
+
132
+ This function is kept for backward compatibility but does nothing.
133
+ All agent cache operations now use the standardized cache/agents/ directory.
134
+ """
13
135
 
14
136
 
15
137
  def setup_early_environment(argv):
@@ -19,23 +141,34 @@ def setup_early_environment(argv):
19
141
  WHY: Some commands need special environment handling before any logging
20
142
  or service initialization occurs.
21
143
 
144
+ CRITICAL: Suppress ALL logging by default until setup_mcp_server_logging()
145
+ configures the user's preference. This prevents early loggers (like
146
+ ProjectInitializer and service.* loggers) from logging at INFO level before
147
+ we know the user's logging preference.
148
+
22
149
  Args:
23
150
  argv: Command line arguments
24
151
 
25
152
  Returns:
26
153
  Processed argv list
27
154
  """
155
+ import logging
156
+
28
157
  # Disable telemetry and set cleanup flags early
29
158
  os.environ.setdefault("DISABLE_TELEMETRY", "1")
30
159
  os.environ.setdefault("CLAUDE_MPM_SKIP_CLEANUP", "0")
31
160
 
32
- # EARLY CHECK: Suppress logging for configure command
161
+ # CRITICAL: Suppress ALL logging by default
162
+ # This catches all loggers (claude_mpm.*, service.*, framework_loader, etc.)
163
+ # This will be overridden by setup_mcp_server_logging() based on user preference
164
+ logging.getLogger().setLevel(logging.CRITICAL + 1) # Root logger catches everything
165
+
166
+ # Process argv
33
167
  if argv is None:
34
168
  argv = sys.argv[1:]
35
- if "configure" in argv or (len(argv) > 0 and argv[0] == "configure"):
36
- import logging
37
169
 
38
- logging.getLogger("claude_mpm").setLevel(logging.WARNING)
170
+ # EARLY CHECK: Additional suppression for configure command
171
+ if "configure" in argv or (len(argv) > 0 and argv[0] == "configure"):
39
172
  os.environ["CLAUDE_MPM_SKIP_CLEANUP"] = "1"
40
173
 
41
174
  return argv
@@ -86,7 +219,7 @@ def deploy_bundled_skills():
86
219
  WHY: Automatically deploy skills from the bundled/ directory to .claude/skills/
87
220
  to ensure skills are available for agents without manual intervention.
88
221
 
89
- DESIGN DECISION: Deployment happens silently on startup with logging only.
222
+ DESIGN DECISION: Deployment happens with minimal feedback (checkmark on success).
90
223
  Failures are logged but don't block startup to ensure claude-mpm remains
91
224
  functional even if skills deployment fails. Respects auto_deploy config setting.
92
225
  """
@@ -117,9 +250,13 @@ def deploy_bundled_skills():
117
250
  logger = get_logger("cli")
118
251
 
119
252
  if deployment_result.get("deployed"):
120
- logger.info(
121
- f"Skills: Deployed {len(deployment_result['deployed'])} skill(s)"
122
- )
253
+ # Show simple feedback for deployed skills
254
+ deployed_count = len(deployment_result["deployed"])
255
+ print(f"✓ Bundled skills ready ({deployed_count} deployed)", flush=True)
256
+ logger.info(f"Skills: Deployed {deployed_count} skill(s)")
257
+ elif not deployment_result.get("errors"):
258
+ # No deployment needed, skills already present
259
+ print("✓ Bundled skills ready", flush=True)
123
260
 
124
261
  if deployment_result.get("errors"):
125
262
  logger.warning(
@@ -142,7 +279,8 @@ def discover_and_link_runtime_skills():
142
279
  WHY: Automatically discover and link skills added to .claude/skills/
143
280
  without requiring manual configuration.
144
281
 
145
- DESIGN DECISION: Failures are logged but don't block startup to ensure
282
+ DESIGN DECISION: Provides simple feedback on completion.
283
+ Failures are logged but don't block startup to ensure
146
284
  claude-mpm remains functional even if skills discovery fails.
147
285
  """
148
286
  try:
@@ -151,6 +289,8 @@ def discover_and_link_runtime_skills():
151
289
  )
152
290
 
153
291
  discover_skills()
292
+ # Show simple success feedback
293
+ print("✓ Runtime skills linked", flush=True)
154
294
  except Exception as e:
155
295
  # Import logger here to avoid circular imports
156
296
  from ..core.logger import get_logger
@@ -160,18 +300,1116 @@ def discover_and_link_runtime_skills():
160
300
  # Continue execution - skills discovery failure shouldn't block startup
161
301
 
162
302
 
303
+ def deploy_output_style_on_startup():
304
+ """
305
+ Deploy claude-mpm output styles to PROJECT-LEVEL directory on CLI startup.
306
+
307
+ WHY: Automatically deploy output styles to ensure consistent, professional
308
+ communication without emojis and exclamation points. Styles are project-specific
309
+ to allow different projects to have different communication styles.
310
+
311
+ DESIGN DECISION: This is non-blocking and idempotent. Deploys to project-level
312
+ directory (.claude/settings/output-styles/) instead of user-level to maintain
313
+ project isolation.
314
+
315
+ Deploys two styles:
316
+ - claude-mpm-style.md (professional mode)
317
+ - claude-mpm-teacher.md (teaching mode)
318
+ """
319
+ try:
320
+ import shutil
321
+ from pathlib import Path
322
+
323
+ # Source files (in framework package)
324
+ package_dir = Path(__file__).parent.parent / "agents"
325
+ professional_source = package_dir / "CLAUDE_MPM_OUTPUT_STYLE.md"
326
+ teacher_source = package_dir / "CLAUDE_MPM_TEACHER_OUTPUT_STYLE.md"
327
+
328
+ # Target directory (PROJECT-LEVEL, not user-level)
329
+ project_dir = Path.cwd()
330
+ output_styles_dir = project_dir / ".claude" / "settings" / "output-styles"
331
+ professional_target = output_styles_dir / "claude-mpm-style.md"
332
+ teacher_target = output_styles_dir / "claude-mpm-teacher.md"
333
+
334
+ # Create directory if it doesn't exist
335
+ output_styles_dir.mkdir(parents=True, exist_ok=True)
336
+
337
+ # Check if already deployed (both files exist and have content)
338
+ already_deployed = (
339
+ professional_target.exists()
340
+ and teacher_target.exists()
341
+ and professional_target.stat().st_size > 0
342
+ and teacher_target.stat().st_size > 0
343
+ )
344
+
345
+ if already_deployed:
346
+ # Show feedback that output styles are ready
347
+ print("✓ Output styles ready", flush=True)
348
+ return
349
+
350
+ # Deploy both styles
351
+ deployed_count = 0
352
+ if professional_source.exists():
353
+ shutil.copy2(professional_source, professional_target)
354
+ deployed_count += 1
355
+
356
+ if teacher_source.exists():
357
+ shutil.copy2(teacher_source, teacher_target)
358
+ deployed_count += 1
359
+
360
+ if deployed_count > 0:
361
+ print(f"✓ Output styles deployed ({deployed_count} styles)", flush=True)
362
+ else:
363
+ # Source files missing - log but don't fail
364
+ from ..core.logger import get_logger
365
+
366
+ logger = get_logger("cli")
367
+ logger.debug("Output style source files not found")
368
+
369
+ except Exception as e:
370
+ # Non-critical - log but don't fail startup
371
+ from ..core.logger import get_logger
372
+
373
+ logger = get_logger("cli")
374
+ logger.debug(f"Failed to deploy output styles: {e}")
375
+ # Continue execution - output style deployment shouldn't block startup
376
+
377
+
378
+ def _cleanup_orphaned_agents(deploy_target: Path, deployed_agents: list[str]) -> int:
379
+ """Remove agents that are managed by claude-mpm but no longer deployed.
380
+
381
+ WHY: When agent configurations change, old agents should be removed to avoid
382
+ confusion and stale agent references. Only removes claude-mpm managed agents,
383
+ leaving user-created agents untouched.
384
+
385
+ SAFETY: Only removes files with claude-mpm ownership markers in frontmatter.
386
+ Files without frontmatter or without ownership indicators are preserved.
387
+
388
+ Args:
389
+ deploy_target: Path to .claude/agents/ directory
390
+ deployed_agents: List of agent filenames that should remain
391
+
392
+ Returns:
393
+ Number of agents removed
394
+ """
395
+ import re
396
+
397
+ import yaml
398
+
399
+ from ..core.logger import get_logger
400
+
401
+ logger = get_logger("cli")
402
+ removed_count = 0
403
+ deployed_set = set(deployed_agents)
404
+
405
+ if not deploy_target.exists():
406
+ return 0
407
+
408
+ # Scan all .md files in agents directory
409
+ for agent_file in deploy_target.glob("*.md"):
410
+ # Skip hidden files
411
+ if agent_file.name.startswith("."):
412
+ continue
413
+
414
+ # Skip if this agent should remain deployed
415
+ if agent_file.name in deployed_set:
416
+ continue
417
+
418
+ # Check if this is a claude-mpm managed agent
419
+ try:
420
+ content = agent_file.read_text(encoding="utf-8")
421
+
422
+ # Parse YAML frontmatter
423
+ if content.startswith("---"):
424
+ match = re.match(r"^---\n(.*?)\n---", content, re.DOTALL)
425
+ if match:
426
+ frontmatter = yaml.safe_load(match.group(1))
427
+
428
+ # Check ownership indicators
429
+ is_ours = False
430
+ if frontmatter:
431
+ author = frontmatter.get("author", "")
432
+ source = frontmatter.get("source", "")
433
+ agent_id = frontmatter.get("agent_id", "")
434
+
435
+ # It's ours if it has any of these markers
436
+ if (
437
+ "Claude MPM" in str(author)
438
+ or source == "remote"
439
+ or agent_id
440
+ ):
441
+ is_ours = True
442
+
443
+ if is_ours:
444
+ # Safe to remove - it's our agent but not deployed
445
+ agent_file.unlink()
446
+ removed_count += 1
447
+ logger.info(f"Removed orphaned agent: {agent_file.name}")
448
+
449
+ except Exception as e:
450
+ logger.debug(f"Could not check agent {agent_file.name}: {e}")
451
+ # Don't remove if we can't verify ownership
452
+
453
+ return removed_count
454
+
455
+
456
+ def sync_remote_agents_on_startup():
457
+ """
458
+ Synchronize agent templates from remote sources on startup.
459
+
460
+ WHY: Ensures agents are up-to-date from remote Git sources (GitHub)
461
+ without manual intervention. Uses ETag-based caching for efficient
462
+ updates (95%+ bandwidth reduction).
463
+
464
+ DESIGN DECISION: Non-blocking synchronization that doesn't prevent
465
+ startup if network is unavailable. Failures are logged but don't
466
+ block startup to ensure claude-mpm remains functional.
467
+
468
+ Workflow:
469
+ 1. Cleanup legacy agent cache directories (if any)
470
+ 2. Sync all enabled Git sources (download/cache files) - Phase 1 progress bar
471
+ 3. Deploy agents to ~/.claude/agents/ - Phase 2 progress bar
472
+ 4. Cleanup orphaned agents (ours but no longer deployed) - Phase 3
473
+ 5. Log deployment results
474
+ """
475
+ # Cleanup legacy cache directories first (before syncing)
476
+ cleanup_legacy_agent_cache()
477
+
478
+ # DEPRECATED: Legacy warning - replaced by automatic cleanup above
479
+ check_legacy_cache()
480
+
481
+ try:
482
+ from ..core.shared.config_loader import ConfigLoader
483
+ from ..services.agents.deployment.agent_deployment import AgentDeploymentService
484
+ from ..services.agents.startup_sync import sync_agents_on_startup
485
+ from ..services.profile_manager import ProfileManager
486
+ from ..utils.progress import ProgressBar
487
+
488
+ # Load active profile if configured
489
+ # Get project root (where .claude-mpm exists)
490
+ from pathlib import Path
491
+ project_root = Path.cwd()
492
+
493
+ profile_manager = ProfileManager(project_dir=project_root)
494
+ config_loader = ConfigLoader()
495
+ main_config = config_loader.load_main_config()
496
+ active_profile = main_config.get("active_profile")
497
+
498
+ if active_profile:
499
+ success = profile_manager.load_profile(active_profile)
500
+ if success:
501
+ summary = profile_manager.get_filtering_summary()
502
+ from ..core.logger import get_logger
503
+
504
+ logger = get_logger("cli")
505
+ logger.info(
506
+ f"Profile '{active_profile}' active: "
507
+ f"{summary['enabled_agents_count']} agents enabled"
508
+ )
509
+
510
+ # Phase 1: Sync files from Git sources
511
+ result = sync_agents_on_startup()
512
+
513
+ # Only proceed with deployment if sync was enabled and ran
514
+ if result.get("enabled") and result.get("sources_synced", 0) > 0:
515
+ from ..core.logger import get_logger
516
+
517
+ logger = get_logger("cli")
518
+
519
+ downloaded = result.get("total_downloaded", 0)
520
+ cached = result.get("cache_hits", 0)
521
+ duration = result.get("duration_ms", 0)
522
+
523
+ if downloaded > 0 or cached > 0:
524
+ logger.debug(
525
+ f"Agent sync: {downloaded} updated, {cached} cached ({duration}ms)"
526
+ )
527
+
528
+ # Log errors if any
529
+ errors = result.get("errors", [])
530
+ if errors:
531
+ logger.warning(f"Agent sync completed with {len(errors)} errors")
532
+
533
+ # Phase 2: Deploy agents from cache to ~/.claude/agents/
534
+ # This mirrors the skills deployment pattern (lines 371-407)
535
+ try:
536
+ # Initialize deployment service with profile-filtered configuration
537
+ from ..core.config import Config
538
+
539
+ deploy_config = None
540
+ if active_profile and profile_manager.active_profile:
541
+ # Create config with excluded agents based on profile
542
+ # Get all agents that should be excluded (not in enabled list)
543
+ from pathlib import Path
544
+
545
+ cache_dir = Path.home() / ".claude-mpm" / "cache" / "agents"
546
+ if cache_dir.exists():
547
+ # Find all agent files
548
+ all_agent_files = [
549
+ f
550
+ for f in cache_dir.rglob("*.md")
551
+ if "/agents/" in str(f)
552
+ and str(f).count("/agents/") == 1
553
+ and f.stem.lower() != "base-agent"
554
+ ]
555
+
556
+ # Build exclusion list for agents not in profile
557
+ excluded_agents = []
558
+ for agent_file in all_agent_files:
559
+ agent_name = agent_file.stem
560
+ if not profile_manager.is_agent_enabled(agent_name):
561
+ excluded_agents.append(agent_name)
562
+
563
+ if excluded_agents:
564
+ # Get singleton config and update with profile settings
565
+ # BUGFIX: Config is a singleton that ignores dict parameter if already initialized.
566
+ # Creating Config({...}) doesn't store excluded_agents - use set() instead.
567
+ deploy_config = Config()
568
+ deploy_config.set("agent_deployment.excluded_agents", excluded_agents)
569
+ deploy_config.set("agent_deployment.filter_non_mpm_agents", False)
570
+ deploy_config.set("agent_deployment.case_sensitive", False)
571
+ deploy_config.set("agent_deployment.exclude_dependencies", False)
572
+ logger.info(
573
+ f"Profile '{active_profile}': Excluding {len(excluded_agents)} agents from deployment"
574
+ )
575
+
576
+ deployment_service = AgentDeploymentService(config=deploy_config)
577
+
578
+ # Count agents in cache to show accurate progress
579
+ from pathlib import Path
580
+
581
+ cache_dir = Path.home() / ".claude-mpm" / "cache" / "agents"
582
+ agent_count = 0
583
+
584
+ if cache_dir.exists():
585
+ # BUGFIX (cache-count-inflation): Clean up stale cache files
586
+ # from old repositories before counting to prevent inflated counts.
587
+ # Issue: Old caches like bobmatnyc/claude-mpm-agents/agents/
588
+ # were counted alongside current agents, inflating count
589
+ # from 44 to 85.
590
+ #
591
+ # Solution: Remove files with nested /agents/ paths
592
+ # (e.g., cache/agents/user/repo/agents/...)
593
+ # Keep only current agents (e.g., cache/agents/engineer/...)
594
+ removed_count = 0
595
+ stale_dirs = set()
596
+
597
+ for md_file in cache_dir.rglob("*.md"):
598
+ # Stale cache files have multiple /agents/ in their path
599
+ # Current: ~/.claude-mpm/cache/agents/engineer/...
600
+ # (1 occurrence)
601
+ # Old: ~/.claude-mpm/cache/agents/bobmatnyc/.../agents/...
602
+ # (2+ occurrences)
603
+ if str(md_file).count("/agents/") > 1:
604
+ # Track parent directory for cleanup
605
+ # Extract subdirectory under cache/agents/
606
+ # (e.g., "bobmatnyc")
607
+ parts = md_file.parts
608
+ cache_agents_idx = parts.index("agents")
609
+ if cache_agents_idx + 1 < len(parts):
610
+ stale_subdir = parts[cache_agents_idx + 1]
611
+ # Only remove if it's not a known category directory
612
+ if stale_subdir not in [
613
+ "engineer",
614
+ "ops",
615
+ "qa",
616
+ "universal",
617
+ "documentation",
618
+ "claude-mpm",
619
+ "security",
620
+ ]:
621
+ stale_dirs.add(cache_dir / stale_subdir)
622
+
623
+ md_file.unlink()
624
+ removed_count += 1
625
+
626
+ # Remove empty stale directories
627
+ for stale_dir in stale_dirs:
628
+ if stale_dir.exists() and stale_dir.is_dir():
629
+ try:
630
+ # Remove directory and all contents
631
+ import shutil
632
+
633
+ shutil.rmtree(stale_dir)
634
+ except Exception:
635
+ pass # Ignore cleanup errors
636
+
637
+ if removed_count > 0:
638
+ from loguru import logger
639
+
640
+ logger.info(
641
+ f"Cleaned up {removed_count} stale cache files "
642
+ f"from old repositories"
643
+ )
644
+
645
+ # Count MD files in cache (agent markdown files from
646
+ # current repos)
647
+ # BUGFIX: Only count files in agent directories,
648
+ # not docs/templates/READMEs
649
+ # Valid agent paths must contain "/agents/" exactly ONCE
650
+ # (current structure)
651
+ # Exclude PM templates, BASE-AGENT, and documentation files
652
+ pm_templates = {
653
+ "base-agent.md",
654
+ "circuit_breakers.md",
655
+ "pm_examples.md",
656
+ "pm_red_flags.md",
657
+ "research_gate_examples.md",
658
+ "response_format.md",
659
+ "ticket_completeness_examples.md",
660
+ "validation_templates.md",
661
+ "git_file_tracking.md",
662
+ }
663
+ # Documentation files to exclude (by filename)
664
+ doc_files = {
665
+ "readme.md",
666
+ "changelog.md",
667
+ "contributing.md",
668
+ "implementation-summary.md",
669
+ "reorganization-plan.md",
670
+ "auto-deploy-index.md",
671
+ }
672
+
673
+ # Find all markdown files (after cleanup)
674
+ all_md_files = list(cache_dir.rglob("*.md"))
675
+
676
+ # Filter to only agent files:
677
+ # 1. Must have "/agents/" in path exactly ONCE
678
+ # (current structure)
679
+ # 2. Must not be in PM templates or doc files
680
+ # 3. Exclude BASE-AGENT.md which is not a deployable agent
681
+ # 4. Exclude build artifacts (dist/, build/, .cache/)
682
+ # to prevent double-counting
683
+ agent_files = [
684
+ f
685
+ for f in all_md_files
686
+ if (
687
+ # Must be in an agent directory (from current
688
+ # cache structure)
689
+ "/agents/" in str(f)
690
+ # NEW: Only ONE /agents/ in path (excludes old
691
+ # nested repos)
692
+ # This prevents counting old caches like
693
+ # bobmatnyc/claude-mpm-agents/agents/...
694
+ and str(f).count("/agents/") == 1
695
+ # Exclude PM templates, doc files, and BASE-AGENT
696
+ and f.name.lower() not in pm_templates
697
+ and f.name.lower() not in doc_files
698
+ and f.name.lower() != "base-agent.md"
699
+ # Exclude build artifacts (prevents double-counting
700
+ # source + built files)
701
+ and not any(
702
+ part in str(f).split("/")
703
+ for part in ["dist", "build", ".cache"]
704
+ )
705
+ )
706
+ ]
707
+ agent_count = len(agent_files)
708
+
709
+ if agent_count > 0:
710
+ # Deploy agents to project-level directory where Claude Code expects them
711
+ deploy_target = Path.cwd() / ".claude" / "agents"
712
+ deployment_result = deployment_service.deploy_agents(
713
+ target_dir=deploy_target,
714
+ force_rebuild=False, # Only deploy if versions differ
715
+ deployment_mode="update", # Version-aware updates
716
+ config=deploy_config, # Pass config to respect profile filtering
717
+ )
718
+
719
+ # Get actual counts from deployment result (reflects configured agents)
720
+ deployed = len(deployment_result.get("deployed", []))
721
+ updated = len(deployment_result.get("updated", []))
722
+ skipped = len(deployment_result.get("skipped", []))
723
+ total_configured = deployed + updated + skipped
724
+
725
+ # FALLBACK: If deployment result doesn't track skipped agents (async path),
726
+ # count existing agents in target directory as "already deployed"
727
+ # This ensures accurate reporting when agents are already up-to-date
728
+ if total_configured == 0 and deploy_target.exists():
729
+ existing_agents = list(deploy_target.glob("*.md"))
730
+ # Filter out non-agent files (e.g., README.md, INSTRUCTIONS.md)
731
+ agent_count_in_target = len(
732
+ [
733
+ f
734
+ for f in existing_agents
735
+ if not f.name.startswith(("README", "INSTRUCTIONS"))
736
+ ]
737
+ )
738
+ if agent_count_in_target > 0:
739
+ # All agents already deployed - count them as skipped
740
+ skipped = agent_count_in_target
741
+ total_configured = agent_count_in_target
742
+
743
+ # Create progress bar with actual configured agent count (not raw file count)
744
+ deploy_progress = ProgressBar(
745
+ total=total_configured if total_configured > 0 else 1,
746
+ prefix="Deploying agents",
747
+ show_percentage=True,
748
+ show_counter=True,
749
+ )
750
+
751
+ # Update progress bar to completion
752
+ deploy_progress.update(
753
+ total_configured if total_configured > 0 else 1
754
+ )
755
+
756
+ # Cleanup orphaned agents (ours but no longer deployed)
757
+ # Get list of deployed agent filenames (what should remain)
758
+ deployed_filenames = []
759
+ for agent_name in deployment_result.get("deployed", []):
760
+ deployed_filenames.append(f"{agent_name}.md")
761
+ for agent_name in deployment_result.get("updated", []):
762
+ deployed_filenames.append(f"{agent_name}.md")
763
+ for agent_name in deployment_result.get("skipped", []):
764
+ deployed_filenames.append(f"{agent_name}.md")
765
+
766
+ # Run cleanup and get count of removed agents
767
+ removed = _cleanup_orphaned_agents(
768
+ deploy_target, deployed_filenames
769
+ )
770
+
771
+ # Show total configured agents (deployed + updated + already existing)
772
+ # Include cache count for context and removed count if any
773
+ if deployed > 0 or updated > 0:
774
+ if removed > 0:
775
+ deploy_progress.finish(
776
+ f"Complete: {deployed} new, {updated} updated, {skipped} unchanged, "
777
+ f"{removed} removed ({total_configured} configured from {agent_count} files in cache)"
778
+ )
779
+ else:
780
+ deploy_progress.finish(
781
+ f"Complete: {deployed} new, {updated} updated, {skipped} unchanged "
782
+ f"({total_configured} configured from {agent_count} files in cache)"
783
+ )
784
+ elif removed > 0:
785
+ deploy_progress.finish(
786
+ f"Complete: {total_configured} agents deployed, "
787
+ f"{removed} removed ({agent_count} files in cache)"
788
+ )
789
+ else:
790
+ deploy_progress.finish(
791
+ f"Complete: {total_configured} agents deployed "
792
+ f"({agent_count} files in cache)"
793
+ )
794
+
795
+ # Display deployment errors to user (not just logs)
796
+ deploy_errors = deployment_result.get("errors", [])
797
+ if deploy_errors:
798
+ # Log for debugging
799
+ logger.warning(
800
+ f"Agent deployment completed with {len(deploy_errors)} errors: {deploy_errors}"
801
+ )
802
+
803
+ # Display errors to user with clear formatting
804
+ print("\n⚠️ Agent Deployment Errors:")
805
+
806
+ # Show first 10 errors to avoid overwhelming output
807
+ max_errors_to_show = 10
808
+ errors_to_display = deploy_errors[:max_errors_to_show]
809
+
810
+ for error in errors_to_display:
811
+ # Format error message for readability
812
+ # Errors typically come as strings like "agent.md: Error message"
813
+ print(f" - {error}")
814
+
815
+ # If more errors exist, show count
816
+ if len(deploy_errors) > max_errors_to_show:
817
+ remaining = len(deploy_errors) - max_errors_to_show
818
+ print(f" ... and {remaining} more error(s)")
819
+
820
+ # Show summary message
821
+ print(
822
+ f"\n❌ Failed to deploy {len(deploy_errors)} agent(s). Please check the error messages above."
823
+ )
824
+ print(" Run with --verbose for detailed error information.\n")
825
+
826
+ except Exception as e:
827
+ # Deployment failure shouldn't block startup
828
+ from ..core.logger import get_logger
829
+
830
+ logger = get_logger("cli")
831
+ logger.warning(f"Failed to deploy agents from cache: {e}")
832
+
833
+ except Exception as e:
834
+ # Non-critical - log but don't fail startup
835
+ from ..core.logger import get_logger
836
+
837
+ logger = get_logger("cli")
838
+ logger.debug(f"Failed to sync remote agents: {e}")
839
+ # Continue execution - agent sync failure shouldn't block startup
840
+
841
+
842
+ def sync_remote_skills_on_startup():
843
+ """
844
+ Synchronize skill templates from remote sources on startup.
845
+
846
+ WHY: Ensures skills are up-to-date from remote Git sources (GitHub)
847
+ without manual intervention. Provides consistency with agent syncing.
848
+
849
+ DESIGN DECISION: Non-blocking synchronization that doesn't prevent
850
+ startup if network is unavailable. Failures are logged but don't
851
+ block startup to ensure claude-mpm remains functional.
852
+
853
+ Workflow:
854
+ 1. Sync all enabled Git sources (download/cache files) - Phase 1 progress bar
855
+ 2. Scan deployed agents for skill requirements → save to configuration.yaml
856
+ 3. Resolve which skills to deploy (user_defined vs agent_referenced)
857
+ 4. Apply profile filtering if active
858
+ 5. Deploy resolved skills to ~/.claude/skills/ - Phase 2 progress bar
859
+ 6. Log deployment results with source indication
860
+ """
861
+ try:
862
+ from pathlib import Path
863
+
864
+ from ..config.skill_sources import SkillSourceConfiguration
865
+ from ..core.shared.config_loader import ConfigLoader
866
+ from ..services.profile_manager import ProfileManager
867
+ from ..services.skills.git_skill_source_manager import GitSkillSourceManager
868
+ from ..services.skills.selective_skill_deployer import (
869
+ get_required_skills_from_agents,
870
+ get_skills_to_deploy,
871
+ save_agent_skills_to_config,
872
+ )
873
+ from ..utils.progress import ProgressBar
874
+
875
+ # Load active profile if configured
876
+ # Get project root (where .claude-mpm exists)
877
+ project_root = Path.cwd()
878
+
879
+ profile_manager = ProfileManager(project_dir=project_root)
880
+ config_loader = ConfigLoader()
881
+ main_config = config_loader.load_main_config()
882
+ active_profile = main_config.get("active_profile")
883
+
884
+ if active_profile:
885
+ success = profile_manager.load_profile(active_profile)
886
+ if success:
887
+ from ..core.logger import get_logger
888
+
889
+ logger = get_logger("cli")
890
+ summary = profile_manager.get_filtering_summary()
891
+ logger.info(
892
+ f"Profile '{active_profile}' active: "
893
+ f"{summary['enabled_skills_count']} skills enabled, "
894
+ f"{summary['disabled_patterns_count']} patterns disabled"
895
+ )
896
+
897
+ config = SkillSourceConfiguration()
898
+ manager = GitSkillSourceManager(config)
899
+
900
+ # Get enabled sources
901
+ enabled_sources = config.get_enabled_sources()
902
+ if not enabled_sources:
903
+ return # No sources enabled, nothing to sync
904
+
905
+ # Phase 1: Sync files from Git sources
906
+ # We need to discover file count first to show accurate progress
907
+ # This requires pre-scanning repositories via GitHub API
908
+ from ..core.logger import get_logger
909
+
910
+ logger = get_logger("cli")
911
+
912
+ # Discover total file count across all sources
913
+ total_file_count = 0
914
+ total_skill_dirs = 0 # Count actual skill directories (folders with SKILL.md)
915
+
916
+ for source in enabled_sources:
917
+ try:
918
+ # Parse GitHub URL
919
+ url_parts = (
920
+ source.url.rstrip("/").replace(".git", "").split("github.com/")
921
+ )
922
+ if len(url_parts) == 2:
923
+ repo_path = url_parts[1].strip("/")
924
+ owner_repo = "/".join(repo_path.split("/")[:2])
925
+
926
+ # Use Tree API to discover all files
927
+ all_files = manager._discover_repository_files_via_tree_api(
928
+ owner_repo, source.branch
929
+ )
930
+
931
+ # Count relevant files (markdown, JSON)
932
+ relevant_files = [
933
+ f
934
+ for f in all_files
935
+ if f.endswith(".md") or f.endswith(".json") or f == ".gitignore"
936
+ ]
937
+ total_file_count += len(relevant_files)
938
+
939
+ # Count skill directories (unique directories containing SKILL.md)
940
+ skill_dirs = set()
941
+ for f in all_files:
942
+ if f.endswith("/SKILL.md"):
943
+ # Extract directory path
944
+ skill_dir = "/".join(f.split("/")[:-1])
945
+ skill_dirs.add(skill_dir)
946
+ total_skill_dirs += len(skill_dirs)
947
+
948
+ except Exception as e:
949
+ logger.debug(f"Failed to discover files for {source.id}: {e}")
950
+ # Use estimate if discovery fails
951
+ total_file_count += 150
952
+ total_skill_dirs += 50 # Estimate ~50 skills
953
+
954
+ # Create progress bar for sync phase with actual file count
955
+ # Note: We sync files (md, json, etc.), but will deploy skill directories
956
+ sync_progress = ProgressBar(
957
+ total=total_file_count if total_file_count > 0 else 1,
958
+ prefix="Syncing skill files",
959
+ show_percentage=True,
960
+ show_counter=True,
961
+ )
962
+
963
+ # Sync all sources with progress callback
964
+ results = manager.sync_all_sources(
965
+ force=False, progress_callback=sync_progress.update
966
+ )
967
+
968
+ # Finish sync progress bar with clear breakdown
969
+ downloaded = results["total_files_updated"]
970
+ cached = results["total_files_cached"]
971
+ total_files = downloaded + cached
972
+
973
+ if cached > 0:
974
+ sync_progress.finish(
975
+ f"Complete: {downloaded} downloaded, {cached} cached ({total_files} files, {total_skill_dirs} skills)"
976
+ )
977
+ else:
978
+ # All new downloads (first sync)
979
+ sync_progress.finish(
980
+ f"Complete: {downloaded} files downloaded ({total_skill_dirs} skills)"
981
+ )
982
+
983
+ # Phase 2: Scan agents and save to configuration.yaml
984
+ # This step populates configuration.yaml with agent-referenced skills
985
+ if results["synced_count"] > 0:
986
+ agents_dir = Path.cwd() / ".claude" / "agents"
987
+
988
+ # Scan agents for skill requirements
989
+ agent_skills = get_required_skills_from_agents(agents_dir)
990
+
991
+ # Save to project-level configuration.yaml
992
+ project_config_path = Path.cwd() / ".claude-mpm" / "configuration.yaml"
993
+ save_agent_skills_to_config(list(agent_skills), project_config_path)
994
+
995
+ # Phase 3: Resolve which skills to deploy (user_defined or agent_referenced)
996
+ skills_to_deploy, skill_source = get_skills_to_deploy(project_config_path)
997
+
998
+ # Phase 4: Apply profile filtering if active
999
+ if active_profile and profile_manager.active_profile:
1000
+ # Filter skills based on profile
1001
+ if skills_to_deploy:
1002
+ # Filter the resolved skill list
1003
+ original_count = len(skills_to_deploy)
1004
+ filtered_skills = [
1005
+ skill
1006
+ for skill in skills_to_deploy
1007
+ if profile_manager.is_skill_enabled(skill)
1008
+ ]
1009
+ filtered_count = original_count - len(filtered_skills)
1010
+
1011
+ # SAFEGUARD: Warn if all skills were filtered out (misconfiguration)
1012
+ if not filtered_skills and original_count > 0:
1013
+ logger.warning(
1014
+ f"Profile '{active_profile}' filtered ALL {original_count} skills. "
1015
+ f"This may indicate a naming mismatch in the profile."
1016
+ )
1017
+ elif filtered_count > 0:
1018
+ logger.info(
1019
+ f"Profile '{active_profile}' filtered {filtered_count} skills "
1020
+ f"({len(filtered_skills)} remaining)"
1021
+ )
1022
+
1023
+ skills_to_deploy = filtered_skills
1024
+ skill_source = f"{skill_source} + profile filtered"
1025
+ else:
1026
+ # No explicit skill list - filter from all available
1027
+ all_skills = manager.get_all_skills()
1028
+ filtered_skills = [
1029
+ skill["name"]
1030
+ for skill in all_skills
1031
+ if profile_manager.is_skill_enabled(skill["name"])
1032
+ ]
1033
+ skills_to_deploy = filtered_skills
1034
+ skill_source = "profile filtered"
1035
+ logger.info(
1036
+ f"Profile '{active_profile}': "
1037
+ f"{len(filtered_skills)} skills enabled from {len(all_skills)} available"
1038
+ )
1039
+
1040
+ # Get all skills to determine counts
1041
+ all_skills = manager.get_all_skills()
1042
+ total_skill_count = len(all_skills)
1043
+
1044
+ # Determine skill count based on resolution
1045
+ skill_count = (
1046
+ len(skills_to_deploy) if skills_to_deploy else total_skill_count
1047
+ )
1048
+
1049
+ if skill_count > 0:
1050
+ # Deploy skills with resolved filter
1051
+ # Deploy to project directory (like agents), not user directory
1052
+ deployment_result = manager.deploy_skills(
1053
+ target_dir=Path.cwd() / ".claude" / "skills",
1054
+ force=False,
1055
+ skill_filter=set(skills_to_deploy) if skills_to_deploy else None,
1056
+ )
1057
+
1058
+ # Get actual counts from deployment result
1059
+ deployed = deployment_result.get("deployed_count", 0)
1060
+ skipped = deployment_result.get("skipped_count", 0)
1061
+ filtered = deployment_result.get("filtered_count", 0)
1062
+ total_available = deployed + skipped
1063
+
1064
+ # Only show progress bar if there are skills to deploy
1065
+ if total_available > 0:
1066
+ deploy_progress = ProgressBar(
1067
+ total=total_available,
1068
+ prefix="Deploying skill directories",
1069
+ show_percentage=True,
1070
+ show_counter=True,
1071
+ )
1072
+ # Update progress bar to completion
1073
+ deploy_progress.update(total_available)
1074
+ else:
1075
+ # No skills to deploy - create dummy progress for message only
1076
+ deploy_progress = ProgressBar(
1077
+ total=1,
1078
+ prefix="Deploying skill directories",
1079
+ show_percentage=False,
1080
+ show_counter=False,
1081
+ )
1082
+ deploy_progress.update(1)
1083
+
1084
+ # Show total available skills (deployed + already existing)
1085
+ # Include source indication (user_defined vs agent_referenced)
1086
+ # Note: total_skill_count is from cache, total_available is what's deployed/needed
1087
+ source_label = (
1088
+ "user override" if skill_source == "user_defined" else "from agents"
1089
+ )
1090
+
1091
+ if deployed > 0:
1092
+ if filtered > 0:
1093
+ deploy_progress.finish(
1094
+ f"Complete: {deployed} new, {skipped} unchanged "
1095
+ f"({total_available} {source_label}, {filtered} files in cache)"
1096
+ )
1097
+ else:
1098
+ deploy_progress.finish(
1099
+ f"Complete: {deployed} new, {skipped} unchanged "
1100
+ f"({total_available} skills {source_label} from {total_skill_count} files in cache)"
1101
+ )
1102
+ elif filtered > 0:
1103
+ # Skills filtered means agents require fewer skills than available
1104
+ deploy_progress.finish(
1105
+ f"No skills needed ({source_label}, {total_skill_count} files in cache)"
1106
+ )
1107
+ else:
1108
+ deploy_progress.finish(
1109
+ f"Complete: {total_available} skills {source_label} "
1110
+ f"({total_skill_count} files in cache)"
1111
+ )
1112
+
1113
+ # Log deployment errors if any
1114
+ from ..core.logger import get_logger
1115
+
1116
+ logger = get_logger("cli")
1117
+
1118
+ errors = deployment_result.get("errors", [])
1119
+ if errors:
1120
+ logger.warning(
1121
+ f"Skill deployment completed with {len(errors)} errors: {errors}"
1122
+ )
1123
+
1124
+ # Log sync errors if any
1125
+ if results["failed_count"] > 0:
1126
+ logger.warning(
1127
+ f"Skill sync completed with {results['failed_count']} failures"
1128
+ )
1129
+
1130
+ except Exception as e:
1131
+ # Non-critical - log but don't fail startup
1132
+ from ..core.logger import get_logger
1133
+
1134
+ logger = get_logger("cli")
1135
+ logger.debug(f"Failed to sync remote skills: {e}")
1136
+ # Continue execution - skill sync failure shouldn't block startup
1137
+
1138
+
1139
+ def show_agent_summary():
1140
+ """
1141
+ Display agent availability summary on startup.
1142
+
1143
+ WHY: Users should see at a glance how many agents are available and installed
1144
+ without having to run /mpm-agents list.
1145
+
1146
+ DESIGN DECISION: Fast, non-blocking check that counts agents from the deployment
1147
+ directory. Shows simple "X installed / Y available" format. Failures are silent
1148
+ to avoid blocking startup.
1149
+ """
1150
+ try:
1151
+ from pathlib import Path
1152
+
1153
+ # Count deployed agents (installed)
1154
+ deploy_target = Path.cwd() / ".claude" / "agents"
1155
+ installed_count = 0
1156
+ if deploy_target.exists():
1157
+ # Count .md files, excluding README and other docs
1158
+ agent_files = [
1159
+ f
1160
+ for f in deploy_target.glob("*.md")
1161
+ if not f.name.startswith(("README", "INSTRUCTIONS", "."))
1162
+ ]
1163
+ installed_count = len(agent_files)
1164
+
1165
+ # Count available agents in cache (from remote sources)
1166
+ cache_dir = Path.home() / ".claude-mpm" / "cache" / "agents"
1167
+ available_count = 0
1168
+ if cache_dir.exists():
1169
+ # Use same filtering logic as agent deployment (lines 486-533 in startup.py)
1170
+ pm_templates = {
1171
+ "base-agent.md",
1172
+ "circuit_breakers.md",
1173
+ "pm_examples.md",
1174
+ "pm_red_flags.md",
1175
+ "research_gate_examples.md",
1176
+ "response_format.md",
1177
+ "ticket_completeness_examples.md",
1178
+ "validation_templates.md",
1179
+ "git_file_tracking.md",
1180
+ }
1181
+ doc_files = {
1182
+ "readme.md",
1183
+ "changelog.md",
1184
+ "contributing.md",
1185
+ "implementation-summary.md",
1186
+ "reorganization-plan.md",
1187
+ "auto-deploy-index.md",
1188
+ }
1189
+
1190
+ # Find all markdown files in agents/ directories
1191
+ all_md_files = list(cache_dir.rglob("*.md"))
1192
+ agent_files = [
1193
+ f
1194
+ for f in all_md_files
1195
+ if (
1196
+ "/agents/" in str(f)
1197
+ and f.name.lower() not in pm_templates
1198
+ and f.name.lower() not in doc_files
1199
+ and f.name.lower() != "base-agent.md"
1200
+ and not any(
1201
+ part in str(f).split("/")
1202
+ for part in ["dist", "build", ".cache"]
1203
+ )
1204
+ )
1205
+ ]
1206
+ available_count = len(agent_files)
1207
+
1208
+ # Display summary if we have agents
1209
+ if installed_count > 0 or available_count > 0:
1210
+ print(
1211
+ f"✓ Agents: {installed_count} deployed / {available_count} cached",
1212
+ flush=True,
1213
+ )
1214
+
1215
+ except Exception as e:
1216
+ # Silent failure - agent summary is informational only
1217
+ from ..core.logger import get_logger
1218
+
1219
+ logger = get_logger("cli")
1220
+ logger.debug(f"Failed to generate agent summary: {e}")
1221
+
1222
+
1223
+ def show_skill_summary():
1224
+ """
1225
+ Display skill availability summary on startup.
1226
+
1227
+ WHY: Users should see at a glance how many skills are deployed and available
1228
+ from collections, similar to the agent summary.
1229
+
1230
+ DESIGN DECISION: Fast, non-blocking check that counts skills from deployment
1231
+ directory and collection repos. Shows "X installed (Y available)" format.
1232
+ Failures are silent to avoid blocking startup.
1233
+ """
1234
+ try:
1235
+ from pathlib import Path
1236
+
1237
+ # Count deployed skills (installed)
1238
+ skills_dir = Path.home() / ".claude" / "skills"
1239
+ installed_count = 0
1240
+ if skills_dir.exists():
1241
+ # Count directories with SKILL.md (excludes collection repos)
1242
+ # Exclude collection directories (obra-superpowers, etc.)
1243
+ skill_dirs = [
1244
+ d
1245
+ for d in skills_dir.iterdir()
1246
+ if d.is_dir()
1247
+ and (d / "SKILL.md").exists()
1248
+ and not (d / ".git").exists() # Exclude collection repos
1249
+ ]
1250
+ installed_count = len(skill_dirs)
1251
+
1252
+ # Count available skills in collections
1253
+ available_count = 0
1254
+ if skills_dir.exists():
1255
+ # Scan all collection directories (those with .git)
1256
+ for collection_dir in skills_dir.iterdir():
1257
+ if (
1258
+ not collection_dir.is_dir()
1259
+ or not (collection_dir / ".git").exists()
1260
+ ):
1261
+ continue
1262
+
1263
+ # Count skill directories in this collection
1264
+ # Skills can be nested in: skills/category/skill-name/SKILL.md
1265
+ # or in flat structure: skill-name/SKILL.md
1266
+ for root, dirs, files in os.walk(collection_dir):
1267
+ if "SKILL.md" in files:
1268
+ # Exclude build artifacts and hidden directories (within the collection)
1269
+ # Get relative path from collection_dir to avoid excluding based on .claude parent
1270
+ root_path = Path(root)
1271
+ relative_parts = root_path.relative_to(collection_dir).parts
1272
+ if not any(
1273
+ part.startswith(".")
1274
+ or part in ["dist", "build", "__pycache__"]
1275
+ for part in relative_parts
1276
+ ):
1277
+ available_count += 1
1278
+
1279
+ # Display summary if we have skills
1280
+ if installed_count > 0 or available_count > 0:
1281
+ print(
1282
+ f"✓ Skills: {installed_count} installed ({available_count} available)",
1283
+ flush=True,
1284
+ )
1285
+
1286
+ except Exception as e:
1287
+ # Silent failure - skill summary is informational only
1288
+ from ..core.logger import get_logger
1289
+
1290
+ logger = get_logger("cli")
1291
+ logger.debug(f"Failed to generate skill summary: {e}")
1292
+
1293
+
1294
+ def verify_and_show_pm_skills():
1295
+ """Verify PM skills and display status.
1296
+
1297
+ WHY: PM skills are essential for PM agent operation.
1298
+ Shows deployment status and auto-deploys if missing.
1299
+ """
1300
+ try:
1301
+ from pathlib import Path
1302
+
1303
+ from ..services.pm_skills_deployer import PMSkillsDeployerService
1304
+
1305
+ deployer = PMSkillsDeployerService()
1306
+ project_dir = Path.cwd()
1307
+
1308
+ result = deployer.verify_pm_skills(project_dir)
1309
+
1310
+ if result.verified:
1311
+ # Show verified status
1312
+ print(f"✓ PM skills: {result.skill_count} verified", flush=True)
1313
+ else:
1314
+ # Auto-deploy if missing
1315
+ print("Deploying PM skills...", end="", flush=True)
1316
+ deploy_result = deployer.deploy_pm_skills(project_dir)
1317
+ if deploy_result.success:
1318
+ total = len(deploy_result.deployed) + len(deploy_result.skipped)
1319
+ print(f"\r✓ PM skills: {total} deployed" + " " * 20, flush=True)
1320
+ else:
1321
+ print(f"\r⚠ PM skills: deployment failed" + " " * 20, flush=True)
1322
+
1323
+ except ImportError:
1324
+ # PM skills deployer not available - skip silently
1325
+ pass
1326
+ except Exception as e:
1327
+ from ..core.logger import get_logger
1328
+
1329
+ logger = get_logger("cli")
1330
+ logger.debug(f"PM skills verification failed: {e}")
1331
+
1332
+
1333
+ def auto_install_chrome_devtools_on_startup():
1334
+ """
1335
+ Automatically install chrome-devtools-mcp on startup if enabled.
1336
+
1337
+ WHY: Browser automation capabilities should be available out-of-the-box without
1338
+ manual MCP server configuration. chrome-devtools-mcp provides powerful browser
1339
+ interaction tools for Claude Code.
1340
+
1341
+ DESIGN DECISION: Non-blocking installation that doesn't prevent startup if it fails.
1342
+ Respects user configuration setting (enabled by default). Only installs if not
1343
+ already configured in Claude.
1344
+ """
1345
+ try:
1346
+ # Check if auto-install is disabled in config
1347
+ from ..config.config_loader import ConfigLoader
1348
+
1349
+ config_loader = ConfigLoader()
1350
+ try:
1351
+ config = config_loader.load_main_config()
1352
+ chrome_devtools_config = config.get("chrome_devtools", {})
1353
+ if not chrome_devtools_config.get("auto_install", True):
1354
+ # Auto-install disabled, skip silently
1355
+ return
1356
+ except Exception:
1357
+ # If config loading fails, assume auto-install is enabled (default)
1358
+ pass
1359
+
1360
+ # Import and run chrome-devtools installation
1361
+ from ..cli.chrome_devtools_installer import auto_install_chrome_devtools
1362
+
1363
+ auto_install_chrome_devtools(quiet=False)
1364
+
1365
+ except Exception as e:
1366
+ # Import logger here to avoid circular imports
1367
+ from ..core.logger import get_logger
1368
+
1369
+ logger = get_logger("cli")
1370
+ logger.debug(f"Failed to auto-install chrome-devtools-mcp: {e}")
1371
+ # Continue execution - chrome-devtools installation failure shouldn't block startup
1372
+
1373
+
163
1374
  def run_background_services():
164
1375
  """
165
1376
  Initialize all background services on startup.
166
1377
 
167
1378
  WHY: Centralizes all startup service initialization for cleaner main().
1379
+
1380
+ NOTE: System instructions (PM_INSTRUCTIONS.md, WORKFLOW.md, MEMORY.md) and
1381
+ templates do NOT deploy automatically on startup. They only deploy when user
1382
+ explicitly requests them via agent-manager commands. This prevents unwanted
1383
+ file creation in project .claude/ directories.
1384
+ See: SystemInstructionsDeployer and agent_deployment.py line 504-509
168
1385
  """
1386
+ # Sync hooks early to ensure up-to-date configuration
1387
+ # RATIONALE: Hooks should be synced before other services to fix stale configs
1388
+ # This is fast (<100ms) and non-blocking, so it doesn't delay startup
1389
+ sync_hooks_on_startup() # Shows "Syncing Claude Code hooks... ✓"
1390
+
169
1391
  initialize_project_registry()
170
1392
  check_mcp_auto_configuration()
171
1393
  verify_mcp_gateway_startup()
172
1394
  check_for_updates_async()
173
- deploy_bundled_skills()
174
- discover_and_link_runtime_skills()
1395
+ sync_remote_agents_on_startup() # Sync agents from remote sources
1396
+ show_agent_summary() # Display agent counts after deployment
1397
+
1398
+ # Skills deployment order (precedence: remote > bundled)
1399
+ # 1. Deploy bundled skills first (base layer from package)
1400
+ # 2. Sync and deploy remote skills (Git sources, can override bundled)
1401
+ # 3. Discover and link runtime skills (user-added skills)
1402
+ # This ensures remote skills take precedence over bundled skills when names conflict
1403
+ deploy_bundled_skills() # Base layer: package-bundled skills
1404
+ sync_remote_skills_on_startup() # Override layer: Git-based skills (takes precedence)
1405
+ discover_and_link_runtime_skills() # Discovery: user-added skills
1406
+ show_skill_summary() # Display skill counts after deployment
1407
+ verify_and_show_pm_skills() # PM skills verification and status
1408
+
1409
+ deploy_output_style_on_startup()
1410
+
1411
+ # Auto-install chrome-devtools-mcp for browser automation
1412
+ auto_install_chrome_devtools_on_startup()
175
1413
 
176
1414
 
177
1415
  def setup_mcp_server_logging(args):
@@ -247,12 +1485,26 @@ def check_mcp_auto_configuration():
247
1485
  user consent.
248
1486
 
249
1487
  DESIGN DECISION: This is blocking but quick - it only runs once and has
250
- a 10-second timeout. We want to catch users on first run for the best
251
- experience.
1488
+ a 10-second timeout. Shows progress feedback during checks to avoid
1489
+ appearing frozen.
1490
+
1491
+ OPTIMIZATION: Skip ALL MCP checks for doctor and configure commands to avoid
1492
+ duplicate checks (doctor performs its own comprehensive check, configure
1493
+ allows users to select services).
252
1494
  """
1495
+ # Skip MCP service checks for the doctor and configure commands
1496
+ # The doctor command performs its own comprehensive MCP service check
1497
+ # The configure command allows users to configure which services to enable
1498
+ # Running both would cause duplicate checks and log messages (9 seconds apart)
1499
+ if len(sys.argv) > 1 and sys.argv[1] in ("doctor", "configure"):
1500
+ return
1501
+
253
1502
  try:
254
1503
  from ..services.mcp_gateway.auto_configure import check_and_configure_mcp
255
1504
 
1505
+ # Show progress feedback - this operation can take 10+ seconds
1506
+ print("Checking MCP configuration...", end="", flush=True)
1507
+
256
1508
  # This function handles all the logic:
257
1509
  # - Checks if already configured
258
1510
  # - Checks if pipx installation
@@ -261,45 +1513,18 @@ def check_mcp_auto_configuration():
261
1513
  # - Configures if user agrees
262
1514
  check_and_configure_mcp()
263
1515
 
264
- except Exception as e:
265
- # Non-critical - log but don't fail
266
- from ..core.logger import get_logger
267
-
268
- logger = get_logger("cli")
269
- logger.debug(f"MCP auto-configuration check failed: {e}")
270
-
271
- # Skip MCP service fixes for the doctor and configure commands
272
- # The doctor command performs its own comprehensive MCP service check
273
- # The configure command allows users to configure which services to enable
274
- # Running both would cause duplicate checks and log messages (9 seconds apart)
275
- if len(sys.argv) > 1 and sys.argv[1] in ("doctor", "configure"):
276
- return
277
-
278
- # Also ensure MCP services are properly configured in ~/.claude.json
279
- # This fixes incorrect paths and adds missing services
280
- try:
281
- from ..core.logger import get_logger
282
- from ..services.mcp_config_manager import MCPConfigManager
283
-
284
- logger = get_logger("cli")
285
- mcp_manager = MCPConfigManager()
286
-
287
- # Fix any corrupted installations first
288
- _fix_success, fix_message = mcp_manager.fix_mcp_service_issues()
289
- if fix_message and "Fixed:" in fix_message:
290
- logger.info(f"MCP service fixes applied: {fix_message}")
291
-
292
- # Ensure all services are configured correctly
293
- _config_success, config_message = mcp_manager.ensure_mcp_services_configured()
294
- if config_message and "Added MCP services" in config_message:
295
- logger.info(f"MCP services configured: {config_message}")
1516
+ # Clear the "Checking..." message by overwriting with spaces
1517
+ print("\r" + " " * 30 + "\r", end="", flush=True)
296
1518
 
297
1519
  except Exception as e:
1520
+ # Clear progress message on error
1521
+ print("\r" + " " * 30 + "\r", end="", flush=True)
1522
+
298
1523
  # Non-critical - log but don't fail
299
1524
  from ..core.logger import get_logger
300
1525
 
301
1526
  logger = get_logger("cli")
302
- logger.debug(f"MCP services configuration update failed: {e}")
1527
+ logger.debug(f"MCP auto-configuration check failed: {e}")
303
1528
 
304
1529
 
305
1530
  def verify_mcp_gateway_startup():
@@ -313,22 +1538,13 @@ def verify_mcp_gateway_startup():
313
1538
  DESIGN DECISION: This is non-blocking - failures are logged but don't prevent
314
1539
  startup to ensure claude-mpm remains functional even if MCP gateway has issues.
315
1540
  """
316
- # Quick verification of MCP services installation
317
- try:
318
- from ..core.logger import get_logger
319
- from ..services.mcp_service_verifier import verify_mcp_services_on_startup
320
-
321
- logger = get_logger("mcp_verify")
322
- all_ok, message = verify_mcp_services_on_startup()
323
- if not all_ok:
324
- logger.warning(message)
325
- except Exception:
326
- # Non-critical - continue with startup
327
- pass
1541
+ # DISABLED: MCP service verification removed - Claude Code handles MCP natively
1542
+ # The previous check warned about missing MCP services, but users should configure
1543
+ # MCP servers through Claude Code's native MCP management, not through claude-mpm.
1544
+ # See: https://docs.anthropic.com/en/docs/claude-code/mcp
328
1545
 
329
1546
  try:
330
1547
  import asyncio
331
- import time
332
1548
 
333
1549
  from ..core.logger import get_logger
334
1550
  from ..services.mcp_gateway.core.startup_verification import (
@@ -343,68 +1559,14 @@ def verify_mcp_gateway_startup():
343
1559
 
344
1560
  # DISABLED: Pre-warming MCP servers can interfere with Claude Code's MCP management
345
1561
  # This was causing issues with MCP server initialization and stderr handling
346
- # def run_pre_warming():
347
- # loop = None
348
- # try:
349
- # start_time = time.time()
350
- # loop = asyncio.new_event_loop()
351
- # asyncio.set_event_loop(loop)
352
- #
353
- # # Pre-warm MCP servers (especially vector search)
354
- # logger.info("Pre-warming MCP servers to eliminate startup delay...")
355
- # loop.run_until_complete(pre_warm_mcp_servers())
356
- #
357
- # pre_warm_time = time.time() - start_time
358
- # if pre_warm_time > 1.0:
359
- # logger.info(f"MCP servers pre-warmed in {pre_warm_time:.2f}s")
360
-
361
- # Dummy function to maintain structure
362
- def run_pre_warming():
363
- loop = None
364
- try:
365
- time.time()
366
- loop = asyncio.new_event_loop()
367
- asyncio.set_event_loop(loop)
1562
+ # Pre-warming functionality has been removed. Gateway verification only runs
1563
+ # if MCP gateway is not already configured.
368
1564
 
369
- # Also run gateway verification if needed
370
- if not gateway_configured:
371
- loop.run_until_complete(verify_mcp_gateway_on_startup())
372
-
373
- except Exception as e:
374
- # Non-blocking - log but don't fail
375
- logger.debug(f"MCP pre-warming error (non-critical): {e}")
376
- finally:
377
- # Properly clean up event loop to prevent kqueue warnings
378
- if loop is not None:
379
- try:
380
- # Cancel all running tasks
381
- pending = asyncio.all_tasks(loop)
382
- for task in pending:
383
- task.cancel()
384
- # Wait for tasks to complete cancellation
385
- if pending:
386
- loop.run_until_complete(
387
- asyncio.gather(*pending, return_exceptions=True)
388
- )
389
- except Exception:
390
- pass # Ignore cleanup errors
391
- finally:
392
- loop.close()
393
- # Clear the event loop reference to help with cleanup
394
- asyncio.set_event_loop(None)
395
-
396
- # Run pre-warming in background thread
397
- import threading
398
-
399
- pre_warm_thread = threading.Thread(target=run_pre_warming, daemon=True)
400
- pre_warm_thread.start()
401
-
402
- return
403
-
404
- # Run detailed verification in background if not configured
1565
+ # Run gateway verification in background if not configured
405
1566
  if not gateway_configured:
406
- # Note: We don't await this to avoid blocking startup
1567
+
407
1568
  def run_verification():
1569
+ """Background thread to verify MCP gateway configuration."""
408
1570
  loop = None
409
1571
  try:
410
1572
  loop = asyncio.new_event_loop()