claude-mpm 5.4.85__py3-none-any.whl → 5.6.76__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (322) hide show
  1. claude_mpm/VERSION +1 -1
  2. claude_mpm/agents/CLAUDE_MPM_OUTPUT_STYLE.md +8 -5
  3. claude_mpm/agents/{CLAUDE_MPM_FOUNDERS_OUTPUT_STYLE.md → CLAUDE_MPM_RESEARCH_OUTPUT_STYLE.md} +14 -6
  4. claude_mpm/agents/PM_INSTRUCTIONS.md +109 -706
  5. claude_mpm/agents/WORKFLOW.md +2 -0
  6. claude_mpm/agents/templates/circuit-breakers.md +26 -17
  7. claude_mpm/auth/__init__.py +35 -0
  8. claude_mpm/auth/callback_server.py +328 -0
  9. claude_mpm/auth/models.py +104 -0
  10. claude_mpm/auth/oauth_manager.py +266 -0
  11. claude_mpm/auth/providers/__init__.py +12 -0
  12. claude_mpm/auth/providers/base.py +165 -0
  13. claude_mpm/auth/providers/google.py +261 -0
  14. claude_mpm/auth/token_storage.py +252 -0
  15. claude_mpm/cli/commands/autotodos.py +566 -0
  16. claude_mpm/cli/commands/commander.py +216 -0
  17. claude_mpm/cli/commands/hook_errors.py +60 -60
  18. claude_mpm/cli/commands/mcp.py +29 -17
  19. claude_mpm/cli/commands/mcp_command_router.py +39 -0
  20. claude_mpm/cli/commands/mcp_service_commands.py +304 -0
  21. claude_mpm/cli/commands/monitor.py +2 -2
  22. claude_mpm/cli/commands/mpm_init/core.py +2 -2
  23. claude_mpm/cli/commands/oauth.py +481 -0
  24. claude_mpm/cli/commands/run.py +35 -3
  25. claude_mpm/cli/commands/skill_source.py +51 -2
  26. claude_mpm/cli/commands/skills.py +5 -3
  27. claude_mpm/cli/executor.py +128 -16
  28. claude_mpm/cli/helpers.py +1 -1
  29. claude_mpm/cli/parsers/base_parser.py +84 -1
  30. claude_mpm/cli/parsers/commander_parser.py +116 -0
  31. claude_mpm/cli/parsers/mcp_parser.py +79 -0
  32. claude_mpm/cli/parsers/oauth_parser.py +165 -0
  33. claude_mpm/cli/parsers/run_parser.py +10 -0
  34. claude_mpm/cli/parsers/skill_source_parser.py +4 -0
  35. claude_mpm/cli/parsers/skills_parser.py +5 -0
  36. claude_mpm/cli/startup.py +345 -40
  37. claude_mpm/cli/startup_display.py +76 -7
  38. claude_mpm/cli/startup_logging.py +2 -2
  39. claude_mpm/cli/startup_migrations.py +236 -0
  40. claude_mpm/cli/utils.py +7 -3
  41. claude_mpm/commander/__init__.py +78 -0
  42. claude_mpm/commander/adapters/__init__.py +60 -0
  43. claude_mpm/commander/adapters/auggie.py +260 -0
  44. claude_mpm/commander/adapters/base.py +288 -0
  45. claude_mpm/commander/adapters/claude_code.py +392 -0
  46. claude_mpm/commander/adapters/codex.py +237 -0
  47. claude_mpm/commander/adapters/communication.py +366 -0
  48. claude_mpm/commander/adapters/example_usage.py +310 -0
  49. claude_mpm/commander/adapters/mpm.py +389 -0
  50. claude_mpm/commander/adapters/registry.py +204 -0
  51. claude_mpm/commander/api/__init__.py +16 -0
  52. claude_mpm/commander/api/app.py +121 -0
  53. claude_mpm/commander/api/errors.py +133 -0
  54. claude_mpm/commander/api/routes/__init__.py +8 -0
  55. claude_mpm/commander/api/routes/events.py +184 -0
  56. claude_mpm/commander/api/routes/inbox.py +171 -0
  57. claude_mpm/commander/api/routes/messages.py +148 -0
  58. claude_mpm/commander/api/routes/projects.py +271 -0
  59. claude_mpm/commander/api/routes/sessions.py +226 -0
  60. claude_mpm/commander/api/routes/work.py +296 -0
  61. claude_mpm/commander/api/schemas.py +186 -0
  62. claude_mpm/commander/chat/__init__.py +7 -0
  63. claude_mpm/commander/chat/cli.py +149 -0
  64. claude_mpm/commander/chat/commands.py +124 -0
  65. claude_mpm/commander/chat/repl.py +1957 -0
  66. claude_mpm/commander/config.py +51 -0
  67. claude_mpm/commander/config_loader.py +115 -0
  68. claude_mpm/commander/core/__init__.py +10 -0
  69. claude_mpm/commander/core/block_manager.py +325 -0
  70. claude_mpm/commander/core/response_manager.py +323 -0
  71. claude_mpm/commander/daemon.py +603 -0
  72. claude_mpm/commander/env_loader.py +59 -0
  73. claude_mpm/commander/events/__init__.py +26 -0
  74. claude_mpm/commander/events/manager.py +392 -0
  75. claude_mpm/commander/frameworks/__init__.py +12 -0
  76. claude_mpm/commander/frameworks/base.py +233 -0
  77. claude_mpm/commander/frameworks/claude_code.py +58 -0
  78. claude_mpm/commander/frameworks/mpm.py +57 -0
  79. claude_mpm/commander/git/__init__.py +5 -0
  80. claude_mpm/commander/git/worktree_manager.py +212 -0
  81. claude_mpm/commander/inbox/__init__.py +16 -0
  82. claude_mpm/commander/inbox/dedup.py +128 -0
  83. claude_mpm/commander/inbox/inbox.py +224 -0
  84. claude_mpm/commander/inbox/models.py +70 -0
  85. claude_mpm/commander/instance_manager.py +868 -0
  86. claude_mpm/commander/llm/__init__.py +6 -0
  87. claude_mpm/commander/llm/openrouter_client.py +167 -0
  88. claude_mpm/commander/llm/summarizer.py +70 -0
  89. claude_mpm/commander/memory/__init__.py +45 -0
  90. claude_mpm/commander/memory/compression.py +347 -0
  91. claude_mpm/commander/memory/embeddings.py +230 -0
  92. claude_mpm/commander/memory/entities.py +310 -0
  93. claude_mpm/commander/memory/example_usage.py +290 -0
  94. claude_mpm/commander/memory/integration.py +325 -0
  95. claude_mpm/commander/memory/search.py +381 -0
  96. claude_mpm/commander/memory/store.py +657 -0
  97. claude_mpm/commander/models/__init__.py +18 -0
  98. claude_mpm/commander/models/events.py +127 -0
  99. claude_mpm/commander/models/project.py +162 -0
  100. claude_mpm/commander/models/work.py +214 -0
  101. claude_mpm/commander/parsing/__init__.py +20 -0
  102. claude_mpm/commander/parsing/extractor.py +132 -0
  103. claude_mpm/commander/parsing/output_parser.py +270 -0
  104. claude_mpm/commander/parsing/patterns.py +100 -0
  105. claude_mpm/commander/persistence/__init__.py +11 -0
  106. claude_mpm/commander/persistence/event_store.py +274 -0
  107. claude_mpm/commander/persistence/state_store.py +403 -0
  108. claude_mpm/commander/persistence/work_store.py +164 -0
  109. claude_mpm/commander/polling/__init__.py +13 -0
  110. claude_mpm/commander/polling/event_detector.py +104 -0
  111. claude_mpm/commander/polling/output_buffer.py +49 -0
  112. claude_mpm/commander/polling/output_poller.py +153 -0
  113. claude_mpm/commander/project_session.py +268 -0
  114. claude_mpm/commander/proxy/__init__.py +12 -0
  115. claude_mpm/commander/proxy/formatter.py +89 -0
  116. claude_mpm/commander/proxy/output_handler.py +191 -0
  117. claude_mpm/commander/proxy/relay.py +155 -0
  118. claude_mpm/commander/registry.py +410 -0
  119. claude_mpm/commander/runtime/__init__.py +10 -0
  120. claude_mpm/commander/runtime/executor.py +191 -0
  121. claude_mpm/commander/runtime/monitor.py +346 -0
  122. claude_mpm/commander/session/__init__.py +6 -0
  123. claude_mpm/commander/session/context.py +81 -0
  124. claude_mpm/commander/session/manager.py +59 -0
  125. claude_mpm/commander/tmux_orchestrator.py +362 -0
  126. claude_mpm/commander/web/__init__.py +1 -0
  127. claude_mpm/commander/work/__init__.py +30 -0
  128. claude_mpm/commander/work/executor.py +207 -0
  129. claude_mpm/commander/work/queue.py +405 -0
  130. claude_mpm/commander/workflow/__init__.py +27 -0
  131. claude_mpm/commander/workflow/event_handler.py +241 -0
  132. claude_mpm/commander/workflow/notifier.py +146 -0
  133. claude_mpm/commands/mpm-config.md +8 -0
  134. claude_mpm/commands/mpm-doctor.md +8 -0
  135. claude_mpm/commands/mpm-help.md +8 -0
  136. claude_mpm/commands/mpm-init.md +8 -0
  137. claude_mpm/commands/mpm-monitor.md +8 -0
  138. claude_mpm/commands/mpm-organize.md +8 -0
  139. claude_mpm/commands/mpm-postmortem.md +8 -0
  140. claude_mpm/commands/mpm-session-resume.md +9 -1
  141. claude_mpm/commands/mpm-status.md +8 -0
  142. claude_mpm/commands/mpm-ticket-view.md +8 -0
  143. claude_mpm/commands/mpm-version.md +8 -0
  144. claude_mpm/commands/mpm.md +8 -0
  145. claude_mpm/config/agent_presets.py +8 -7
  146. claude_mpm/config/skill_sources.py +16 -0
  147. claude_mpm/constants.py +5 -0
  148. claude_mpm/core/claude_runner.py +152 -0
  149. claude_mpm/core/config.py +35 -22
  150. claude_mpm/core/config_constants.py +74 -9
  151. claude_mpm/core/constants.py +56 -12
  152. claude_mpm/core/hook_manager.py +53 -4
  153. claude_mpm/core/interactive_session.py +5 -4
  154. claude_mpm/core/logger.py +26 -9
  155. claude_mpm/core/logging_utils.py +39 -13
  156. claude_mpm/core/network_config.py +148 -0
  157. claude_mpm/core/oneshot_session.py +7 -6
  158. claude_mpm/core/output_style_manager.py +52 -12
  159. claude_mpm/core/socketio_pool.py +47 -15
  160. claude_mpm/core/unified_config.py +10 -6
  161. claude_mpm/core/unified_paths.py +68 -80
  162. claude_mpm/dashboard/static/svelte-build/_app/immutable/assets/0.C33zOoyM.css +1 -0
  163. claude_mpm/dashboard/static/svelte-build/_app/immutable/assets/2.CW1J-YuA.css +1 -0
  164. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{Cs_tUR18.js → 1WZnGYqX.js} +1 -1
  165. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{CDuw-vjf.js → 67pF3qNn.js} +1 -1
  166. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{bTOqqlTd.js → 6RxdMKe4.js} +1 -1
  167. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{DwBR2MJi.js → 8cZrfX0h.js} +1 -1
  168. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{ZGh7QtNv.js → 9a6T2nm-.js} +1 -1
  169. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{D9lljYKQ.js → B443AUzu.js} +1 -1
  170. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{RJiighC3.js → B8AwtY2H.js} +1 -1
  171. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{uuIeMWc-.js → BF15LAsF.js} +1 -1
  172. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{D3k0OPJN.js → BRcwIQNr.js} +1 -1
  173. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{CyWMqx4W.js → BV6nKitt.js} +1 -1
  174. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{CiIAseT4.js → BViJ8lZt.js} +5 -5
  175. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{CBBdVcY8.js → BcQ-Q0FE.js} +1 -1
  176. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{BovzEFCE.js → Bpyvgze_.js} +1 -1
  177. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/BzTRqg-z.js +1 -0
  178. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/C0Fr8dve.js +1 -0
  179. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{eNVUfhuA.js → C3rbW_a-.js} +1 -1
  180. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{GYwsonyD.js → C8WYN38h.js} +1 -1
  181. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{BIF9m_hv.js → C9I8FlXH.js} +1 -1
  182. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{B0uc0UOD.js → CIQcWgO2.js} +3 -3
  183. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{Be7GpZd6.js → CIctN7YN.js} +1 -1
  184. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{Bh0LDWpI.js → CKrS_JZW.js} +2 -2
  185. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{DUrLdbGD.js → CR6P9C4A.js} +1 -1
  186. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{B7xVLGWV.js → CRRR9MD_.js} +1 -1
  187. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/CRcR2DqT.js +334 -0
  188. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{Dhb8PKl3.js → CSXtMOf0.js} +1 -1
  189. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{BPYeabCQ.js → CT-sbxSk.js} +1 -1
  190. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{sQeU3Y1z.js → CWm6DJsp.js} +1 -1
  191. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{CnA0NrzZ.js → CpqQ1Kzn.js} +1 -1
  192. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{C4B-KCzX.js → D2nGpDRe.js} +1 -1
  193. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{DGkLK5U1.js → D9iCMida.js} +1 -1
  194. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{BofRWZRR.js → D9ykgMoY.js} +1 -1
  195. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{DmxopI1J.js → DL2Ldur1.js} +1 -1
  196. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{C30mlcqg.js → DPfltzjH.js} +1 -1
  197. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{Vzk33B_K.js → DR8nis88.js} +2 -2
  198. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{DI7hHRFL.js → DUliQN2b.js} +1 -1
  199. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{C4JcI4KD.js → DXlhR01x.js} +1 -1
  200. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{bT1r9zLR.js → D_lyTybS.js} +1 -1
  201. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{DZX00Y4g.js → DngoTTgh.js} +1 -1
  202. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{CzZX-COe.js → DqkmHtDC.js} +1 -1
  203. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{B7RN905-.js → DsDh8EYs.js} +1 -1
  204. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{DLVjFsZ3.js → DypDmXgd.js} +1 -1
  205. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{iEWssX7S.js → IPYC-LnN.js} +1 -1
  206. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/JTLiF7dt.js +24 -0
  207. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{DaimHw_p.js → JpevfAFt.js} +1 -1
  208. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{DY1XQ8fi.js → R8CEIRAd.js} +1 -1
  209. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{Dle-35c7.js → Zxy7qc-l.js} +2 -2
  210. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/q9Hm6zAU.js +1 -0
  211. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{C_Usid8X.js → qtd3IeO4.js} +2 -2
  212. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{CzeYkLYB.js → ulBFON_C.js} +2 -2
  213. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/{Cfqx1Qun.js → wQVh1CoA.js} +1 -1
  214. claude_mpm/dashboard/static/svelte-build/_app/immutable/entry/{app.D6-I5TpK.js → app.Dr7t0z2J.js} +2 -2
  215. claude_mpm/dashboard/static/svelte-build/_app/immutable/entry/start.BGhZHUS3.js +1 -0
  216. claude_mpm/dashboard/static/svelte-build/_app/immutable/nodes/{0.m1gL8KXf.js → 0.RgBboRvH.js} +1 -1
  217. claude_mpm/dashboard/static/svelte-build/_app/immutable/nodes/{1.CgNOuw-d.js → 1.DG-KkbDf.js} +1 -1
  218. claude_mpm/dashboard/static/svelte-build/_app/immutable/nodes/2.D_jnf-x6.js +1 -0
  219. claude_mpm/dashboard/static/svelte-build/_app/version.json +1 -1
  220. claude_mpm/dashboard/static/svelte-build/index.html +9 -9
  221. claude_mpm/experimental/cli_enhancements.py +2 -1
  222. claude_mpm/hooks/claude_hooks/INTEGRATION_EXAMPLE.md +243 -0
  223. claude_mpm/hooks/claude_hooks/README_AUTO_PAUSE.md +403 -0
  224. claude_mpm/hooks/claude_hooks/auto_pause_handler.py +485 -0
  225. claude_mpm/hooks/claude_hooks/event_handlers.py +466 -136
  226. claude_mpm/hooks/claude_hooks/hook_handler.py +204 -104
  227. claude_mpm/hooks/claude_hooks/hook_wrapper.sh +6 -11
  228. claude_mpm/hooks/claude_hooks/installer.py +291 -59
  229. claude_mpm/hooks/claude_hooks/memory_integration.py +52 -32
  230. claude_mpm/hooks/claude_hooks/response_tracking.py +43 -60
  231. claude_mpm/hooks/claude_hooks/services/__init__.py +21 -0
  232. claude_mpm/hooks/claude_hooks/services/connection_manager.py +41 -26
  233. claude_mpm/hooks/claude_hooks/services/connection_manager_http.py +38 -105
  234. claude_mpm/hooks/claude_hooks/services/container.py +326 -0
  235. claude_mpm/hooks/claude_hooks/services/protocols.py +328 -0
  236. claude_mpm/hooks/claude_hooks/services/state_manager.py +25 -38
  237. claude_mpm/hooks/claude_hooks/services/subagent_processor.py +75 -77
  238. claude_mpm/hooks/session_resume_hook.py +89 -1
  239. claude_mpm/hooks/templates/pre_tool_use_simple.py +6 -6
  240. claude_mpm/hooks/templates/pre_tool_use_template.py +16 -8
  241. claude_mpm/init.py +22 -15
  242. claude_mpm/mcp/__init__.py +9 -0
  243. claude_mpm/mcp/google_workspace_server.py +610 -0
  244. claude_mpm/scripts/claude-hook-handler.sh +46 -19
  245. claude_mpm/services/agents/agent_recommendation_service.py +8 -8
  246. claude_mpm/services/agents/agent_selection_service.py +2 -2
  247. claude_mpm/services/agents/cache_git_manager.py +1 -1
  248. claude_mpm/services/agents/deployment/remote_agent_discovery_service.py +3 -0
  249. claude_mpm/services/agents/loading/framework_agent_loader.py +75 -2
  250. claude_mpm/services/agents/single_tier_deployment_service.py +4 -4
  251. claude_mpm/services/cli/__init__.py +3 -0
  252. claude_mpm/services/cli/incremental_pause_manager.py +561 -0
  253. claude_mpm/services/cli/session_resume_helper.py +10 -2
  254. claude_mpm/services/command_deployment_service.py +44 -26
  255. claude_mpm/services/delegation_detector.py +175 -0
  256. claude_mpm/services/diagnostics/checks/agent_sources_check.py +30 -0
  257. claude_mpm/services/diagnostics/checks/configuration_check.py +24 -0
  258. claude_mpm/services/diagnostics/checks/installation_check.py +22 -0
  259. claude_mpm/services/diagnostics/checks/mcp_services_check.py +23 -0
  260. claude_mpm/services/diagnostics/doctor_reporter.py +31 -1
  261. claude_mpm/services/diagnostics/models.py +14 -1
  262. claude_mpm/services/event_log.py +325 -0
  263. claude_mpm/services/hook_installer_service.py +77 -8
  264. claude_mpm/services/infrastructure/__init__.py +4 -0
  265. claude_mpm/services/infrastructure/context_usage_tracker.py +291 -0
  266. claude_mpm/services/infrastructure/resume_log_generator.py +24 -5
  267. claude_mpm/services/mcp_config_manager.py +99 -19
  268. claude_mpm/services/mcp_service_registry.py +294 -0
  269. claude_mpm/services/monitor/daemon_manager.py +15 -4
  270. claude_mpm/services/monitor/management/lifecycle.py +8 -2
  271. claude_mpm/services/monitor/server.py +111 -16
  272. claude_mpm/services/pm_skills_deployer.py +261 -87
  273. claude_mpm/services/skills/git_skill_source_manager.py +130 -10
  274. claude_mpm/services/skills/selective_skill_deployer.py +142 -16
  275. claude_mpm/services/skills/skill_discovery_service.py +74 -4
  276. claude_mpm/services/skills_deployer.py +31 -5
  277. claude_mpm/services/socketio/handlers/hook.py +14 -7
  278. claude_mpm/services/socketio/server/main.py +12 -4
  279. claude_mpm/skills/__init__.py +2 -1
  280. claude_mpm/skills/bundled/pm/mpm/SKILL.md +38 -0
  281. claude_mpm/skills/bundled/pm/mpm-agent-update-workflow/SKILL.md +75 -0
  282. claude_mpm/skills/bundled/pm/mpm-circuit-breaker-enforcement/SKILL.md +476 -0
  283. claude_mpm/skills/bundled/pm/mpm-config/SKILL.md +29 -0
  284. claude_mpm/skills/bundled/pm/mpm-doctor/SKILL.md +53 -0
  285. claude_mpm/skills/bundled/pm/mpm-help/SKILL.md +35 -0
  286. claude_mpm/skills/bundled/pm/mpm-init/SKILL.md +125 -0
  287. claude_mpm/skills/bundled/pm/mpm-monitor/SKILL.md +32 -0
  288. claude_mpm/skills/bundled/pm/mpm-organize/SKILL.md +121 -0
  289. claude_mpm/skills/bundled/pm/mpm-postmortem/SKILL.md +22 -0
  290. claude_mpm/skills/bundled/pm/mpm-session-management/SKILL.md +312 -0
  291. claude_mpm/skills/bundled/pm/mpm-session-pause/SKILL.md +170 -0
  292. claude_mpm/skills/bundled/pm/mpm-session-resume/SKILL.md +31 -0
  293. claude_mpm/skills/bundled/pm/mpm-status/SKILL.md +37 -0
  294. claude_mpm/skills/bundled/pm/{pm-teaching-mode → mpm-teaching-mode}/SKILL.md +2 -2
  295. claude_mpm/skills/bundled/pm/mpm-ticket-view/SKILL.md +110 -0
  296. claude_mpm/skills/bundled/pm/mpm-tool-usage-guide/SKILL.md +386 -0
  297. claude_mpm/skills/bundled/pm/mpm-version/SKILL.md +21 -0
  298. claude_mpm/skills/registry.py +295 -90
  299. claude_mpm/skills/skill_manager.py +4 -4
  300. claude_mpm-5.6.76.dist-info/METADATA +416 -0
  301. {claude_mpm-5.4.85.dist-info → claude_mpm-5.6.76.dist-info}/RECORD +312 -175
  302. {claude_mpm-5.4.85.dist-info → claude_mpm-5.6.76.dist-info}/WHEEL +1 -1
  303. {claude_mpm-5.4.85.dist-info → claude_mpm-5.6.76.dist-info}/entry_points.txt +2 -0
  304. claude_mpm/dashboard/static/svelte-build/_app/immutable/assets/0.DWzvg0-y.css +0 -1
  305. claude_mpm/dashboard/static/svelte-build/_app/immutable/assets/2.ThTw9_ym.css +0 -1
  306. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/4TdZjIqw.js +0 -1
  307. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/5shd3_w0.js +0 -24
  308. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/BKjSRqUr.js +0 -1
  309. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/Da0KfYnO.js +0 -1
  310. claude_mpm/dashboard/static/svelte-build/_app/immutable/chunks/Dfy6j1xT.js +0 -323
  311. claude_mpm/dashboard/static/svelte-build/_app/immutable/entry/start.NWzMBYRp.js +0 -1
  312. claude_mpm/dashboard/static/svelte-build/_app/immutable/nodes/2.C0GcWctS.js +0 -1
  313. claude_mpm-5.4.85.dist-info/METADATA +0 -1023
  314. /claude_mpm/skills/bundled/pm/{pm-bug-reporting/pm-bug-reporting.md → mpm-bug-reporting/SKILL.md} +0 -0
  315. /claude_mpm/skills/bundled/pm/{pm-delegation-patterns → mpm-delegation-patterns}/SKILL.md +0 -0
  316. /claude_mpm/skills/bundled/pm/{pm-git-file-tracking → mpm-git-file-tracking}/SKILL.md +0 -0
  317. /claude_mpm/skills/bundled/pm/{pm-pr-workflow → mpm-pr-workflow}/SKILL.md +0 -0
  318. /claude_mpm/skills/bundled/pm/{pm-ticketing-integration → mpm-ticketing-integration}/SKILL.md +0 -0
  319. /claude_mpm/skills/bundled/pm/{pm-verification-protocols → mpm-verification-protocols}/SKILL.md +0 -0
  320. {claude_mpm-5.4.85.dist-info → claude_mpm-5.6.76.dist-info}/licenses/LICENSE +0 -0
  321. {claude_mpm-5.4.85.dist-info → claude_mpm-5.6.76.dist-info}/licenses/LICENSE-FAQ.md +0 -0
  322. {claude_mpm-5.4.85.dist-info → claude_mpm-5.6.76.dist-info}/top_level.txt +0 -0
