@desplega.ai/agent-swarm 1.158.0 → 1.159.0

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 (272) hide show
  1. package/dist/{acp-adapter-xaq4n6pc.js → acp-adapter-qhch0n2v.js} +1 -1
  2. package/dist/{actions-p9hz5yat.js → actions-dtsh1mfb.js} +33 -29
  3. package/dist/{anthropic-messages-51pz26qe.js → anthropic-messages-f2h06k64.js} +8 -3
  4. package/dist/{app-g26wdcz6.js → app-y1b9srva.js} +10 -9
  5. package/dist/{assistant-wydfqkb3.js → assistant-31hwy5xj.js} +34 -30
  6. package/dist/{azure-openai-responses-8gksqtmz.js → azure-openai-responses-0k1mfax5.js} +12 -13
  7. package/dist/{boot-reembed-se8zmdcp.js → boot-reembed-48d2qpkt.js} +11 -11
  8. package/dist/{boot-reembed-g5ckg9yb.js → boot-reembed-w0bryhkr.js} +12 -12
  9. package/dist/{boot-scrub-logs-wfxqan61.js → boot-scrub-logs-t65wbrn7.js} +9 -8
  10. package/dist/{boot-seeds-s3q01xj3.js → boot-seeds-h7c32hvm.js} +12 -11
  11. package/dist/{claude-adapter-tv2x4f36.js → claude-adapter-1t6611ne.js} +26 -21
  12. package/dist/{claude-managed-adapter-41b2s7fd.js → claude-managed-adapter-werp659j.js} +4 -2
  13. package/dist/{claude-managed-setup-60g8aazx.js → claude-managed-setup-y6rdgbc1.js} +11 -2
  14. package/dist/claude-sdk-session-zhkyk8yw.js +29319 -0
  15. package/dist/{cli-vj6h9kc2.js → cli-0m7wct0d.js} +59 -1
  16. package/dist/{cli-wscdvcqz.js → cli-0n2e4x49.js} +1 -1
  17. package/dist/cli-0xqde53b.js +176 -0
  18. package/dist/{cli-xberxa1r.js → cli-10ym38qc.js} +2 -2
  19. package/dist/{cli-5b6b62tz.js → cli-13hw4z91.js} +1 -1
  20. package/dist/{cli-rqz8qbw7.js → cli-20035trh.js} +50 -18
  21. package/dist/{cli-k0g1sjzm.js → cli-31nkw3g3.js} +3 -3
  22. package/dist/cli-3gvrr8vj.js +1422 -0
  23. package/dist/{cli-c07r9a2m.js → cli-48527fpw.js} +9 -8
  24. package/dist/{cli-24k806sc.js → cli-4aj25szq.js} +2 -2
  25. package/dist/{cli-7gtvvpbh.js → cli-4tvgz99m.js} +7 -7
  26. package/dist/cli-503ya656.js +455 -0
  27. package/dist/{cli-cw9zck8j.js → cli-5f2hq128.js} +8 -4
  28. package/dist/{cli-s8eet254.js → cli-68bmme5p.js} +11078 -27833
  29. package/dist/{cli-ftfvggzx.js → cli-79aq9cgb.js} +794 -563
  30. package/dist/cli-7cxw8b60.js +14910 -0
  31. package/dist/cli-7kyk9jr3.js +22 -0
  32. package/dist/cli-7zttzetj.js +324 -0
  33. package/dist/{cli-y95wp3tg.js → cli-96qd5psa.js} +1 -1
  34. package/dist/{cli-g8djp6qe.js → cli-9yg65c1j.js} +22 -0
  35. package/dist/{cli-3gmcwfyx.js → cli-ardpzhjm.js} +5 -5
  36. package/dist/{cli-7s3syk22.js → cli-b6thtzac.js} +5 -5
  37. package/dist/{cli-00w2c66p.js → cli-bgv70kym.js} +13 -2
  38. package/dist/{cli-j55n64b6.js → cli-bv0a38v9.js} +163 -44
  39. package/dist/cli-ca2w7zv7.js +115 -0
  40. package/dist/cli-cpvsaqsw.js +333 -0
  41. package/dist/cli-cygyqj3b.js +754 -0
  42. package/dist/{cli-x24pshtq.js → cli-dvjpkkjd.js} +6 -6
  43. package/dist/{cli-5d10vd2m.js → cli-e0ndxhtk.js} +4 -4
  44. package/dist/{cli-4198qc9v.js → cli-e4xnc0qp.js} +15 -3
  45. package/dist/{cli-rjehvrts.js → cli-eg7cdg68.js} +8 -8
  46. package/dist/cli-ejpygnqz.js +3815 -0
  47. package/dist/{cli-fgqxwrpv.js → cli-fjtp3463.js} +1631 -127
  48. package/dist/{cli-zt1227k1.js → cli-fkqhbg8g.js} +5 -3
  49. package/dist/{cli-47m6dkd3.js → cli-g9df2m37.js} +409 -168
  50. package/dist/cli-gzyh0j0g.js +8455 -0
  51. package/dist/cli-hgqfttfc.js +183 -0
  52. package/dist/cli-hj65wsts.js +17755 -0
  53. package/dist/cli-j9z8mfx3.js +476 -0
  54. package/dist/{cli-aehm1rbq.js → cli-kc3dp84d.js} +1135 -61
  55. package/dist/{cli-h38x0qhg.js → cli-kdnehe0t.js} +4 -3
  56. package/dist/{cli-20cj37vt.js → cli-m4excttz.js} +136 -2216
  57. package/dist/{cli-8qmme6vd.js → cli-mg24hkt4.js} +2 -2
  58. package/dist/{cli-xhaeg2nc.js → cli-mzkqpxee.js} +1 -1
  59. package/dist/{cli-q67y4wzm.js → cli-phsaj4xq.js} +24 -2
  60. package/dist/{cli-pw9rj5t9.js → cli-pqetb83f.js} +1 -176
  61. package/dist/{cli-rj19hc34.js → cli-qjxy52w7.js} +1 -1
  62. package/dist/{cli-53sz8gkz.js → cli-qv4jv8bx.js} +1 -1
  63. package/dist/cli-qvnnx4ct.js +1051 -0
  64. package/dist/cli-rb9m6rpe.js +4980 -0
  65. package/dist/{cli-tt9k8r35.js → cli-rfezr056.js} +476 -909
  66. package/dist/{cli-ggm92wcn.js → cli-rgjprct3.js} +1 -0
  67. package/dist/{cli-9httdpyq.js → cli-rrqmqr1s.js} +1 -1
  68. package/dist/cli-rykfmgwg.js +102 -0
  69. package/dist/{cli-eetrvv91.js → cli-t3p77qk1.js} +1 -1
  70. package/dist/{cli-68w09sjw.js → cli-vn0qv9cj.js} +25 -88
  71. package/dist/{cli-987hg0aa.js → cli-vwbbaecp.js} +2 -2
  72. package/dist/cli-wd9hz40d.js +69 -0
  73. package/dist/{cli-j57qkrpq.js → cli-wgjx0q33.js} +13 -13
  74. package/dist/cli-xgpf00sk.js +2149 -0
  75. package/dist/{cli-mcnhgnn1.js → cli-ykk5jaax.js} +184 -26
  76. package/dist/{cli-aky8tctm.js → cli-z9x0sh1t.js} +3 -3
  77. package/dist/{cli-1hkrch3k.js → cli-zw65mab6.js} +5 -5
  78. package/dist/cli.js +38 -29
  79. package/dist/cloudflare-workers-ai-system-one-1sg586qv.js +46 -0
  80. package/dist/{codex-adapter-cnm8wk11.js → codex-adapter-jqfqqa21.js} +21 -14
  81. package/dist/{codex-hook-9hptmdhj.js → codex-hook-5eys3dya.js} +2 -2
  82. package/dist/{codex-session-runner-gfg547zj.js → codex-session-runner-zd341dsm.js} +21 -14
  83. package/dist/{commands-e3bn0p75.js → commands-vfsysz4s.js} +9 -8
  84. package/dist/{db-03v9kzr2.js → db-s3znhvbn.js} +15 -10
  85. package/dist/{dispatcher-nrmg8yht.js → dispatcher-5xn0c7rf.js} +32 -28
  86. package/dist/{dsh-adapter-k03nfqa6.js → dsh-adapter-894mgfvs.js} +3 -3
  87. package/dist/{e2b-93x1k0j5.js → e2b-ez07znam.js} +4 -3
  88. package/dist/execute-71ysgv35.js +965 -0
  89. package/dist/{google-generative-ai-bxmv50nc.js → google-generative-ai-1nfcdphp.js} +5 -4
  90. package/dist/{google-vertex-809af514.js → google-vertex-1tqcd7b1.js} +5 -4
  91. package/dist/{handlers-aqcedbyb.js → handlers-5w4jwycr.js} +35 -31
  92. package/dist/{hook-7vkskkre.js → hook-853bxrr6.js} +16 -13
  93. package/dist/{hook-ybvmrmhq.js → hook-z0hbxj85.js} +16 -13
  94. package/dist/{http-2eqa8t24.js → http-akc3wy3m.js} +600 -123
  95. package/dist/{index-f6cryxwe.js → index-4a5njnm1.js} +2 -59
  96. package/dist/{index-a3vn96n8.js → index-5sz16ksh.js} +187 -47
  97. package/dist/{index-c6zsv1bd.js → index-bjmjh9h4.js} +11 -11
  98. package/dist/{index-chgdkq36.js → index-cd151qkq.js} +32 -28
  99. package/dist/{index-x71bvq0p.js → index-k661dzzr.js} +33 -29
  100. package/dist/{index-1yks3qcr.js → index-ttpbhnjg.js} +32 -28
  101. package/dist/{keepalive-vtkf5n99.js → keepalive-8p9rpvz5.js} +11 -10
  102. package/dist/{lead-h3sp357x.js → lead-jp69z5h3.js} +49 -45
  103. package/dist/llama-cpp-classify-t2tccams.js +335 -0
  104. package/dist/{maintenance-jzeqtk3q.js → maintenance-fwx4ev0k.js} +12 -12
  105. package/dist/{mistral-conversations-zx0kn554.js → mistral-conversations-bhvwqcnk.js} +14 -17
  106. package/dist/{oauth-refresh-sweep-qp3dzmdp.js → oauth-refresh-sweep-cwcq1ctx.js} +10 -9
  107. package/dist/{onboard-tmsp0qbz.js → onboard-2b4q0t84.js} +6 -5
  108. package/dist/{openai-codex-responses-4vjqzvjp.js → openai-codex-responses-nekthgks.js} +21 -8
  109. package/dist/{openai-completions-9hjrqbw8.js → openai-completions-hxtzwj0s.js} +8 -11
  110. package/dist/{openai-responses-7b1pn0xt.js → openai-responses-w4r118w7.js} +22 -17
  111. package/dist/{opencode-adapter-x6x2da1z.js → opencode-adapter-zz7xvjj6.js} +6 -4
  112. package/dist/{openrouter-images-9f9ek4rw.js → openrouter-images-b6sqqjgn.js} +4 -6
  113. package/dist/{otel-impl-9mz73q65.js → otel-impl-g8rs4vwr.js} +1 -1
  114. package/dist/{pi-messages-txpjj39q.js → pi-messages-vxdt8v7j.js} +2 -1
  115. package/dist/{pi-mono-adapter-m6dvv0dz.js → pi-mono-adapter-n0me28wt.js} +29 -17
  116. package/dist/pricing-refresh-0v77385v.js +39 -0
  117. package/dist/{rbac-roles-c9wqz83x.js → rbac-roles-krjyazbj.js} +10 -9
  118. package/dist/{render-v2-gryrh9h8.js → render-v2-3wjsp9aw.js} +10 -9
  119. package/dist/runtime-ktjysacx.js +24 -0
  120. package/dist/{setup-q9720bt6.js → setup-yeqryke6.js} +6 -5
  121. package/dist/typesafe-system-one-96960jxp.js +27 -0
  122. package/dist/{virtual-modules-3htpgn8x.js → virtual-modules-dzdeq1sf.js} +21 -13
  123. package/dist/{work-objects-b76x7deb.js → work-objects-3pakpkw0.js} +35 -31
  124. package/dist/{worker-6vrxbv41.js → worker-85testgj.js} +49 -45
  125. package/openapi.json +863 -14
  126. package/package.json +9 -8
  127. package/src/be/db/agents.ts +20 -0
  128. package/src/be/db/tasks/human-free.ts +442 -0
  129. package/src/be/db/tasks/read.ts +56 -1
  130. package/src/be/db/tasks/write.ts +107 -11
  131. package/src/be/db.ts +89 -165
  132. package/src/be/harness-model-support.ts +182 -0
  133. package/src/be/human-free-drain.ts +67 -0
  134. package/src/be/migrations/182_task_human_free_flag.sql +63 -0
  135. package/src/be/migrations/183_human_free_reclassify_queue.sql +25 -0
  136. package/src/be/migrations/184_model_catalog.sql +120 -0
  137. package/src/be/model-catalog-store.ts +644 -0
  138. package/src/be/model-tier-keys.ts +31 -0
  139. package/src/be/model-tier-resolution.ts +489 -0
  140. package/src/be/model-validation.ts +112 -0
  141. package/src/be/models-catalog.ts +61 -7
  142. package/src/be/modelsdev-cache.json +82 -0
  143. package/src/be/modelsdev-cache.ts +2 -0
  144. package/src/be/pricing-refresh.ts +154 -12
  145. package/src/be/scripts/typecheck.ts +15 -0
  146. package/src/be/seed-scripts/catalog/task-failure-audit.ts +61 -9
  147. package/src/be/swarm-config-guard.ts +6 -0
  148. package/src/cli.tsx +10 -0
  149. package/src/commands/claude-managed-setup.ts +3 -1
  150. package/src/commands/runner.ts +76 -2
  151. package/src/extensions/contract-types.generated.ts +1 -1
  152. package/src/heartbeat/heartbeat.ts +64 -15
  153. package/src/heartbeat/templates.ts +2 -2
  154. package/src/http/agents.ts +49 -1
  155. package/src/http/index.ts +8 -0
  156. package/src/http/models-catalog.ts +357 -8
  157. package/src/http/poll.ts +45 -2
  158. package/src/http/schedules.ts +36 -6
  159. package/src/http/session-data.ts +2 -5
  160. package/src/http/stats.ts +6 -8
  161. package/src/http/tasks.ts +26 -1
  162. package/src/http/usage-cache.ts +56 -15
  163. package/src/http/workflows.ts +35 -8
  164. package/src/prompts/session-templates.ts +1 -0
  165. package/src/providers/claude-managed-models.ts +47 -161
  166. package/src/providers/codex-adapter.ts +4 -4
  167. package/src/providers/codex-models.ts +65 -198
  168. package/src/providers/reasoning-effort.ts +44 -140
  169. package/src/rbac/legacy-policy.ts +25 -0
  170. package/src/rbac/permissions.ts +10 -0
  171. package/src/scripts-runtime/sdk-allowlist.ts +4 -0
  172. package/src/scripts-runtime/types/stdlib.d.ts +15 -0
  173. package/src/scripts-runtime/types/swarm-extension.d.ts +3 -0
  174. package/src/scripts-runtime/types/swarm-sdk.d.ts +15 -0
  175. package/src/server.ts +6 -0
  176. package/src/slack/message-text.ts +56 -2
  177. package/src/slack/thread-buffer.ts +10 -2
  178. package/src/tests/agents-list-model-display.test.ts +4 -6
  179. package/src/tests/base-prompt.test.ts +3 -0
  180. package/src/tests/claude-adapter.test.ts +10 -0
  181. package/src/tests/claude-managed-adapter.test.ts +12 -18
  182. package/src/tests/codex-adapter.test.ts +2 -1
  183. package/src/tests/codex-gpt6-release.test.ts +66 -5
  184. package/src/tests/context-window.test.ts +7 -5
  185. package/src/tests/db-extraction-contract.test.ts +1 -0
  186. package/src/tests/db-task-read-contract.test.ts +5 -1
  187. package/src/tests/db-task-write-contract.test.ts +4 -1
  188. package/src/tests/docs-index-footprint.test.js +3 -3
  189. package/src/tests/explicit-model-validation.test.ts +332 -0
  190. package/src/tests/harness-model-support.test.ts +374 -0
  191. package/src/tests/heartbeat-checklist-config.test.ts +71 -0
  192. package/src/tests/heartbeat-checklist.test.ts +4 -2
  193. package/src/tests/heartbeat-orphan-resume.test.ts +48 -0
  194. package/src/tests/human-free-flag.test.ts +279 -0
  195. package/src/tests/human-free-oracle.ts +57 -0
  196. package/src/tests/human-free-reclassify.test.ts +669 -0
  197. package/src/tests/migration-046-budgets.test.ts +3 -3
  198. package/src/tests/model-catalog-migration.test.ts +134 -0
  199. package/src/tests/model-catalog-table.test.ts +249 -0
  200. package/src/tests/model-catalog-write-access.test.ts +387 -0
  201. package/src/tests/model-tier-resolution.test.ts +519 -0
  202. package/src/tests/models-catalog.test.ts +1 -1
  203. package/src/tests/multi-runtime-enabled-stats.test.ts +65 -1
  204. package/src/tests/package-publish.test.ts +137 -36
  205. package/src/tests/pricing-routes.test.ts +2 -2
  206. package/src/tests/rbac-engine.test.ts +42 -2
  207. package/src/tests/reasoning-effort.test.ts +109 -0
  208. package/src/tests/refresh-modelsdev-carryforward.test.ts +5 -5
  209. package/src/tests/runtime-model-catalog.test.ts +86 -0
  210. package/src/tests/script-connections.test.ts +5 -0
  211. package/src/tests/seed-scripts.test.ts +89 -0
  212. package/src/tests/session-costs.test.ts +14 -11
  213. package/src/tests/slack-message-text.test.ts +101 -0
  214. package/src/tests/slack-thread-buffer-context.test.ts +93 -0
  215. package/src/tests/task-cascade-fail.test.ts +148 -2
  216. package/src/tests/tool-annotations.test.ts +1 -1
  217. package/src/tests/usage-cache.test.ts +166 -0
  218. package/src/tests/workflow-executors.test.ts +5 -2
  219. package/src/tests/workflow-system-one-decision-review.test.ts +1021 -0
  220. package/src/tests/workflow-system-one-decision-save-warnings.test.ts +365 -0
  221. package/src/tests/workflow-system-one-decision.test.ts +2063 -0
  222. package/src/tools/model-catalog/index.ts +137 -0
  223. package/src/tools/schedules/create-schedule.ts +16 -1
  224. package/src/tools/schedules/patch-schedule.ts +17 -0
  225. package/src/tools/schedules/update-schedule.ts +17 -0
  226. package/src/tools/send-task.ts +14 -0
  227. package/src/tools/task-action.ts +12 -0
  228. package/src/tools/tool-config.ts +3 -1
  229. package/src/tools/workflows/create-workflow.ts +9 -2
  230. package/src/tools/workflows/patch-workflow-node.ts +17 -7
  231. package/src/tools/workflows/patch-workflow.ts +9 -2
  232. package/src/tools/workflows/update-workflow.ts +9 -2
  233. package/src/types.ts +30 -1
  234. package/src/utils/context-window.ts +47 -53
  235. package/src/utils/harness-cli-version.ts +115 -0
  236. package/src/utils/harness-model-error.ts +33 -0
  237. package/src/utils/runtime-model-catalog.ts +137 -0
  238. package/src/workflows/approval-resolution.ts +39 -0
  239. package/src/workflows/definition.ts +7 -0
  240. package/src/workflows/engine.ts +69 -1
  241. package/src/workflows/executors/agent-task.ts +9 -0
  242. package/src/workflows/executors/base.ts +53 -0
  243. package/src/workflows/executors/human-in-the-loop.ts +8 -8
  244. package/src/workflows/executors/index.ts +1 -0
  245. package/src/workflows/executors/registry.ts +2 -0
  246. package/src/workflows/executors/system-one-decision.ts +1232 -0
  247. package/src/workflows/executors/system-one-providers.ts +301 -0
  248. package/src/workflows/executors/workflow-llm.ts +13 -1
  249. package/src/workflows/readiness.ts +86 -0
  250. package/src/workflows/recovery.ts +12 -12
  251. package/src/workflows/resume.ts +23 -9
  252. package/templates/schedules/daily-blocker-digest/content.md +4 -5
  253. package/templates/skills/agent-browser/SKILL.md +6 -5
  254. package/templates/skills/agent-browser/content.md +6 -5
  255. package/templates/skills/heartbeat-runbook/config.json +1 -1
  256. package/templates/skills/heartbeat-runbook/content.md +2 -2
  257. package/templates/skills/swarm-scripts/SKILL.md +1 -1
  258. package/templates/skills/swarm-scripts/content.md +1 -1
  259. package/templates/skills/workflow-iterate/content.md +81 -1
  260. package/templates/workflows/claude-code-changelog-watch/content.md +2 -0
  261. package/templates/workflows/pr-review-status-sweep/content.md +2 -0
  262. package/dist/claude-sdk-session-t442qz6f.js +0 -39108
  263. package/dist/cli-0xjkj1j7.js +0 -61
  264. package/dist/cli-65hjmev5.js +0 -1141
  265. package/dist/cli-aw1jwp1r.js +0 -14075
  266. package/dist/cli-h967nb6r.js +0 -6603
  267. package/dist/cli-vapyk8sw.js +0 -20
  268. package/dist/cli-ws6rqycm.js +0 -247
  269. package/dist/pricing-refresh-v1cbr9te.js +0 -27
  270. package/src/providers/modelsdev-reasoning.json +0 -6453
  271. package/dist/{codex-login-x3jk4etn.js → codex-login-he9vrn90.js} +3 -3
  272. package/dist/{index-f24115ge.js → index-2wsdsnmm.js} +3 -3