@@ -127,6 +127,14 @@ def execute_command(command: str, args) -> int:
127
127
  result = handle_verify(args)
128
128
  return result if result is not None else 0
129
129
 
130
+ # Handle commander command with lazy import
131
+ if command == "commander":
132
+ # Lazy import to avoid loading unless needed
133
+ from .commands.commander import handle_commander_command
134
+
135
+ result = handle_commander_command(args)
136
+ return result if result is not None else 0
137
+
130
138
  # Handle skill-source command with lazy import
131
139
  if command == "skill-source":
132
140
  # Lazy import to avoid loading unless needed
@@ -151,6 +159,14 @@ def execute_command(command: str, args) -> int:
151
159
  result = summarize_command(args)
152
160
  return result if result is not None else 0
153
161
 
162
+ # Handle oauth command with lazy import
163
+ if command == "oauth":
164
+ # Lazy import to avoid loading unless needed
165
+ from .commands.oauth import manage_oauth
166
+
167
+ result = manage_oauth(args)
168
+ return result if result is not None else 0
169
+
154
170
  # Handle profile command with lazy import
155
171
  if command == "profile":
156
172
  # Lazy import to avoid loading unless needed
@@ -206,35 +222,127 @@ def execute_command(command: str, args) -> int:
206
222
  "status": show_status,
207
223
  }
208
224
 
209
- # Get handler and invoke
225
+ # Get handler and call it with argument list (same pattern as autotodos)
210
226
  handler = handlers.get(subcommand)
211
227
  if handler:
212
- # Build Click context programmatically
213
- import click
228
+ try:
229
+ # Build argument list for Click command based on subcommand
230
+ click_args = []
231
+
232
+ # list command: --format, --hook-type
233
+ if subcommand == "list":
234
+ if hasattr(args, "format") and args.format:
235
+ click_args.extend(["--format", args.format])
236
+ if hasattr(args, "hook_type") and args.hook_type:
237
+ click_args.extend(["--hook-type", args.hook_type])
238
+ # clear command: --hook-type, -y
239
+ elif subcommand == "clear":
240
+ if hasattr(args, "hook_type") and args.hook_type:
241
+ click_args.extend(["--hook-type", args.hook_type])
242
+ if hasattr(args, "yes") and args.yes:
243
+ click_args.append("-y")
244
+ # diagnose command: hook_type (positional argument)
245
+ elif subcommand == "diagnose":
246
+ if hasattr(args, "hook_type") and args.hook_type:
247
+ click_args.append(args.hook_type)
248
+ # status and summary commands: no options
249
+
250
+ # Call Click command with argument list and standalone_mode=False
251
+ handler(click_args, standalone_mode=False)
252
+ return 0
253
+ except SystemExit as e:
254
+ return e.code if e.code is not None else 0
255
+ except Exception as e:
256
+ print(f"Error: {e}")
257
+ return 1
258
+ else:
259
+ print(f"Unknown hook-errors subcommand: {subcommand}")
260
+ return 1
214
261
 