@@ -0,0 +1,476 @@
1
+ import {
2
+ ProjectTrustStore,
3
+ addMcpServerConfig,
4
+ getMcpToolExposure,
5
+ loadMcpConfig,
6
+ openBrowser,
7
+ removeMcpServerConfig,
8
+ validateMcpServerConfig
9
+ } from "./cli-503ya656.js";
10
+ import {
11
+ McpOAuthCredentialStore,
12
+ McpServerConnection,
13
+ McpServerLog,
14
+ McpSignInCancelledError,
15
+ createDefaultTransport,
16
+ signInMcpServer
17
+ } from "./cli-3gvrr8vj.js";
18
+ import"./cli-ejpygnqz.js";
19
+ import {
20
+ APP_NAME,
21
+ CONFIG_DIR_NAME,
22
+ source_default
23
+ } from "./cli-hj65wsts.js";
24
+ import"./cli-5bfdm1ah.js";
25
+ import"./cli-0m7wct0d.js";
26
+ import"./cli-rykfmgwg.js";
27
+ import"./cli-0xqde53b.js";
28
+ import"./cli-pqetb83f.js";
29
+ import"./cli-bc05qbss.js";
30
+
31
+ // node_modules/@earendil-works/pi-coding-agent/dist/extensions/mcp/cli.js
32
+ import { existsSync } from "node:fs";
33
+ import { join } from "node:path";
34
+ import { createInterface } from "node:readline/promises";
35
+ var HELP = `${source_default.bold("Usage:")}
36
+ ${APP_NAME} mcp add <server> [options] -- <command> [args...]
37
+ ${APP_NAME} mcp add <server> [options] --url <url>
38
+ ${APP_NAME} mcp remove <server> [-l]
39
+ ${APP_NAME} mcp list [--json]
40
+ ${APP_NAME} mcp login <server> [--timeout <seconds>]
41
+ ${APP_NAME} mcp logout <server>
42
+
43
+ Configure and check MCP servers and sign in to OAuth servers without starting a session.
44
+ Reads ~/${CONFIG_DIR_NAME}/agent/mcp.json and, in trusted projects, ${CONFIG_DIR_NAME}/mcp.json.
45
+
46
+ Commands:
47
+ add <server> Add or replace a server in mcp.json
48
+ remove <server> Remove a server from mcp.json
49
+ list Show state, tools, and errors (exits 1 on failure)
50
+ login <server> Sign in through the browser
51
+ logout <server> Delete the stored OAuth credentials
52
+
53
+ Options for add and remove:
54
+ -l, --local Use ${CONFIG_DIR_NAME}/mcp.json in the current project instead of the global file
55
+
56
+ Options for add:
57
+ --url <url> Streamable HTTP server URL (instead of a command)
58
+ --env <KEY=VALUE> Environment variable for a stdio server (repeatable)
59
+ --cwd <dir> Working directory for a stdio server
60
+ --header <KEY=VALUE> HTTP header (repeatable)
61
+ --bearer-token-env-var <NAME>
62
+ Send "Authorization: Bearer \${NAME}"
63
+ --oauth-client-id <id> Pre-registered OAuth client id
64
+ --oauth-client-secret <secret>
65
+ OAuth client secret (may be \${NAME} or !command)
66
+ --oauth-callback-port <port>
67
+ Fixed OAuth callback port
68
+ --exposure <mode> codemode (default), codemode-deferred, deferred, direct,
69
+ or hidden
70
+
71
+ Other options:
72
+ --json Print the list as JSON
73
+ --timeout <seconds> How long login waits for the browser (default: 300)`;
74
+ var HELP_HINT = source_default.dim(`Use "${APP_NAME} mcp --help" for usage.`);
75
+ var DEFAULT_LOGIN_TIMEOUT_SECONDS = 300;
76
+ function errorMessage(error) {
77
+ return error instanceof Error ? error.message : String(error);
78
+ }
79
+ function describeTransport(entry) {
80
+ const { config } = entry;
81
+ return "url" in config ? config.url : [config.command, ...config.args ?? []].join(" ");
82
+ }
83
+ function createConnection(entry, options, credentials) {
84
+ return new McpServerConnection({
85
+ entry,
86
+ cwd: options.cwd,
87
+ createTransport: createDefaultTransport,
88
+ credentials,
89
+ log: new McpServerLog(join(options.agentDir, "mcp.log")),
90
+ onTools: () => {}
91
+ });
92
+ }
93
+ var OPTION_ALIASES = new Map([["-l", "--local"]]);
94
+ function parseOptions(args, known, error, maxPositionals = Number.POSITIVE_INFINITY) {
95
+ const positional = [];
96
+ const values = new Map;
97
+ const lists = new Map;
98
+ for (let index = 0;index < args.length; index++) {
99
+ const arg = OPTION_ALIASES.get(args[index]) ?? args[index];
100
+ if (arg === "--" || positional.length >= maxPositionals) {
101
+ positional.push(...args.slice(arg === "--" ? index + 1 : index));
102
+ break;
103
+ }
104
+ if (!arg.startsWith("--")) {
105
+ positional.push(arg);
106
+ continue;
107
+ }
108
+ const name = arg.slice(2);
109
+ const kind = known[name];
110
+ if (!kind) {
111
+ error(`Unknown option ${arg}.
112
+ ${HELP_HINT}`);
113
+ return;
114
+ }
115
+ if (kind === "flag") {
116
+ values.set(name, true);
117
+ continue;
118
+ }
119
+ const value = args[++index];
120
+ if (value === undefined) {
121
+ error(`${arg} needs a value.`);
122
+ return;
123
+ }
124
+ if (kind === "list")
125
+ lists.set(name, [...lists.get(name) ?? [], value]);
126
+ else
127
+ values.set(name, value);
128
+ }
129
+ return { positional, values, lists };
130
+ }
131
+ async function runMcpCommand(args, options) {
132
+ const log = options.log ?? ((line) => console.log(line));
133
+ const error = options.error ?? ((line) => console.error(line));
134
+ const [command, ...rest] = args;
135
+ if (command === undefined || command === "help" || args.includes("--help") || args.includes("-h")) {
136
+ log(HELP);
137
+ return 0;
138
+ }
139
+ const projectConfig = join(options.cwd, CONFIG_DIR_NAME, "mcp.json");
140
+ if (command === "add" || command === "remove") {
141
+ return command === "add" ? add(rest, projectConfig, options, log, error) : remove(rest, projectConfig, options, log, error);
142
+ }
143
+ const projectTrusted = new ProjectTrustStore(options.agentDir).get(options.cwd) === true;
144
+ const loaded = loadMcpConfig({ agentDir: options.agentDir, cwd: options.cwd, projectTrusted });
145
+ const untrustedNote = !projectTrusted && existsSync(projectConfig) ? `${projectConfig} is ignored because the project is not trusted. Start ${APP_NAME} in the project to trust it.` : undefined;
146
+ const credentials = options.credentials ?? new McpOAuthCredentialStore;
147
+ switch (command) {
148
+ case "list": {
149
+ const parsed = parseOptions(rest, { json: "flag" }, error);
150
+ if (!parsed)
151
+ return 1;
152
+ if (parsed.positional.length > 0) {
153
+ error(`Usage: ${APP_NAME} mcp list [--json]
154
+ ${HELP_HINT}`);
155
+ return 1;
156
+ }
157
+ return list(loaded, parsed.values.has("json"), untrustedNote, options, credentials, log);
158
+ }
159
+ case "login":
160
+ case "logout": {
161
+ const parsed = parseOptions(rest, command === "login" ? { timeout: "value" } : {}, error);
162
+ if (!parsed)
163
+ return 1;
164
+ const [name, ...extra] = parsed.positional;
165
+ if (!name || extra.length > 0) {
166
+ error(`Usage: ${APP_NAME} mcp ${command} <server>
167
+ ${HELP_HINT}`);
168
+ return 1;
169
+ }
170
+ const entry = loaded.servers.find((server) => server.name === name);
171
+ if (!entry) {
172
+ error(`No MCP server named "${name}".${untrustedNote ? ` ${untrustedNote}` : ""} Configured: ${loaded.servers.map((server) => server.name).join(", ") || "none"}.`);
173
+ return 1;
174
+ }
175
+ const connection = createConnection(entry, options, credentials);
176
+ const url = connection.oauthUrl;
177
+ if (!url) {
178
+ error(`MCP server "${name}" does not use OAuth. Only HTTP servers without an Authorization header do.`);
179
+ return 1;
180
+ }
181
+ if (command === "logout") {
182
+ const removed = credentials.remove(url);
183
+ log(removed ? `Signed out of MCP server "${name}".` : `No stored credentials for MCP server "${name}".`);
184
+ return 0;
185
+ }
186
+ const timeout = Number(parsed.values.get("timeout") ?? DEFAULT_LOGIN_TIMEOUT_SECONDS);
187
+ if (!Number.isFinite(timeout) || timeout <= 0) {
188
+ error("--timeout must be a positive number of seconds.");
189
+ return 1;
190
+ }
191
+ try {
192
+ return await login(entry, connection, url, timeout * 1000, options, credentials, log, error);
193
+ } finally {
194
+ await connection.close();
195
+ }
196
+ }
197
+ default:
198
+ error(`Unknown mcp command "${command}".
199
+ ${HELP_HINT}`);
200
+ return 1;
201
+ }
202
+ }
203
+ function parsePairs(option, pairs, error) {
204
+ if (!pairs)
205
+ return {};
206
+ const record = {};
207
+ for (const pair of pairs) {
208
+ const separator = pair.indexOf("=");
209
+ if (separator <= 0) {
210
+ error(`--${option} expects KEY=VALUE, got "${pair}".`);
211
+ return;
212
+ }
213
+ record[pair.slice(0, separator)] = pair.slice(separator + 1);
214
+ }
215
+ return record;
216
+ }
217
+ function add(args, projectConfig, options, log, error) {
218
+ const usage = `Usage: ${APP_NAME} mcp add <server> [options] (--url <url> | -- <command> [args...])
219
+ ${HELP_HINT}`;
220
+ const parsed = parseOptions(args, {
221
+ local: "flag",
222
+ url: "value",
223
+ env: "list",
224
+ cwd: "value",
225
+ header: "list",
226
+ "bearer-token-env-var": "value",
227
+ "oauth-client-id": "value",
228
+ "oauth-client-secret": "value",
229
+ "oauth-callback-port": "value",
230
+ exposure: "value"
231
+ }, error, 2);
232
+ if (!parsed)
233
+ return 1;
234
+ const { positional, values, lists } = parsed;
235
+ const [name, ...command] = positional;
236
+ const url = values.get("url");
237
+ if (!name || url === undefined === (command.length === 0)) {
238
+ error(usage);
239
+ return 1;
240
+ }
241
+ const value = (option) => {
242
+ const found = values.get(option);
243
+ return typeof found === "string" ? found : undefined;
244
+ };
245
+ const exposure = value("exposure");
246
+ const httpOnly = ["header", "bearer-token-env-var", "oauth-client-id", "oauth-client-secret", "oauth-callback-port"];
247
+ const stdioOnly = ["env", "cwd"];
248
+ const misplaced = (url === undefined ? httpOnly : stdioOnly).find((option) => values.has(option) || lists.has(option));
249
+ if (misplaced) {
250
+ error(`--${misplaced} only applies to ${url === undefined ? "HTTP servers (--url)" : "stdio servers"}.`);
251
+ return 1;
252
+ }
253
+ let config;
254
+ if (typeof url === "string") {
255
+ const headers = parsePairs("header", lists.get("header"), error);
256
+ if (!headers)
257
+ return 1;
258
+ const bearer = value("bearer-token-env-var");
259
+ if (bearer !== undefined)
260
+ headers.Authorization = `Bearer \${${bearer}}`;
261
+ const port = value("oauth-callback-port");
262
+ const oauth = {
263
+ ...value("oauth-client-id") === undefined ? {} : { clientId: value("oauth-client-id") },
264
+ ...value("oauth-client-secret") === undefined ? {} : { clientSecret: value("oauth-client-secret") },
265
+ ...port === undefined ? {} : { callbackPort: Number(port) }
266
+ };
267
+ config = {
268
+ url,
269
+ ...Object.keys(headers).length > 0 ? { headers } : {},
270
+ ...Object.keys(oauth).length > 0 ? { oauth } : {}
271
+ };
272
+ } else {
273
+ const env = parsePairs("env", lists.get("env"), error);
274
+ if (!env)
275
+ return 1;
276
+ const [executable, ...commandArgs] = command;
277
+ config = {
278
+ command: executable,
279
+ ...commandArgs.length > 0 ? { args: commandArgs } : {},
280
+ ...Object.keys(env).length > 0 ? { env } : {},
281
+ ...value("cwd") === undefined ? {} : { cwd: value("cwd") }
282
+ };
283
+ }
284
+ if (exposure !== undefined)
285
+ config.exposure = exposure;
286
+ const validated = validateMcpServerConfig(name, config);
287
+ if (typeof validated === "string") {
288
+ error(validated);
289
+ return 1;
290
+ }
291
+ const project = values.has("local");
292
+ const path = project ? projectConfig : join(options.agentDir, "mcp.json");
293
+ const scope = project ? "project" : "global";
294
+ let replaced;
295
+ try {
296
+ replaced = addMcpServerConfig(path, name, validated);
297
+ } catch (addError) {
298
+ error(`Could not update ${path}: ${errorMessage(addError)}`);
299
+ return 1;
300
+ }
301
+ log(`${replaced ? "Replaced" : "Added"} ${scope} MCP server "${name}" in ${path}.`);
302
+ if (project && new ProjectTrustStore(options.agentDir).get(options.cwd) !== true) {
303
+ log(`The project is not trusted, so ${path} is ignored until you start ${APP_NAME} in the project and trust it.`);
304
+ }
305
+ const mayNeedSignIn = "url" in validated && !Object.keys(validated.headers ?? {}).some((header) => header.toLowerCase() === "authorization");
306
+ log(`Check it with: ${APP_NAME} mcp list${mayNeedSignIn ? `. If it requires sign-in: ${APP_NAME} mcp login ${name}` : ""}`);
307
+ return 0;
308
+ }
309
+ function remove(args, projectConfig, options, log, error) {
310
+ const parsed = parseOptions(args, { local: "flag" }, error);
311
+ if (!parsed)
312
+ return 1;
313
+ const [name, ...extra] = parsed.positional;
314
+ if (!name || extra.length > 0) {
315
+ error(`Usage: ${APP_NAME} mcp remove <server> [-l]
316
+ ${HELP_HINT}`);
317
+ return 1;
318
+ }
319
+ const project = parsed.values.has("local");
320
+ const globalConfig = join(options.agentDir, "mcp.json");
321
+ const path = project ? projectConfig : globalConfig;
322
+ const scope = project ? "project" : "global";
323
+ let removed;
324
+ try {
325
+ removed = removeMcpServerConfig(path, name);
326
+ } catch (removeError) {
327
+ error(`Could not update ${path}: ${errorMessage(removeError)}`);
328
+ return 1;
329
+ }
330
+ if (removed) {
331
+ log(`Removed ${scope} MCP server "${name}" from ${path}.`);
332
+ return 0;
333
+ }
334
+ const other = loadMcpConfig({ agentDir: options.agentDir, cwd: options.cwd, projectTrusted: true }).servers.find((server) => server.name === name && server.scope !== scope);
335
+ error(`No ${scope} MCP server named "${name}" in ${path}.${other ? ` It is defined in ${other.source}${other.scope === "project" ? "; use --local" : "; omit --local"}.` : ""}`);
336
+ return 1;
337
+ }
338
+ async function list(loaded, json, untrustedNote, options, credentials, log) {
339
+ const reports = await Promise.all(loaded.servers.map(async (entry) => {
340
+ const report = {
341
+ name: entry.name,
342
+ scope: entry.scope ?? "global",
343
+ source: entry.source,
344
+ enabled: entry.config.enabled !== false,
345
+ exposure: entry.config.exposure ?? "codemode",
346
+ transport: describeTransport(entry),
347
+ state: "disabled",
348
+ tools: []
349
+ };
350
+ if (!report.enabled)
351
+ return report;
352
+ const connection = createConnection(entry, options, credentials);
353
+ try {
354
+ await connection.getClient();
355
+ } catch {}
356
+ report.state = connection.state;
357
+ report.tools = connection.tools.map((tool) => tool.name);
358
+ const overrides = connection.tools.flatMap((tool) => {
359
+ const exposure = getMcpToolExposure(entry.config, tool.name);
360
+ return exposure === report.exposure ? [] : [[tool.name, exposure]];
361
+ });
362
+ if (overrides.length > 0)
363
+ report.toolExposure = Object.fromEntries(overrides);
364
+ if (connection.hasResources) {
365
+ report.resources = connection.resources.length;
366
+ report.resourceTemplates = connection.resourceTemplates.length;
367
+ }
368
+ if (connection.state !== "connected" && connection.error)
369
+ report.error = connection.error;
370
+ await connection.close();
371
+ return report;
372
+ }));
373
+ const failed = loaded.errors.length > 0 || reports.some((report) => report.enabled && report.state !== "connected");
374
+ if (json) {
375
+ log(JSON.stringify({ servers: reports, errors: loaded.errors, ...untrustedNote ? { note: untrustedNote } : {} }, null, 2));
376
+ return failed ? 1 : 0;
377
+ }
378
+ if (reports.length === 0 && loaded.errors.length === 0) {
379
+ log(`No MCP servers configured. Add them to ${join(options.agentDir, "mcp.json")} or .pi/mcp.json.`);
380
+ }
381
+ for (const report of reports) {
382
+ const state = report.state === "connected" ? `connected, ${report.tools.length} tool${report.tools.length === 1 ? "" : "s"}` : report.state === "needs-auth" ? "needs sign-in" : report.state;
383
+ log(`${report.name}: ${state} (${report.exposure}, ${report.scope})`);
384
+ log(` ${report.transport}`);
385
+ if (report.state === "needs-auth")
386
+ log(` sign in with: ${APP_NAME} mcp login ${report.name}`);
387
+ if (report.tools.length > 0) {
388
+ const tools = report.tools.map((tool) => {
389
+ const exposure = report.toolExposure?.[tool];
390
+ return exposure ? `${tool} [${exposure}]` : tool;
391
+ });
392
+ log(` tools: ${tools.join(", ")}`);
393
+ }
394
+ if (report.resources !== undefined) {
395
+ log(` resources: ${report.resources}, URI templates: ${report.resourceTemplates ?? 0}`);
396
+ }
397
+ if (report.error)
398
+ log(` ${report.error.split(`
399
+ `).join(`
400
+ `)}`);
401
+ }
402
+ for (const configError of loaded.errors)
403
+ log(`config error: ${configError}`);
404
+ if (untrustedNote)
405
+ log(untrustedNote);
406
+ return failed ? 1 : 0;
407
+ }
408
+ async function login(entry, connection, url, timeoutMs, options, credentials, log, error) {
409
+ const { name } = entry;
410
+ try {
411
+ await connection.getClient();
412
+ log(`Already signed in to MCP server "${name}" (${connection.tools.length} tools).`);
413
+ return 0;
414
+ } catch {
415
+ if (connection.state !== "needs-auth") {
416
+ error(`MCP server "${name}" failed to connect: ${connection.error ?? "unknown error"}`);
417
+ return 1;
418
+ }
419
+ }
420
+ const openUrl = options.openUrl ?? openBrowser;
421
+ const interactive = process.stdin.isTTY === true && options.openUrl === undefined;
422
+ try {
423
+ await signInMcpServer({
424
+ serverUrl: url,
425
+ store: credentials.forServer(url),
426
+ settings: connection.oauthSettings(),
427
+ challenge: connection.challenge,
428
+ prompt: {
429
+ showAuthorizationUrl: (authorizationUrl) => {
430
+ log(`Sign in to MCP server "${name}" in your browser:
431
+ ${authorizationUrl.href}`);
432
+ openUrl(authorizationUrl.href);
433
+ },
434
+ promptForRedirectUrl: (signal) => waitForRedirectUrl(signal, timeoutMs, interactive)
435
+ }
436
+ });
437
+ } catch (signInError) {
438
+ error(signInError instanceof McpSignInCancelledError ? `Sign-in to MCP server "${name}" was cancelled or not completed within ${Math.round(timeoutMs / 1000)} seconds.` : `Sign-in to MCP server "${name}" failed: ${errorMessage(signInError)}`);
439
+ return 1;
440
+ }
441
+ connection.challenge = undefined;
442
+ try {
443
+ await connection.reconnect();
444
+ } catch (connectError) {
445
+ error(`Signed in, but ${errorMessage(connectError)}`);
446
+ return 1;
447
+ }
448
+ log(`Signed in to MCP server "${name}" (${connection.tools.length} tools).`);
449
+ return 0;
450
+ }
451
+ async function waitForRedirectUrl(signal, timeoutMs, interactive) {
452
+ const controller = new AbortController;
453
+ const abort = () => controller.abort();
454
+ signal.addEventListener("abort", abort, { once: true });
455
+ const timer = setTimeout(abort, timeoutMs);
456
+ try {
457
+ if (!interactive) {
458
+ await new Promise((resolve) => controller.signal.addEventListener("abort", () => resolve(), { once: true }));
459
+ return;
460
+ }
461
+ const readline = createInterface({ input: process.stdin, output: process.stderr });
462
+ try {
463
+ return await readline.question("If the browser cannot reach this machine, paste the URL it was redirected to: ", { signal: controller.signal });
464
+ } catch {
465
+ return;
466
+ } finally {
467
+ readline.close();
468
+ }
469
+ } finally {
470
+ clearTimeout(timer);
471
+ signal.removeEventListener("abort", abort);
472
+ }
473
+ }
474
+ export {
475
+ runMcpCommand
476
+ };