215
- ctx = click.Context(command=handler)
262
+ # Handle autotodos command with lazy import
263
+ if command == "autotodos":
264
+ # Lazy import to avoid loading unless needed
265
+ from .commands.autotodos import (
266
+ clear_autotodos,
267
+ inject_autotodos,
268
+ list_autotodos,
269
+ list_pm_violations,
270
+ scan_delegation_patterns,
271
+ show_autotodos_status,
272
+ )
216
273
 
217
- # Prepare keyword arguments from args
218
- kwargs = {}
219
- if hasattr(args, "format"):
220
- kwargs["format"] = args.format
221
- if hasattr(args, "hook_type"):
222
- kwargs["hook_type"] = args.hook_type
223
- if hasattr(args, "yes"):
224
- kwargs["yes"] = args.yes
274
+ # Get subcommand
275
+ subcommand = getattr(args, "autotodos_command", "status")
276
+ if not subcommand:
277
+ subcommand = "status"
225
278
 
279
+ # Map subcommands to functions
280
+ handlers = {
281
+ "list": list_autotodos,
282
+ "inject": inject_autotodos,
283
+ "clear": clear_autotodos,
284
+ "status": show_autotodos_status,
285
+ "scan": scan_delegation_patterns,
286
+ "violations": list_pm_violations,
287
+ }
288
+
289
+ # Get handler and call it with standalone_mode=False
290
+ handler = handlers.get(subcommand)
291
+ if handler:
226
292
  try:
227
- # Invoke handler with arguments
228
- with ctx:
229
- handler.invoke(ctx, **kwargs)
293
+ # Build argument list for Click command
294
+ click_args = []
295
+
296
+ if subcommand == "list":
297
+ fmt = getattr(args, "format", "table")
298
+ click_args = ["--format", fmt]
299
+ elif subcommand == "inject":
300
+ output = getattr(args, "output", None)
301
+ if output:
302
+ click_args = ["--output", output]
303
+ elif subcommand == "clear":
304
+ error_key = getattr(args, "error_key", None)
305
+ event_type = getattr(args, "event_type", "all")
306
+ if error_key:
307
+ click_args.append("--error-key")
308
+ click_args.append(error_key)
309
+ if event_type != "all":
310
+ click_args.append("--event-type")
311
+ click_args.append(event_type)
312
+ if getattr(args, "yes", False):
313
+ click_args.append("-y")
314
+ elif subcommand == "scan":
315
+ text = getattr(args, "text", None)
316
+ file = getattr(args, "file", None)
317
+ fmt = getattr(args, "format", "table")
318
+ save = getattr(args, "save", False)
319
+
320
+ if text:
321
+ click_args.append(text)
322
+ if file:
323
+ click_args.extend(["--file", file])
324
+ if fmt != "table":
325
+ click_args.extend(["--format", fmt])
326
+ if save:
327
+ click_args.append("--save")
328
+ elif subcommand == "violations":
329
+ fmt = getattr(args, "format", "table")
330
+ if fmt != "table":
331
+ click_args.extend(["--format", fmt])
332
+
333
+ # Call Click command with argument list and standalone_mode=False
334
+ handler(click_args, standalone_mode=False)
230
335
  return 0
231
336
  except SystemExit as e:
232
337
  return e.code if e.code is not None else 0
233
338
  except Exception as e:
234
339
  print(f"Error: {e}")
340
+ import traceback
341
+
342
+ traceback.print_exc()
235
343
  return 1
236
344
  else:
237
- print(f"Unknown hook-errors subcommand: {subcommand}")
345
+ print(f"Unknown autotodos subcommand: {subcommand}")
238
346
  return 1
239
347
 
240
348
  # Map stable commands to their implementations
@@ -260,6 +368,7 @@ def execute_command(command: str, args) -> int:
260
368
  CLICommands.SKILLS.value: manage_skills,
261
369
  "debug": manage_debug, # Add debug command
262
370
  "mpm-init": None, # Will be handled separately with lazy import
371
+ "commander": None, # Will be handled separately with lazy import
263
372
  }
264
373
 
265
374
  # Execute command if found
@@ -287,6 +396,9 @@ def execute_command(command: str, args) -> int:
287
396
  "local-deploy",
288
397
  "skill-source",
289
398
  "agent-source",
399
+ "hook-errors",
400
+ "autotodos",
401
+ "oauth",
290
402
  ]
291
403
 
292
404
  suggestion = suggest_similar_commands(command, all_commands)
claude_mpm/cli/helpers.py CHANGED
@@ -30,7 +30,7 @@ def is_interactive_session() -> bool:
30
30
 
31
31
  def should_skip_config_check(command: str | None) -> bool:
32
32
  """Check if command should skip configuration check."""
33
- skip_commands = ["configure", "doctor", "info", "mcp", "config"]
33
+ skip_commands = ["configure", "doctor", "info", "mcp", "config", "oauth"]
34
34
  return command in skip_commands if command else False
35
35
 
36
36
 
@@ -125,7 +125,7 @@ def _get_enhanced_version(base_version: str) -> str:
125
125
 
126
126
  if enhanced and enhanced != base_version:
127
127
  return enhanced
128
- except Exception:
128
+ except Exception: # nosec B110
129
129
  # If anything fails, fall back to base version
130
130
  pass
131
131
 
@@ -297,6 +297,22 @@ def add_top_level_run_arguments(parser: argparse.ArgumentParser) -> None:
297
297
  action="store_true",
298
298
  help="Force refresh agents and skills from remote repos, bypassing ETag cache",
299
299
  )
300
+ run_group.add_argument(
301
+ "--chrome",
302
+ action="store_true",
303
+ help="Enable Claude in Chrome integration (passed to Claude Code)",
304
+ )
305
+ run_group.add_argument(
306
+ "--no-chrome",
307
+ action="store_true",
308
+ help="Disable Claude in Chrome integration (passed to Claude Code)",
309
+ )
310
+ run_group.add_argument(
311
+ "--mcp",
312
+ type=str,
313
+ metavar="SERVICES",
314
+ help="Comma-separated list of MCP services to enable for this session (e.g., --mcp kuzu-memory,mcp-ticketer)",
315
+ )
300
316
 
301
317
  # Dependency checking options (for backward compatibility at top level)
302
318
  dep_group_top = parser.add_argument_group(
@@ -492,6 +508,20 @@ def create_parser(
492
508
  except ImportError:
493
509
  pass
494
510
 
511
+ try:
512
+ from .commander_parser import add_commander_subparser
513
+
514
+ add_commander_subparser(subparsers)
515
+ except ImportError:
516
+ pass
517
+
518
+ try:
519
+ from .oauth_parser import add_oauth_subparser
520
+
521
+ add_oauth_subparser(subparsers)
522
+ except ImportError:
523
+ pass
524
+
495
525
  # Add uninstall command parser
496
526
  try:
497
527
  from ..commands.uninstall import add_uninstall_parser
@@ -607,6 +637,59 @@ def create_parser(
607
637
  help="Skip confirmation prompts",
608
638
  )
609
639
 
640
+ # Add autotodos command for auto-generating todos from hook errors
641
+ autotodos_parser = subparsers.add_parser(
642
+ "autotodos",
643
+ help="Auto-generate todos from hook errors and delegation patterns",
644
+ )
645
+ autotodos_parser.add_argument(
646
+ "autotodos_command",
647
+ nargs="?",
648
+ choices=["list", "inject", "clear", "status", "scan", "violations"],
649
+ help="AutoTodos subcommand",
650
+ )
651
+ autotodos_parser.add_argument(
652
+ "text",
653
+ nargs="?",
654
+ help="Text to scan for delegation patterns (scan command only)",
655
+ )
656
+ autotodos_parser.add_argument(
657
+ "--format",
658
+ choices=["table", "json"],
659
+ default="table",
660
+ help="Output format for list/scan commands",
661
+ )
662
+ autotodos_parser.add_argument(
663
+ "--output",
664
+ help="Output file path for inject command",
665
+ )
666
+ autotodos_parser.add_argument(
667
+ "--error-key",
668
+ help="Specific error key to clear",
669
+ )
670
+ autotodos_parser.add_argument(
671
+ "--event-type",
672
+ choices=["error", "violation", "all"],
673
+ default="all",
674
+ help="Type of events to clear (clear command only)",
675
+ )
676
+ autotodos_parser.add_argument(
677
+ "--file",
678
+ "-f",
679
+ help="Scan text from file (scan command only)",
680
+ )
681
+ autotodos_parser.add_argument(
682
+ "--save",
683
+ action="store_true",
684
+ help="Save detections to event log (scan command only)",
685
+ )
686
+ autotodos_parser.add_argument(
687
+ "-y",
688
+ "--yes",
689
+ action="store_true",
690
+ help="Skip confirmation prompts",
691
+ )
692
+
610
693
  # Add summarize command
611
694
  from ..commands.summarize import add_summarize_parser
612
695
 
@@ -0,0 +1,116 @@
1
+ """
2
+ Commander parser module for claude-mpm CLI.
3
+
4
+ WHY: This module provides the commander subcommand for interactive instance management
5
+ and chat interface.
6
+
7
+ DESIGN DECISION: Uses subparser pattern consistent with other commands (run, agents, etc.)
8
+ to provide a clean interface for Commander mode.
9
+ """
10
+
11
+ import argparse
12
+ from pathlib import Path
13
+
14
+
15
+ def add_commander_subparser(subparsers: argparse._SubParsersAction) -> None:
16
+ """
17
+ Add commander subcommand parser.
18
+
19
+ WHY: Provides interactive mode for managing and chatting with multiple Claude instances.
20
+
21
+ Args:
22
+ subparsers: The subparsers object to add the commander parser to
23
+ """
24
+ commander_parser = subparsers.add_parser(
25
+ "commander",
26
+ help="Launch Commander multi-project orchestration (ALPHA)",
27
+ description="""
28
+ Commander Mode - Multi-Project Orchestration (ALPHA)
29
+
30
+ The commander subcommand auto-starts the Commander daemon (if not already running)
31
+ and launches an interactive REPL for managing multiple Claude Code instances.
32
+
33
+ Commander provides:
34
+ - Auto-starting daemon that manages project lifecycles
35
+ - Interactive REPL for controlling instances
36
+ - Tmux-based session management
37
+ - Real-time output monitoring
38
+ - REST API for external control (http://127.0.0.1:8765)
39
+
40
+ REPL Commands:
41
+ list, ls, instances List active instances
42
+ start <path> Start new instance at path
43
+ --framework <cc|mpm> Specify framework (default: cc)
44
+ --name <name> Specify instance name (default: dir name)
45
+ stop <name> Stop an instance
46
+ connect <name> Connect to an instance
47
+ disconnect Disconnect from current instance
48
+ status Show current session status
49
+ help Show help message
50
+ exit, quit, q Exit Commander
51
+
52
+ Natural Language:
53
+ When connected to an instance, any input that is not a built-in
54
+ command will be sent to the connected instance as a message.
55
+
56
+ Examples:
57
+ # Start daemon and launch interactive chat
58
+ claude-mpm commander
59
+
60
+ # Start daemon only (no chat interface)
61
+ claude-mpm commander --daemon-only
62
+
63
+ # Use custom port
64
+ claude-mpm commander --port 9000
65
+
66
+ # In REPL:
67
+ > start ~/myproject --framework cc --name myapp
68
+ > connect myapp
69
+ > Fix the authentication bug in login.py
70
+ > disconnect
71
+ > exit
72
+ """,
73
+ formatter_class=argparse.RawDescriptionHelpFormatter,
74
+ )
75
+
76
+ # Optional: Port for internal services
77
+ commander_parser.add_argument(
78
+ "--port",
79
+ type=int,
80
+ default=8766, # NetworkPorts.COMMANDER_DEFAULT
81
+ help="Port for internal services (default: 8766)",
82
+ )
83
+
84
+ # Optional: State directory
85
+ commander_parser.add_argument(
86
+ "--state-dir",
87
+ type=Path,
88
+ help="Directory for state persistence (optional)",
89
+ )
90
+
91
+ # Debug mode
92
+ commander_parser.add_argument(
93
+ "--debug",
94
+ action="store_true",
95
+ help="Enable debug logging",
96
+ )
97
+
98
+ # Daemon auto-start options
99
+ commander_parser.add_argument(
100
+ "--host",
101
+ type=str,
102
+ default="127.0.0.1",
103
+ help="Daemon host (default: 127.0.0.1)",
104
+ )
105
+
106
+ commander_parser.add_argument(
107
+ "--no-chat",
108
+ action="store_true",
109
+ help="Start daemon only without interactive chat",
110
+ )
111
+
112
+ commander_parser.add_argument(
113
+ "--daemon-only",
114
+ action="store_true",
115
+ help="Alias for --no-chat (start daemon only)",
116
+ )
@@ -192,4 +192,83 @@ def add_mcp_subparser(subparsers) -> argparse.ArgumentParser:
192
192
  "--force", action="store_true", help="Force overwrite existing configuration"
193
193
  )
194
194
 
195
+ # =========================================================================
196
+ # Service Management Commands (enable/disable/list)
197
+ # =========================================================================
198
+
199
+ # Enable MCP service
200
+ enable_parser = mcp_subparsers.add_parser(
201
+ MCPCommands.ENABLE.value,
202
+ help="Enable an MCP service in configuration",
203
+ )
204
+ enable_parser.add_argument(
205
+ "service_name",
206
+ help="Name of the MCP service to enable (e.g., kuzu-memory, mcp-github)",
207
+ )
208
+ enable_parser.add_argument(
209
+ "--interactive",
210
+ "-i",
211
+ action="store_true",
212
+ help="Prompt for required credentials interactively",
213
+ )
214
+ enable_parser.add_argument(
215
+ "--env",
216
+ "-e",
217
+ action="append",
218
+ metavar="KEY=VALUE",
219
+ help="Set environment variable (can be used multiple times)",
220
+ )
221
+ enable_parser.add_argument(
222
+ "--global",
223
+ dest="use_global",
224
+ action="store_true",
225
+ help="Enable in global ~/.claude.json instead of project .mcp.json",
226
+ )
227
+
228
+ # Disable MCP service
229
+ disable_parser = mcp_subparsers.add_parser(
230
+ MCPCommands.DISABLE.value,
231
+ help="Disable an MCP service from configuration",
232
+ )
233
+ disable_parser.add_argument(
234
+ "service_name",
235
+ help="Name of the MCP service to disable",
236
+ )
237
+ disable_parser.add_argument(
238
+ "--global",
239
+ dest="use_global",
240
+ action="store_true",
241
+ help="Disable in global ~/.claude.json instead of project .mcp.json",
242
+ )
243
+
244
+ # List MCP services
245
+ list_parser = mcp_subparsers.add_parser(
246
+ MCPCommands.LIST.value,
247
+ help="List MCP services (available and enabled)",
248
+ )
249
+ list_parser.add_argument(
250
+ "--available",
251
+ "-a",
252
+ action="store_true",
253
+ help="Show all available services from registry",
254
+ )
255
+ list_parser.add_argument(
256
+ "--enabled",
257
+ "-e",
258
+ action="store_true",
259
+ help="Show only enabled services",
260
+ )
261
+ list_parser.add_argument(
262
+ "--global",
263
+ dest="use_global",
264
+ action="store_true",
265
+ help="Check global ~/.claude.json instead of project .mcp.json",
266
+ )
267
+ list_parser.add_argument(
268
+ "--verbose",
269
+ "-v",
270
+ action="store_true",
271
+ help="Show detailed service information",
272
+ )
273
+
195
274
  return mcp_parser
@@ -0,0 +1,165 @@
1
+ """
2
+ OAuth command parser for claude-mpm CLI.
3
+
4
+ WHY: This module provides the oauth command with subcommands for
5
+ managing OAuth authentication for MCP services that require OAuth2 flows.
6
+
7
+ DESIGN DECISION: 'oauth' provides comprehensive OAuth management including
8
+ listing OAuth-capable services, setup, status, token revocation, and refresh.
9
+ """
10
+
11
+ import argparse
12
+
13
+ from .base_parser import add_common_arguments
14
+
15
+
16
+ def add_oauth_subparser(subparsers) -> argparse.ArgumentParser:
17
+ """
18
+ Add the oauth subparser with all OAuth management subcommands.
19
+
20
+ WHY: 'oauth' provides comprehensive OAuth management for MCP services
21
+ that require OAuth2 authentication flows.
22
+
23
+ Args:
24
+ subparsers: The subparsers object from the main parser
25
+
26
+ Returns:
27
+ The configured oauth subparser
28
+ """
29
+ # OAuth command with subcommands
30
+ oauth_parser = subparsers.add_parser(
31
+ "oauth",
32
+ help="Manage OAuth authentication for MCP services",
33
+ description="""
34
+ Manage OAuth authentication for MCP services.
35
+
36
+ Available commands:
37
+ list List OAuth-capable MCP services
38
+ setup <service> Set up OAuth authentication for a service
39
+ status <service> Show OAuth token status for a service
40
+ revoke <service> Revoke OAuth tokens for a service
41
+ refresh <service> Refresh OAuth tokens for a service
42
+
43
+ Examples:
44
+ claude-mpm oauth list
45
+ claude-mpm oauth setup workspace-mcp
46
+ claude-mpm oauth status workspace-mcp
47
+ claude-mpm oauth revoke workspace-mcp
48
+ claude-mpm oauth refresh workspace-mcp
49
+ """,
50
+ formatter_class=argparse.RawDescriptionHelpFormatter,
51
+ )
52
+ add_common_arguments(oauth_parser)
53
+
54
+ # Add subcommands
55
+ oauth_subparsers = oauth_parser.add_subparsers(
56
+ dest="oauth_command", help="OAuth commands", metavar="SUBCOMMAND"
57
+ )
58
+
59
+ # List subcommand
60
+ list_parser = oauth_subparsers.add_parser(
61
+ "list",
62
+ help="List OAuth-capable MCP services",
63
+ description="List all MCP services that support OAuth authentication.",
64
+ )
65
+ add_common_arguments(list_parser)
66
+ list_parser.add_argument(
67
+ "--format",
68
+ choices=["table", "json"],
69
+ default="table",
70
+ help="Output format (default: table)",
71
+ )
72
+
73
+ # Setup subcommand
74
+ setup_parser = oauth_subparsers.add_parser(
75
+ "setup",
76
+ help="Set up OAuth authentication for a service",
77
+ description="""
78
+ Set up OAuth authentication for an MCP service.
79
+
80
+ This command initiates the OAuth2 flow by:
81
+ 1. Looking for credentials in .env.local, .env, or environment variables
82
+ 2. Prompting for credentials if not found
83
+ 3. Opening a browser for user authentication
84
+ 4. Starting a local callback server to receive the OAuth redirect
85
+ 5. Storing the tokens securely for future use
86
+
87
+ Required environment variables (checked in order):
88
+ 1. .env.local file (highest priority)
89
+ 2. .env file
90
+ 3. Environment variables
91
+
92
+ For Google OAuth services:
93
+ GOOGLE_OAUTH_CLIENT_ID - Your OAuth client ID
94
+ GOOGLE_OAUTH_CLIENT_SECRET - Your OAuth client secret
95
+
96
+ Get credentials from: https://console.cloud.google.com/apis/credentials
97
+ """,
98
+ formatter_class=argparse.RawDescriptionHelpFormatter,
99
+ )
100
+ add_common_arguments(setup_parser)
101
+ setup_parser.add_argument(
102
+ "service_name",
103
+ help="Name of the MCP service to authenticate (e.g., workspace-mcp)",
104
+ )
105
+ setup_parser.add_argument(
106
+ "--no-browser",
107
+ action="store_true",
108
+ help="Don't open browser automatically, just print the URL",
109
+ )
110
+ setup_parser.add_argument(
111
+ "--port",
112
+ type=int,
113
+ default=8085,
114
+ help="Port for the OAuth callback server (default: 8085)",
115
+ )
116
+
117
+ # Status subcommand
118
+ status_parser = oauth_subparsers.add_parser(
119
+ "status",
120
+ help="Show OAuth token status for a service",
121
+ description="Display the current OAuth token status including validity and expiration.",
122
+ )
123
+ add_common_arguments(status_parser)
124
+ status_parser.add_argument(
125
+ "service_name",
126
+ help="Name of the MCP service to check",
127
+ )
128
+ status_parser.add_argument(
129
+ "--format",
130
+ choices=["table", "json"],
131
+ default="table",
132
+ help="Output format (default: table)",
133
+ )
134
+
135
+ # Revoke subcommand
136
+ revoke_parser = oauth_subparsers.add_parser(
137
+ "revoke",
138
+ help="Revoke OAuth tokens for a service",
139
+ description="Revoke and delete stored OAuth tokens for a service.",
140
+ )
141
+ add_common_arguments(revoke_parser)
142
+ revoke_parser.add_argument(
143
+ "service_name",
144
+ help="Name of the MCP service to revoke tokens for",
145
+ )
146
+ revoke_parser.add_argument(
147
+ "-y",
148
+ "--yes",
149
+ action="store_true",
150
+ help="Skip confirmation prompt",
151
+ )
152
+
153
+ # Refresh subcommand
154
+ refresh_parser = oauth_subparsers.add_parser(
155
+ "refresh",
156
+ help="Refresh OAuth tokens for a service",
157
+ description="Refresh the OAuth tokens using the stored refresh token.",
158
+ )
159
+ add_common_arguments(refresh_parser)
160
+ refresh_parser.add_argument(
161
+ "service_name",
162
+ help="Name of the MCP service to refresh tokens for",
163
+ )
164
+
165
+ return oauth_parser
@@ -85,6 +85,16 @@ def add_run_arguments(parser: argparse.ArgumentParser) -> None:
85
85
  action="store_true",
86
86
  help="Pass --resume flag to Claude Code to resume the last conversation",
87
87
  )
88
+ run_group.add_argument(
89
+ "--chrome",
90
+ action="store_true",
91
+ help="Enable Claude in Chrome integration (passed to Claude Code)",
92
+ )
93
+ run_group.add_argument(
94
+ "--no-chrome",
95
+ action="store_true",
96
+ help="Disable Claude in Chrome integration (passed to Claude Code)",
97
+ )
88
98
 
89
99
  # Dependency checking options
90
100
  dep_group = parser.add_argument_group("dependency options")