@xopcai/xopc 0.0.224 → 0.0.227

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 (232) hide show
  1. package/dist/browser-ext/manifest.json +1 -1
  2. package/dist/extensions/demo-memory/src/index.js +10 -1
  3. package/dist/extensions/feishu/src/outbound/media-load.js +1 -1
  4. package/dist/extensions/telegram/xopc.extension.json +1 -1
  5. package/dist/gateway/static/root/assets/{activity-store--GBciH10.js → activity-store-BevwE16n.js} +1 -1
  6. package/dist/gateway/static/root/assets/{agent-avatar-dicebear-K7V4XXt7.js → agent-avatar-dicebear-BggVQrEZ.js} +1 -1
  7. package/dist/gateway/static/root/assets/agents-TJpjRHnr.js +68 -0
  8. package/dist/gateway/static/root/assets/{api-HoIz_ija.js → api-Bx_BpIt8.js} +1 -1
  9. package/dist/gateway/static/root/assets/{app-management-settings-panel-xQCmkAHh.js → app-management-settings-panel-BtKP9n2r.js} +1 -1
  10. package/dist/gateway/static/root/assets/{appearance-settings-BRoeA4kU.js → appearance-settings-BoH2NAUX.js} +1 -1
  11. package/dist/gateway/static/root/assets/apps-page-CZ4Da51l.js +1 -0
  12. package/dist/gateway/static/root/assets/{archive-plugin-CteCVsBP.js → archive-plugin-DnceUyxm.js} +1 -1
  13. package/dist/gateway/static/root/assets/{attachment-load-D7xNA2jB.js → attachment-load-Bh8_9gkr.js} +1 -1
  14. package/dist/gateway/static/root/assets/{automations-page-BD1vK7r5.js → automations-page-ZKeAAVxD.js} +1 -1
  15. package/dist/gateway/static/root/assets/automations-workspace-2Y00PvJU.js +6 -0
  16. package/dist/gateway/static/root/assets/{binary-plugins-C3DaJa0W.js → binary-plugins-Cy9er6w-.js} +1 -1
  17. package/dist/gateway/static/root/assets/{block-editor-lTkcHTve.js → block-editor-Cc0wWvNX.js} +3 -3
  18. package/dist/gateway/static/root/assets/browser-settings-page-CbJD27_j.js +8 -0
  19. package/dist/gateway/static/root/assets/{browser-workflow-inputs-1UZ0vnIy.js → browser-workflow-inputs-BS7rpLLl.js} +1 -1
  20. package/dist/gateway/static/root/assets/{browser-workflows-page-BHuJOF4M.js → browser-workflows-page-BdBVUZXm.js} +2 -2
  21. package/dist/gateway/static/root/assets/capabilities-settings-panel-Dv8y6OuP.js +7 -0
  22. package/dist/gateway/static/root/assets/{capability-presets-api-yNqTIuyd.js → capability-presets-api-D1Lqz0Tt.js} +1 -1
  23. package/dist/gateway/static/root/assets/capability-presets-settings-panel-TZmjzWzt.js +3 -0
  24. package/dist/gateway/static/root/assets/{channel-recipient-api-krezGsKc.js → channel-recipient-api-CGuEl-l2.js} +1 -1
  25. package/dist/gateway/static/root/assets/{channels-settings-B4AtvQHk.js → channels-settings-g-68dutA.js} +1 -1
  26. package/dist/gateway/static/root/assets/channels-status-swr-D7KsAeWh.js +1 -0
  27. package/dist/gateway/static/root/assets/{chat-terminal-dock-BRrL2iHA.js → chat-terminal-dock-CdX_7aQh.js} +1 -1
  28. package/dist/gateway/static/root/assets/connectors-page-DXA0rAvQ.js +2 -0
  29. package/dist/gateway/static/root/assets/{cron-expression-Bl-2DzBQ.js → cron-expression-BnSQc4Ek.js} +1 -1
  30. package/dist/gateway/static/root/assets/{date-picker-CxTl6Wlz.js → date-picker-BbuG7zQ_.js} +1 -1
  31. package/dist/gateway/static/root/assets/{dependency-picker-DSl0mOPa.js → dependency-picker-snZeqOmG.js} +1 -1
  32. package/dist/gateway/static/root/assets/{desktop-pet-DTeCmCdb.js → desktop-pet-DJQ8JoR1.js} +1 -1
  33. package/dist/gateway/static/root/assets/{desktop-pet-settings-BNebxg0V.js → desktop-pet-settings-B9txsRtv.js} +1 -1
  34. package/dist/gateway/static/root/assets/{directory-picker-path-field-Dn9XpmXY.js → directory-picker-path-field-D7WKWkNB.js} +1 -1
  35. package/dist/gateway/static/root/assets/{extension-debug-page-D-J-eOTb.js → extension-debug-page-D_7cOCj2.js} +1 -1
  36. package/dist/gateway/static/root/assets/{extension-page-CpST24nU.js → extension-page-Bwu47iUb.js} +1 -1
  37. package/dist/gateway/static/root/assets/{extension-settings-page-4nQXFnFq.js → extension-settings-page-Dwg4dSZM.js} +1 -1
  38. package/dist/gateway/static/root/assets/{gateway-config-api-BHWHduDi.js → gateway-config-api-jURUSte_.js} +1 -1
  39. package/dist/gateway/static/root/assets/{gateway-config-swr-yUxMMVjK.js → gateway-config-swr-6SQXF1yR.js} +1 -1
  40. package/dist/gateway/static/root/assets/{gateway-settings-BimMKmkM.js → gateway-settings-UklJOMLX.js} +1 -1
  41. package/dist/gateway/static/root/assets/{gateway-startup-retry-9mrsL84j.js → gateway-startup-retry-DqWaxyvZ.js} +1 -1
  42. package/dist/gateway/static/root/assets/heartbeat-settings-Djs_nduD.js +1 -0
  43. package/dist/gateway/static/root/assets/{home-page-DSM6aPHF.js → home-page-i6bXCHdo.js} +1 -1
  44. package/dist/gateway/static/root/assets/{image-generation-api-CgFAGDi8.js → image-generation-api-Bxmt6LEr.js} +1 -1
  45. package/dist/gateway/static/root/assets/index-BBBE89vm.css +2 -0
  46. package/dist/gateway/static/root/assets/index-BsD5wygl.js +74 -0
  47. package/dist/gateway/static/root/assets/{keyboard-shortcuts-settings-6Ar5rfX4.js → keyboard-shortcuts-settings-ByVsCH3d.js} +1 -1
  48. package/dist/gateway/static/root/assets/{local-app-workbench-page-tzM0wTL8.js → local-app-workbench-page-BCKEDMlP.js} +2 -2
  49. package/dist/gateway/static/root/assets/{local-apps-page-B5n-x544.js → local-apps-page-D19R-xsz.js} +1 -1
  50. package/dist/gateway/static/root/assets/{locale-store-CPylQjH9.js → locale-store-Ci1Qi0Q-.js} +1 -1
  51. package/dist/gateway/static/root/assets/{logs-page-CgoQlera.js → logs-page-Cy9YQK7j.js} +2 -2
  52. package/dist/gateway/static/root/assets/{management-settings-CXBLyU-0.js → management-settings-G0y7zmfY.js} +1 -1
  53. package/dist/gateway/static/root/assets/{markdown-split-CtmQemJi.js → markdown-split-B69d2HWt.js} +1 -1
  54. package/dist/gateway/static/root/assets/{markdown-view-CUsob4Pz.js → markdown-view-CBM-v2ph.js} +1 -1
  55. package/dist/gateway/static/root/assets/{media-plugins-Dsd-IEOW.js → media-plugins-6TWEQgN_.js} +1 -1
  56. package/dist/gateway/static/root/assets/messages-CtOJwGW3.js +3 -0
  57. package/dist/gateway/static/root/assets/{notes-api-CfKZYrBC.js → notes-api-DLsnnZCS.js} +1 -1
  58. package/dist/gateway/static/root/assets/{notes-page-BKbOTE2n.js → notes-page-CkRJJKDm.js} +1 -1
  59. package/dist/gateway/static/root/assets/notes-workbench-B10T3hGX.js +4 -0
  60. package/dist/gateway/static/root/assets/{product-open-page-DqB9bsDB.js → product-open-page-HxArIvoN.js} +1 -1
  61. package/dist/gateway/static/root/assets/project-detail-page-DsqRlgsy.js +1 -0
  62. package/dist/gateway/static/root/assets/{projects-page-PeXUdGdO.js → projects-page-Bu2PN8OK.js} +1 -1
  63. package/dist/gateway/static/root/assets/{registry-api-B_5D8epF.js → registry-api-lEar5FOV.js} +1 -1
  64. package/dist/gateway/static/root/assets/remote-access-hub-CXACdJ2f.js +1 -0
  65. package/dist/gateway/static/root/assets/{runtime-tools-settings-panel-DBTH_t0O.js → runtime-tools-settings-panel-Bf03UNGD.js} +2 -2
  66. package/dist/gateway/static/root/assets/{schema-form-CqMKAwV0.js → schema-form-CIXMBgx5.js} +1 -1
  67. package/dist/gateway/static/root/assets/sessions-page-CS2knWDT.js +1 -0
  68. package/dist/gateway/static/root/assets/settings-advanced-gate-ByFGk0q_.js +1 -0
  69. package/dist/gateway/static/root/assets/{settings-form-section-dPriuuYq.js → settings-form-section-DgdB26mE.js} +1 -1
  70. package/dist/gateway/static/root/assets/{settings-loading-skeleton-B-Mbm8Va.js → settings-loading-skeleton-efk5W6lG.js} +1 -1
  71. package/dist/gateway/static/root/assets/{settings-page-Dyj3w-Ml.js → settings-page-BHVf4gEP.js} +1 -1
  72. package/dist/gateway/static/root/assets/{setup-status-panel-C4FxY5J3.js → setup-status-panel-WK0dGNMv.js} +1 -1
  73. package/dist/gateway/static/root/assets/{share-preview-page-emEdx7YL.js → share-preview-page-Cod-w2qm.js} +1 -1
  74. package/dist/gateway/static/root/assets/shares-settings-CUqQ31gt.js +1 -0
  75. package/dist/gateway/static/root/assets/skill-reload-api-DweAPjI8.js +1 -0
  76. package/dist/gateway/static/root/assets/{skills-page-BNtYnrRT.js → skills-page-DwCcipqK.js} +1 -1
  77. package/dist/gateway/static/root/assets/{skills-page.utils-DjnbNFs5.js → skills-page.utils-3WSbtl3S.js} +1 -1
  78. package/dist/gateway/static/root/assets/{system-settings-panel-DDStf-jZ.js → system-settings-panel-C5VxqC_s.js} +1 -1
  79. package/dist/gateway/static/root/assets/task-detail-page-DEj-BFMP.js +1 -0
  80. package/dist/gateway/static/root/assets/{theme-store-BN-32Fz5.js → theme-store-Dd89g_ki.js} +1 -1
  81. package/dist/gateway/static/root/assets/{use-autosave-C2mKZ-ua.js → use-autosave-CeV8VJh2.js} +1 -1
  82. package/dist/gateway/static/root/assets/user-context-page-f7yh7aD5.js +1 -0
  83. package/dist/gateway/static/root/assets/{voice-api-key-field-D7OHeQby.js → voice-api-key-field-EmJ-8aZu.js} +1 -1
  84. package/dist/gateway/static/root/assets/{work-discovery-overlay-CIiXie7F.js → work-discovery-overlay-zsk6E3Mi.js} +1 -1
  85. package/dist/gateway/static/root/assets/workflow-run-setup-panel-CBAYvm3G.js +3 -0
  86. package/dist/gateway/static/root/assets/workflows-page-BN0JmHrG.js +5 -0
  87. package/dist/gateway/static/root/index.html +11 -11
  88. package/dist/package.js +1 -1
  89. package/dist/src/agent/agent-manager.d.ts +3 -1
  90. package/dist/src/agent/agent-manager.js +22 -5
  91. package/dist/src/agent/embedded/run-turn.js +2 -0
  92. package/dist/src/agent/mcp/bundle-mcp-config.d.ts +9 -1
  93. package/dist/src/agent/mcp/bundle-mcp-config.js +11 -15
  94. package/dist/src/agent/mcp/embedded-mcp.d.ts +1 -1
  95. package/dist/src/agent/mcp/index.d.ts +1 -0
  96. package/dist/src/agent/mcp/index.js +7 -1
  97. package/dist/src/agent/mcp/mcp-http.d.ts +4 -0
  98. package/dist/src/agent/mcp/mcp-http.js +25 -1
  99. package/dist/src/agent/mcp/mcp-transport-config.d.ts +4 -0
  100. package/dist/src/agent/mcp/mcp-transport-config.js +1 -0
  101. package/dist/src/agent/mcp/mcp-transport.d.ts +7 -1
  102. package/dist/src/agent/mcp/mcp-transport.js +38 -11
  103. package/dist/src/agent/mcp/oauth/index.d.ts +6 -0
  104. package/dist/src/agent/mcp/oauth/index.js +6 -0
  105. package/dist/src/agent/mcp/oauth/mcp-oauth-errors.d.ts +5 -0
  106. package/dist/src/agent/mcp/oauth/mcp-oauth-errors.js +14 -0
  107. package/dist/src/agent/mcp/oauth/mcp-oauth-manager.d.ts +25 -0
  108. package/dist/src/agent/mcp/oauth/mcp-oauth-manager.js +219 -0
  109. package/dist/src/agent/mcp/oauth/mcp-oauth-provider.d.ts +33 -0
  110. package/dist/src/agent/mcp/oauth/mcp-oauth-provider.js +103 -0
  111. package/dist/src/agent/mcp/oauth/mcp-oauth-session.d.ts +29 -0
  112. package/dist/src/agent/mcp/oauth/mcp-oauth-session.js +169 -0
  113. package/dist/src/agent/mcp/oauth/mcp-oauth-store.d.ts +9 -0
  114. package/dist/src/agent/mcp/oauth/mcp-oauth-store.js +79 -0
  115. package/dist/src/agent/mcp/oauth/mcp-oauth-types.d.ts +22 -0
  116. package/dist/src/agent/mcp/oauth/mcp-oauth-types.js +1 -0
  117. package/dist/src/agent/memory/builtin-provider.js +23 -4
  118. package/dist/src/agent/memory/compaction-promotion.d.ts +18 -0
  119. package/dist/src/agent/memory/compaction-promotion.js +211 -0
  120. package/dist/src/agent/memory/context/types.d.ts +5 -0
  121. package/dist/src/agent/memory/manager.d.ts +3 -0
  122. package/dist/src/agent/memory/manager.js +12 -2
  123. package/dist/src/agent/memory/trusted-recall.d.ts +7 -0
  124. package/dist/src/agent/memory/trusted-recall.js +53 -0
  125. package/dist/src/agent/memory/turn-provenance.d.ts +14 -0
  126. package/dist/src/agent/memory/turn-provenance.js +60 -0
  127. package/dist/src/agent/memory/types.d.ts +18 -3
  128. package/dist/src/agent/memory/understanding/service.js +1 -0
  129. package/dist/src/agent/memory/understanding/types.d.ts +1 -0
  130. package/dist/src/agent/memory/user-context-coordinator.js +57 -6
  131. package/dist/src/agent/service.d.ts +2 -0
  132. package/dist/src/agent/service.js +6 -0
  133. package/dist/src/agent/skills/index.d.ts +22 -2
  134. package/dist/src/agent/skills/index.js +74 -32
  135. package/dist/src/agent/skills/marketplace/adapters/store/store-api-client.d.ts +2 -0
  136. package/dist/src/agent/skills/skill-sources.d.ts +0 -1
  137. package/dist/src/agent/skills/skill-sources.js +1 -11
  138. package/dist/src/agent/tools/memory-tool.js +5 -1
  139. package/dist/src/capabilities/store-connector.js +99 -10
  140. package/dist/src/cli/commands/channels.js +1 -1
  141. package/dist/src/cli/commands/connectors.js +1 -1
  142. package/dist/src/cli/commands/doctor/checks/database-schema.js +1 -1
  143. package/dist/src/cli/commands/extension-marketplace.js +1 -1
  144. package/dist/src/cli/commands/models.js +1 -1
  145. package/dist/src/cli/commands/onboard.js +1 -1
  146. package/dist/src/config/config-mutation.d.ts +14 -0
  147. package/dist/src/config/config-mutation.js +33 -0
  148. package/dist/src/config/index.js +3 -3
  149. package/dist/src/config/paths.d.ts +2 -0
  150. package/dist/src/config/paths.js +5 -1
  151. package/dist/src/config/schema.d.ts +17 -0
  152. package/dist/src/config/schema.js +26 -2
  153. package/dist/src/connectors/auth-provider-registry.d.ts +1 -1
  154. package/dist/src/connectors/auth-provider-registry.js +23 -2
  155. package/dist/src/connectors/connected-source-understanding.js +1 -1
  156. package/dist/src/connectors/install.js +3 -3
  157. package/dist/src/connectors/instances.d.ts +2 -1
  158. package/dist/src/connectors/instances.js +15 -5
  159. package/dist/src/connectors/materialize.d.ts +1 -0
  160. package/dist/src/connectors/materialize.js +9 -1
  161. package/dist/src/connectors/runtime-adapter-registry.js +1 -0
  162. package/dist/src/connectors/types.d.ts +4 -1
  163. package/dist/src/extensions/connector-dependencies.d.ts +10 -0
  164. package/dist/src/extensions/connector-dependencies.js +65 -0
  165. package/dist/src/extensions/install.js +27 -0
  166. package/dist/src/extensions/normalize-manifest.js +1 -0
  167. package/dist/src/extensions/sdk/index.js +1 -1
  168. package/dist/src/extensions/types/manifest.d.ts +2 -0
  169. package/dist/src/gateway/hono/routes/capabilities.js +8 -8
  170. package/dist/src/gateway/hono/routes/connectors.js +104 -70
  171. package/dist/src/gateway/hono/routes/mcp.js +77 -5
  172. package/dist/src/gateway/hono/routes/project-skills.js +30 -2
  173. package/dist/src/gateway/hono/routes/you.js +52 -0
  174. package/dist/src/gateway/service.js +8 -8
  175. package/dist/src/knowledge/connected-knowledge-pipeline.js +26 -4
  176. package/dist/src/knowledge/connected-understanding-pipeline.js +12 -3
  177. package/dist/src/knowledge/index.d.ts +0 -1
  178. package/dist/src/knowledge/index.js +1 -2
  179. package/dist/src/projects/project-skill-service.d.ts +28 -6
  180. package/dist/src/projects/project-skill-service.js +76 -29
  181. package/dist/src/session/store.js +27 -0
  182. package/dist/src/storage/sqlite/index.d.ts +1 -0
  183. package/dist/src/storage/sqlite/index.js +2 -1
  184. package/dist/src/storage/sqlite/memory-records-repository.d.ts +9 -1
  185. package/dist/src/storage/sqlite/memory-records-repository.js +40 -6
  186. package/dist/src/storage/sqlite/migrations/134_memory_provenance.sql +18 -0
  187. package/dist/src/storage/sqlite/migrations/135_user_people.sql +59 -0
  188. package/dist/src/storage/sqlite/migrations/runner.d.ts +1 -1
  189. package/dist/src/storage/sqlite/migrations/runner.js +3 -3
  190. package/dist/src/storage/sqlite/migrations/runner.ts +1 -1
  191. package/dist/src/storage/sqlite/schema.js +1 -1
  192. package/dist/src/storage/sqlite/user-people-repository.d.ts +32 -0
  193. package/dist/src/storage/sqlite/user-people-repository.js +246 -0
  194. package/dist/src/tui/backends/embedded-backend.js +1 -1
  195. package/dist/src/user-context/planner.js +8 -3
  196. package/dist/src/user-context/relationships/indexer.d.ts +13 -0
  197. package/dist/src/user-context/relationships/indexer.js +185 -0
  198. package/dist/src/user-context/relationships/service.d.ts +22 -0
  199. package/dist/src/user-context/relationships/service.js +50 -0
  200. package/dist/src/user-context/relationships/types.d.ts +55 -0
  201. package/dist/src/user-context/relationships/types.js +10 -0
  202. package/dist/src/user-context/sources/repository.d.ts +1 -1
  203. package/dist/src/user-context/sources/repository.js +8 -2
  204. package/dist/src/work-discovery/service.js +1 -1
  205. package/package.json +2 -2
  206. package/dist/gateway/static/root/assets/agents-BsxTpXyq.js +0 -68
  207. package/dist/gateway/static/root/assets/apps-page-BXgpBA8w.js +0 -1
  208. package/dist/gateway/static/root/assets/automations-workspace-wrgf-z7D.js +0 -6
  209. package/dist/gateway/static/root/assets/browser-settings-page-zhzNkeVG.js +0 -8
  210. package/dist/gateway/static/root/assets/capabilities-settings-panel-DuCmg2Ej.js +0 -7
  211. package/dist/gateway/static/root/assets/capability-presets-settings-panel-DjiP3mQQ.js +0 -3
  212. package/dist/gateway/static/root/assets/channels-status-swr-DMxB7slL.js +0 -1
  213. package/dist/gateway/static/root/assets/connectors-page-fmda2NEP.js +0 -2
  214. package/dist/gateway/static/root/assets/heartbeat-settings-MUJ3mEC9.js +0 -1
  215. package/dist/gateway/static/root/assets/index-B3zYJBhK.js +0 -74
  216. package/dist/gateway/static/root/assets/index-D3_xSYKd.css +0 -2
  217. package/dist/gateway/static/root/assets/messages-B82nsi9k.js +0 -3
  218. package/dist/gateway/static/root/assets/notes-workbench-BScELo01.js +0 -4
  219. package/dist/gateway/static/root/assets/project-detail-page-DUoyty8X.js +0 -1
  220. package/dist/gateway/static/root/assets/remote-access-hub-sHho-uXP.js +0 -1
  221. package/dist/gateway/static/root/assets/sessions-page-DyvNgaP9.js +0 -1
  222. package/dist/gateway/static/root/assets/settings-advanced-gate-CnYf1R7z.js +0 -1
  223. package/dist/gateway/static/root/assets/shares-settings-BQBVq-sN.js +0 -1
  224. package/dist/gateway/static/root/assets/skill-reload-api-BFoEpQ4I.js +0 -1
  225. package/dist/gateway/static/root/assets/task-detail-page-ZVwr8KbS.js +0 -1
  226. package/dist/gateway/static/root/assets/user-context-page-CHjIinCW.js +0 -1
  227. package/dist/gateway/static/root/assets/workflow-run-setup-panel-9_dAGW3_.js +0 -3
  228. package/dist/gateway/static/root/assets/workflows-page-DXpYJxao.js +0 -5
  229. package/dist/src/extensions/bundle-mcp.d.ts +0 -18
  230. package/dist/src/extensions/bundle-mcp.js +0 -69
  231. package/dist/src/knowledge/people-graph.d.ts +0 -25
  232. package/dist/src/knowledge/people-graph.js +0 -92
@@ -1,26 +1,22 @@
1
1
  import { normalizeConfiguredMcpServers } from "../../config/mcp-config-normalize.js";
2
- import { loadEnabledBundleMcpConfig } from "../../extensions/bundle-mcp.js";
2
+ import { inspectExtensionConnectorDependencies } from "../../extensions/connector-dependencies.js";
3
3
  //#region src/agent/mcp/bundle-mcp-config.ts
4
4
  function listConfiguredMcpServers(params) {
5
5
  const configuredMcp = normalizeConfiguredMcpServers(params.cfg?.mcp?.servers);
6
- return Object.fromEntries(Object.entries(configuredMcp).map(([name, server]) => [name, params.mapConfiguredServer(server, name)]));
6
+ return Object.fromEntries(Object.entries(configuredMcp).filter(([, server]) => {
7
+ const marker = server.xopcConnector;
8
+ return !marker || typeof marker !== "object" || Array.isArray(marker) || marker.enabled !== false;
9
+ }).map(([name, server]) => [name, params.mapConfiguredServer(server, name)]));
7
10
  }
8
11
  function loadMergedBundleMcpConfig(params) {
9
12
  const mapConfiguredServer = params.mapConfiguredServer ?? ((server) => server);
10
- const bundled = loadEnabledBundleMcpConfig({
11
- workspaceDir: params.workspaceDir,
12
- cfg: params.cfg
13
- });
14
- const configured = listConfiguredMcpServers({
15
- cfg: params.cfg,
16
- mapConfiguredServer
17
- });
13
+ params.workspaceDir;
18
14
  return {
19
- config: { mcpServers: {
20
- ...bundled.config.mcpServers,
21
- ...configured
22
- } },
23
- diagnostics: bundled.diagnostics
15
+ config: { mcpServers: { ...listConfiguredMcpServers({
16
+ cfg: params.cfg,
17
+ mapConfiguredServer
18
+ }) } },
19
+ diagnostics: inspectExtensionConnectorDependencies({ cfg: params.cfg })
24
20
  };
25
21
  }
26
22
  //#endregion
@@ -1,5 +1,5 @@
1
1
  import type { Config } from "../../config/schema.js";
2
- import type { BundleMcpDiagnostic, BundleMcpServerConfig } from "../../extensions/bundle-mcp.js";
2
+ import { type BundleMcpDiagnostic, type BundleMcpServerConfig } from "./bundle-mcp-config.js";
3
3
  export type EmbeddedMcpConfig = {
4
4
  mcpServers: Record<string, BundleMcpServerConfig>;
5
5
  diagnostics: BundleMcpDiagnostic[];
@@ -2,3 +2,4 @@ export * from './bundle-mcp-tools.js';
2
2
  export * from './bundle-mcp-policy.js';
3
3
  export * from './bundle-mcp-config.js';
4
4
  export * from './embedded-mcp.js';
5
+ export * from './oauth/index.js';
@@ -1,6 +1,12 @@
1
1
  import { isMcpCatalogToolDenied, mcpToolPolicyId, resolveMcpToolPolicy } from "./bundle-mcp-policy.js";
2
2
  import { loadMergedBundleMcpConfig } from "./bundle-mcp-config.js";
3
3
  import { loadEmbeddedMcpConfig } from "./embedded-mcp.js";
4
+ import { McpAuthorizationRequiredError, isMcpAuthorizationError } from "./oauth/mcp-oauth-errors.js";
5
+ import { McpOAuthStore, canonicalMcpServerUrl, mcpOAuthServerKey } from "./oauth/mcp-oauth-store.js";
6
+ import { XopcMcpOAuthClientProvider } from "./oauth/mcp-oauth-provider.js";
4
7
  import { __testing, createSessionMcpRuntime, disposeAllSessionMcpRuntimes, disposeSessionMcpRuntime, getOrCreateSessionMcpRuntime, getSessionMcpRuntimeManager, retireSessionMcpRuntime, retireSessionMcpRuntimeForSessionKey } from "./bundle-mcp-runtime.js";
5
8
  import "./bundle-mcp-tools.js";
6
- export { __testing, createSessionMcpRuntime, disposeAllSessionMcpRuntimes, disposeSessionMcpRuntime, getOrCreateSessionMcpRuntime, getSessionMcpRuntimeManager, isMcpCatalogToolDenied, loadEmbeddedMcpConfig, loadMergedBundleMcpConfig, mcpToolPolicyId, resolveMcpToolPolicy, retireSessionMcpRuntime, retireSessionMcpRuntimeForSessionKey };
9
+ import { McpOAuthSession } from "./oauth/mcp-oauth-session.js";
10
+ import { McpOAuthManager, getMcpOAuthManager } from "./oauth/mcp-oauth-manager.js";
11
+ import "./oauth/index.js";
12
+ export { McpAuthorizationRequiredError, McpOAuthManager, McpOAuthSession, McpOAuthStore, XopcMcpOAuthClientProvider, __testing, canonicalMcpServerUrl, createSessionMcpRuntime, disposeAllSessionMcpRuntimes, disposeSessionMcpRuntime, getMcpOAuthManager, getOrCreateSessionMcpRuntime, getSessionMcpRuntimeManager, isMcpAuthorizationError, isMcpCatalogToolDenied, loadEmbeddedMcpConfig, loadMergedBundleMcpConfig, mcpOAuthServerKey, mcpToolPolicyId, resolveMcpToolPolicy, retireSessionMcpRuntime, retireSessionMcpRuntimeForSessionKey };
@@ -3,6 +3,10 @@ export type HttpMcpServerLaunchConfig = {
3
3
  transportType: HttpMcpTransportType;
4
4
  url: string;
5
5
  headers?: Record<string, string>;
6
+ auth?: {
7
+ type: "oauth";
8
+ clientId?: string;
9
+ };
6
10
  };
7
11
  export type HttpMcpServerLaunchResult = {
8
12
  ok: true;
@@ -27,12 +27,36 @@ function resolveHttpMcpServerLaunchConfig(raw, options) {
27
27
  let headers;
28
28
  if (raw.headers !== void 0 && raw.headers !== null) if (!isMcpConfigRecord(raw.headers)) options?.onMalformedHeaders?.(raw.headers);
29
29
  else headers = toMcpStringRecord(raw.headers, { onDroppedEntry: options?.onDroppedHeader });
30
+ let auth;
31
+ if (raw.auth !== void 0) {
32
+ if (!isMcpConfigRecord(raw.auth) || raw.auth.type !== "oauth") return {
33
+ ok: false,
34
+ reason: "its auth must be { \"type\": \"oauth\" }"
35
+ };
36
+ if (raw.auth.clientId !== void 0 && (typeof raw.auth.clientId !== "string" || !raw.auth.clientId.trim())) return {
37
+ ok: false,
38
+ reason: "its OAuth clientId must be a non-empty string"
39
+ };
40
+ if ((options?.transportType ?? "streamable-http") !== "streamable-http") return {
41
+ ok: false,
42
+ reason: "OAuth supports streamable HTTP only"
43
+ };
44
+ if (headers && Object.keys(headers).some((key) => key.toLowerCase() === "authorization")) return {
45
+ ok: false,
46
+ reason: "OAuth cannot be combined with a static Authorization header"
47
+ };
48
+ auth = {
49
+ type: "oauth",
50
+ ...typeof raw.auth.clientId === "string" ? { clientId: raw.auth.clientId.trim() } : {}
51
+ };
52
+ }
30
53
  return {
31
54
  ok: true,
32
55
  config: {
33
56
  transportType: options?.transportType ?? "streamable-http",
34
57
  url,
35
- headers
58
+ headers,
59
+ auth
36
60
  }
37
61
  };
38
62
  }
@@ -17,6 +17,10 @@ export type ResolvedHttpMcpTransportConfig = ResolvedBaseMcpTransportConfig & {
17
17
  transportType: HttpMcpTransportType;
18
18
  url: string;
19
19
  headers?: Record<string, string>;
20
+ auth?: {
21
+ type: "oauth";
22
+ clientId?: string;
23
+ };
20
24
  };
21
25
  export type ResolvedMcpTransportConfig = ResolvedStdioMcpTransportConfig | ResolvedHttpMcpTransportConfig;
22
26
  export declare const DEFAULT_MCP_REQUEST_TIMEOUT_MS = 60000;
@@ -50,6 +50,7 @@ function resolveHttpTransportConfig(serverName, rawServer, transportType) {
50
50
  transportType: launch.config.transportType,
51
51
  url: launch.config.url,
52
52
  headers: launch.config.headers,
53
+ auth: launch.config.auth,
53
54
  description: describeHttpMcpServerLaunchConfig(launch.config),
54
55
  connectionTimeoutMs: getConnectionTimeoutMs(rawServer),
55
56
  requestTimeoutMs: getRequestTimeoutMs(rawServer)
@@ -1,5 +1,7 @@
1
+ import type { OAuthClientProvider } from "@modelcontextprotocol/sdk/client/auth.js";
1
2
  import type { Transport } from "@modelcontextprotocol/sdk/shared/transport.js";
2
3
  import type { Config } from "../../config/schema.js";
4
+ import { McpOAuthStore } from "./oauth/mcp-oauth-store.js";
3
5
  export type ResolvedMcpTransport = {
4
6
  transport: Transport;
5
7
  description: string;
@@ -8,4 +10,8 @@ export type ResolvedMcpTransport = {
8
10
  requestTimeoutMs: number;
9
11
  detachStderr?: () => void;
10
12
  };
11
- export declare function resolveMcpTransport(serverName: string, rawServer: unknown, config?: Config): Promise<ResolvedMcpTransport | null>;
13
+ export type ResolveMcpTransportOptions = {
14
+ oauthProvider?: OAuthClientProvider;
15
+ oauthStore?: McpOAuthStore;
16
+ };
17
+ export declare function resolveMcpTransport(serverName: string, rawServer: unknown, config?: Config, options?: ResolveMcpTransportOptions): Promise<ResolvedMcpTransport | null>;
@@ -5,6 +5,8 @@ import { init_string_coerce, normalizeOptionalString } from "../../utils/string-
5
5
  import { buildRuntimeEnvironment, resolveRuntimeCommand } from "../../runtime-tools/environment.js";
6
6
  import { XopcStdioClientTransport } from "./mcp-stdio-transport.js";
7
7
  import { resolveMcpTransportConfig } from "./mcp-transport-config.js";
8
+ import { McpOAuthStore } from "./oauth/mcp-oauth-store.js";
9
+ import { XopcMcpOAuthClientProvider } from "./oauth/mcp-oauth-provider.js";
8
10
  import { SSEClientTransport } from "@modelcontextprotocol/sdk/client/sse.js";
9
11
  import { StreamableHTTPClientTransport } from "@modelcontextprotocol/sdk/client/streamableHttp.js";
10
12
  import { getDefaultEnvironment } from "@modelcontextprotocol/sdk/client/stdio.js";
@@ -48,7 +50,18 @@ function buildSseEventSourceFetch(headers) {
48
50
  });
49
51
  };
50
52
  }
51
- async function resolveMcpTransport(serverName, rawServer, config) {
53
+ function buildScopedHttpFetch(serverUrl, headers) {
54
+ return async (url, init) => {
55
+ const mergedHeaders = new Headers();
56
+ if (new URL(url).origin === serverUrl.origin) for (const [key, value] of Object.entries(headers)) mergedHeaders.set(key, value);
57
+ if (init?.headers) new Headers(init.headers).forEach((value, key) => mergedHeaders.set(key, value));
58
+ return fetchWithUndici(url, {
59
+ ...init,
60
+ headers: mergedHeaders
61
+ });
62
+ };
63
+ }
64
+ async function resolveMcpTransport(serverName, rawServer, config, options = {}) {
52
65
  const resolved = resolveMcpTransportConfig(serverName, rawServer);
53
66
  if (!resolved) return null;
54
67
  if (resolved.kind === "stdio") {
@@ -82,16 +95,30 @@ async function resolveMcpTransport(serverName, rawServer, config) {
82
95
  detachStderr: attachStderrLogging(serverName, transport)
83
96
  };
84
97
  }
85
- if (resolved.transportType === "streamable-http") return {
86
- transport: new StreamableHTTPClientTransport(new URL(resolved.url), {
87
- requestInit: resolved.headers ? { headers: resolved.headers } : void 0,
88
- fetch: fetchWithUndici
89
- }),
90
- description: resolved.description,
91
- transportType: "streamable-http",
92
- connectionTimeoutMs: resolved.connectionTimeoutMs,
93
- requestTimeoutMs: resolved.requestTimeoutMs
94
- };
98
+ if (resolved.transportType === "streamable-http") {
99
+ const serverUrl = new URL(resolved.url);
100
+ const oauthEnabled = Boolean(resolved.auth);
101
+ let oauthProvider = options.oauthProvider;
102
+ if (resolved.auth && !oauthProvider) {
103
+ const store = options.oauthStore ?? new McpOAuthStore();
104
+ if ((await store.load(serverUrl))?.tokens) oauthProvider = new XopcMcpOAuthClientProvider({
105
+ serverUrl,
106
+ clientId: resolved.auth.clientId,
107
+ store
108
+ });
109
+ }
110
+ return {
111
+ transport: new StreamableHTTPClientTransport(serverUrl, {
112
+ authProvider: oauthProvider,
113
+ requestInit: !oauthEnabled && resolved.headers ? { headers: resolved.headers } : void 0,
114
+ fetch: oauthEnabled ? buildScopedHttpFetch(serverUrl, resolved.headers ?? {}) : fetchWithUndici
115
+ }),
116
+ description: resolved.description,
117
+ transportType: "streamable-http",
118
+ connectionTimeoutMs: resolved.connectionTimeoutMs,
119
+ requestTimeoutMs: resolved.requestTimeoutMs
120
+ };
121
+ }
95
122
  const headers = { ...resolved.headers };
96
123
  const hasHeaders = Object.keys(headers).length > 0;
97
124
  return {
@@ -0,0 +1,6 @@
1
+ export * from './mcp-oauth-errors.js';
2
+ export * from './mcp-oauth-manager.js';
3
+ export * from './mcp-oauth-provider.js';
4
+ export * from './mcp-oauth-session.js';
5
+ export * from './mcp-oauth-store.js';
6
+ export type * from './mcp-oauth-types.js';
@@ -0,0 +1,6 @@
1
+ import { McpAuthorizationRequiredError, isMcpAuthorizationError } from "./mcp-oauth-errors.js";
2
+ import { McpOAuthStore, canonicalMcpServerUrl, mcpOAuthServerKey } from "./mcp-oauth-store.js";
3
+ import { XopcMcpOAuthClientProvider } from "./mcp-oauth-provider.js";
4
+ import { McpOAuthSession } from "./mcp-oauth-session.js";
5
+ import { McpOAuthManager, getMcpOAuthManager } from "./mcp-oauth-manager.js";
6
+ export { McpAuthorizationRequiredError, McpOAuthManager, McpOAuthSession, McpOAuthStore, XopcMcpOAuthClientProvider, canonicalMcpServerUrl, getMcpOAuthManager, isMcpAuthorizationError, mcpOAuthServerKey };
@@ -0,0 +1,5 @@
1
+ export declare class McpAuthorizationRequiredError extends Error {
2
+ readonly code = "MCP_AUTHORIZATION_REQUIRED";
3
+ constructor(message?: string);
4
+ }
5
+ export declare function isMcpAuthorizationError(error: unknown): boolean;
@@ -0,0 +1,14 @@
1
+ import { UnauthorizedError } from "@modelcontextprotocol/sdk/client/auth.js";
2
+ //#region src/agent/mcp/oauth/mcp-oauth-errors.ts
3
+ var McpAuthorizationRequiredError = class extends Error {
4
+ code = "MCP_AUTHORIZATION_REQUIRED";
5
+ constructor(message = "MCP server authorization is required") {
6
+ super(message);
7
+ this.name = "McpAuthorizationRequiredError";
8
+ }
9
+ };
10
+ function isMcpAuthorizationError(error) {
11
+ return error instanceof UnauthorizedError || error instanceof McpAuthorizationRequiredError;
12
+ }
13
+ //#endregion
14
+ export { McpAuthorizationRequiredError, isMcpAuthorizationError };
@@ -0,0 +1,25 @@
1
+ import type { Config } from '../../../config/schema.js';
2
+ import { McpOAuthStore } from './mcp-oauth-store.js';
3
+ import type { McpOAuthSessionSnapshot } from './mcp-oauth-types.js';
4
+ export type McpOAuthConnectionStatus = 'not_configured' | 'disconnected' | 'authorizing' | 'connected' | 'error';
5
+ export type McpOAuthStatus = {
6
+ configured: boolean;
7
+ status: McpOAuthConnectionStatus;
8
+ session?: McpOAuthSessionSnapshot;
9
+ };
10
+ type StartMcpOAuthParams = {
11
+ serverId: string;
12
+ rawServer: unknown;
13
+ cfg?: Config;
14
+ };
15
+ export declare class McpOAuthManager {
16
+ private readonly store;
17
+ private readonly sessionsByServerUrl;
18
+ constructor(store?: McpOAuthStore);
19
+ status(serverId: string, rawServer: unknown): Promise<McpOAuthStatus>;
20
+ start(params: StartMcpOAuthParams): Promise<McpOAuthStatus>;
21
+ disconnect(serverId: string, rawServer: unknown): Promise<McpOAuthStatus>;
22
+ private finishAuthorization;
23
+ }
24
+ export declare function getMcpOAuthManager(): McpOAuthManager;
25
+ export {};
@@ -0,0 +1,219 @@
1
+ import { createLogger } from "../../../utils/logger/index.js";
2
+ import { init_logger } from "../../../utils/logger.js";
3
+ import { resolveGlobalSingleton } from "../../../utils/global-singleton.js";
4
+ import { redactSensitiveUrlLikeString } from "../../../utils/redact-sensitive-url.js";
5
+ import { resolveConnectorSecretReferences } from "../../../connectors/secret-store.js";
6
+ import { resolveMcpTransportConfig } from "../mcp-transport-config.js";
7
+ import { isMcpAuthorizationError } from "./mcp-oauth-errors.js";
8
+ import { McpOAuthStore, canonicalMcpServerUrl } from "./mcp-oauth-store.js";
9
+ import { XopcMcpOAuthClientProvider } from "./mcp-oauth-provider.js";
10
+ import { resolveMcpTransport } from "../mcp-transport.js";
11
+ import { disposeAllSessionMcpRuntimes } from "../bundle-mcp-runtime.js";
12
+ import { McpOAuthSession } from "./mcp-oauth-session.js";
13
+ import { Client } from "@modelcontextprotocol/sdk/client/index.js";
14
+ //#region src/agent/mcp/oauth/mcp-oauth-manager.ts
15
+ init_logger();
16
+ const log = createLogger("Mcp:OAuth");
17
+ const MCP_OAUTH_MANAGER_KEY = Symbol.for("xopc.mcpOAuthManager");
18
+ function createClient() {
19
+ return new Client({
20
+ name: "xopc-mcp-oauth",
21
+ version: "0.0.0"
22
+ });
23
+ }
24
+ async function connectClient(client, resolved) {
25
+ await new Promise((resolve, reject) => {
26
+ const timer = setTimeout(() => reject(/* @__PURE__ */ new Error(`MCP server connection timed out after ${resolved.connectionTimeoutMs}ms`)), resolved.connectionTimeoutMs);
27
+ client.connect(resolved.transport).then(() => {
28
+ clearTimeout(timer);
29
+ resolve();
30
+ }, (error) => {
31
+ clearTimeout(timer);
32
+ reject(error);
33
+ });
34
+ });
35
+ }
36
+ async function closeConnection(client, resolved) {
37
+ await client.close().catch(() => {});
38
+ await resolved.transport.close().catch(() => {});
39
+ resolved.detachStderr?.();
40
+ }
41
+ function isAuthorizing(snapshot) {
42
+ return [
43
+ "starting",
44
+ "waiting_browser",
45
+ "exchanging_code"
46
+ ].includes(snapshot.status);
47
+ }
48
+ var McpOAuthManager = class {
49
+ store;
50
+ sessionsByServerUrl = /* @__PURE__ */ new Map();
51
+ constructor(store = new McpOAuthStore()) {
52
+ this.store = store;
53
+ }
54
+ async status(serverId, rawServer) {
55
+ const resolved = resolveMcpTransportConfig(serverId, rawServer);
56
+ if (!resolved || resolved.kind !== "http" || !resolved.auth) return {
57
+ configured: false,
58
+ status: "not_configured"
59
+ };
60
+ const session = this.sessionsByServerUrl.get(canonicalMcpServerUrl(resolved.url))?.snapshot();
61
+ if (session) {
62
+ if (isAuthorizing(session)) return {
63
+ configured: true,
64
+ status: "authorizing",
65
+ session
66
+ };
67
+ if (session.status === "failed" || session.status === "expired") return {
68
+ configured: true,
69
+ status: "error",
70
+ session
71
+ };
72
+ if (session.status === "connected") return {
73
+ configured: true,
74
+ status: "connected",
75
+ session
76
+ };
77
+ }
78
+ return {
79
+ configured: true,
80
+ status: (await this.store.load(resolved.url))?.tokens ? "connected" : "disconnected",
81
+ session
82
+ };
83
+ }
84
+ async start(params) {
85
+ const rawServer = await resolveConnectorSecretReferences(params.rawServer);
86
+ const resolvedConfig = resolveMcpTransportConfig(params.serverId, rawServer);
87
+ if (!resolvedConfig || resolvedConfig.kind !== "http" || !resolvedConfig.auth) throw new Error(`MCP server "${params.serverId}" is not configured for OAuth`);
88
+ const serverUrl = new URL(resolvedConfig.url);
89
+ const sessionKey = canonicalMcpServerUrl(serverUrl);
90
+ const previous = this.sessionsByServerUrl.get(sessionKey);
91
+ if (previous && isAuthorizing(previous.snapshot())) return this.status(params.serverId, params.rawServer);
92
+ if (previous) await previous.close();
93
+ const session = new McpOAuthSession(params.serverId, serverUrl);
94
+ this.sessionsByServerUrl.set(sessionKey, session);
95
+ try {
96
+ await session.start();
97
+ } catch (error) {
98
+ this.sessionsByServerUrl.delete(sessionKey);
99
+ throw error;
100
+ }
101
+ try {
102
+ await this.store.update(serverUrl, (current) => current ? {
103
+ ...current,
104
+ clientInformation: void 0,
105
+ tokens: void 0,
106
+ tokensSavedAt: void 0
107
+ } : void 0);
108
+ } catch (error) {
109
+ session.fail(error);
110
+ throw error;
111
+ }
112
+ let provider;
113
+ let resolved;
114
+ try {
115
+ provider = new XopcMcpOAuthClientProvider({
116
+ serverUrl,
117
+ clientId: resolvedConfig.auth.clientId,
118
+ store: this.store,
119
+ interaction: {
120
+ redirectUrl: session.redirectUrl,
121
+ state: session.state,
122
+ onRedirect: (authorizationUrl) => session.setAuthorizationUrl(authorizationUrl)
123
+ }
124
+ });
125
+ resolved = await resolveMcpTransport(params.serverId, rawServer, params.cfg, {
126
+ oauthProvider: provider,
127
+ oauthStore: this.store
128
+ });
129
+ } catch (error) {
130
+ session.fail(error);
131
+ return this.status(params.serverId, params.rawServer);
132
+ }
133
+ if (!resolved || resolved.transportType !== "streamable-http") {
134
+ session.fail(/* @__PURE__ */ new Error("MCP OAuth requires a streamable HTTP transport"));
135
+ await resolved?.transport.close().catch(() => {});
136
+ return this.status(params.serverId, params.rawServer);
137
+ }
138
+ const client = createClient();
139
+ try {
140
+ await connectClient(client, resolved);
141
+ session.complete();
142
+ await closeConnection(client, resolved);
143
+ await disposeAllSessionMcpRuntimes();
144
+ } catch (error) {
145
+ if (!isMcpAuthorizationError(error) || !session.snapshot().authorizationUrl) {
146
+ session.fail(error);
147
+ await closeConnection(client, resolved);
148
+ } else this.finishAuthorization({
149
+ session,
150
+ provider,
151
+ client,
152
+ resolved,
153
+ params: {
154
+ ...params,
155
+ rawServer
156
+ }
157
+ });
158
+ }
159
+ return this.status(params.serverId, params.rawServer);
160
+ }
161
+ async disconnect(serverId, rawServer) {
162
+ const resolved = resolveMcpTransportConfig(serverId, rawServer);
163
+ if (!resolved || resolved.kind !== "http" || !resolved.auth) throw new Error(`MCP server "${serverId}" is not configured for OAuth`);
164
+ const sessionKey = canonicalMcpServerUrl(resolved.url);
165
+ const session = this.sessionsByServerUrl.get(sessionKey);
166
+ this.sessionsByServerUrl.delete(sessionKey);
167
+ if (session) await session.close();
168
+ await this.store.delete(resolved.url);
169
+ await disposeAllSessionMcpRuntimes();
170
+ return {
171
+ configured: true,
172
+ status: "disconnected"
173
+ };
174
+ }
175
+ async finishAuthorization(context) {
176
+ const { session, provider, client, resolved, params } = context;
177
+ try {
178
+ const code = await session.waitForCode();
179
+ await resolved.transport.finishAuth(code);
180
+ if (session.snapshot().status === "cancelled") {
181
+ await this.store.delete(session.serverUrl);
182
+ await closeConnection(client, resolved);
183
+ return;
184
+ }
185
+ await closeConnection(client, resolved);
186
+ const authenticated = await resolveMcpTransport(params.serverId, params.rawServer, params.cfg, {
187
+ oauthProvider: provider,
188
+ oauthStore: this.store
189
+ });
190
+ if (!authenticated) throw new Error("MCP transport could not be created after authorization");
191
+ const authenticatedClient = createClient();
192
+ try {
193
+ await connectClient(authenticatedClient, authenticated);
194
+ } finally {
195
+ await closeConnection(authenticatedClient, authenticated);
196
+ }
197
+ session.complete();
198
+ await disposeAllSessionMcpRuntimes();
199
+ } catch (error) {
200
+ if (session.snapshot().status === "cancelled") {
201
+ await this.store.delete(session.serverUrl);
202
+ await closeConnection(client, resolved);
203
+ return;
204
+ }
205
+ session.fail(error);
206
+ await closeConnection(client, resolved);
207
+ log.warn({
208
+ err: error,
209
+ phase: "mcp.oauth_finish",
210
+ serverId: params.serverId
211
+ }, `MCP OAuth failed for server "${params.serverId}": ${redactSensitiveUrlLikeString(error instanceof Error ? error.message : String(error))}`);
212
+ }
213
+ }
214
+ };
215
+ function getMcpOAuthManager() {
216
+ return resolveGlobalSingleton(MCP_OAUTH_MANAGER_KEY, () => new McpOAuthManager());
217
+ }
218
+ //#endregion
219
+ export { McpOAuthManager, getMcpOAuthManager };
@@ -0,0 +1,33 @@
1
+ import type { OAuthClientProvider, OAuthDiscoveryState } from '@modelcontextprotocol/sdk/client/auth.js';
2
+ import type { OAuthClientInformationMixed, OAuthClientMetadata, OAuthTokens } from '@modelcontextprotocol/sdk/shared/auth.js';
3
+ import { McpOAuthStore } from './mcp-oauth-store.js';
4
+ export type McpOAuthInteraction = {
5
+ redirectUrl: URL;
6
+ state: string;
7
+ onRedirect: (authorizationUrl: URL) => void | Promise<void>;
8
+ };
9
+ export type McpOAuthClientProviderOptions = {
10
+ serverUrl: URL;
11
+ clientId?: string;
12
+ interaction?: McpOAuthInteraction;
13
+ store?: McpOAuthStore;
14
+ };
15
+ export declare class XopcMcpOAuthClientProvider implements OAuthClientProvider {
16
+ private readonly options;
17
+ private readonly store;
18
+ private codeVerifierValue?;
19
+ constructor(options: McpOAuthClientProviderOptions);
20
+ get redirectUrl(): URL;
21
+ get clientMetadata(): OAuthClientMetadata;
22
+ state(): string | undefined;
23
+ clientInformation(): Promise<OAuthClientInformationMixed | undefined>;
24
+ saveClientInformation(clientInformation: OAuthClientInformationMixed): Promise<void>;
25
+ tokens(): Promise<OAuthTokens | undefined>;
26
+ saveTokens(tokens: OAuthTokens): Promise<void>;
27
+ redirectToAuthorization(authorizationUrl: URL): Promise<void>;
28
+ saveCodeVerifier(codeVerifier: string): void;
29
+ codeVerifier(): string;
30
+ saveDiscoveryState(discoveryState: OAuthDiscoveryState): Promise<void>;
31
+ discoveryState(): Promise<OAuthDiscoveryState | undefined>;
32
+ invalidateCredentials(scope: 'all' | 'client' | 'tokens' | 'verifier' | 'discovery'): Promise<void>;
33
+ }
@@ -0,0 +1,103 @@
1
+ import { McpAuthorizationRequiredError } from "./mcp-oauth-errors.js";
2
+ import { McpOAuthStore } from "./mcp-oauth-store.js";
3
+ //#region src/agent/mcp/oauth/mcp-oauth-provider.ts
4
+ var XopcMcpOAuthClientProvider = class {
5
+ store;
6
+ codeVerifierValue;
7
+ constructor(options) {
8
+ this.options = options;
9
+ this.store = options.store ?? new McpOAuthStore();
10
+ }
11
+ get redirectUrl() {
12
+ return this.options.interaction?.redirectUrl ?? new URL("http://127.0.0.1/oauth/callback");
13
+ }
14
+ get clientMetadata() {
15
+ return {
16
+ client_name: "XOPC",
17
+ client_uri: "https://xopc.ai",
18
+ redirect_uris: [this.redirectUrl.toString()],
19
+ grant_types: ["authorization_code", "refresh_token"],
20
+ response_types: ["code"],
21
+ token_endpoint_auth_method: "none"
22
+ };
23
+ }
24
+ state() {
25
+ return this.options.interaction?.state;
26
+ }
27
+ async clientInformation() {
28
+ if (this.options.clientId) return { client_id: this.options.clientId };
29
+ return (await this.store.load(this.options.serverUrl))?.clientInformation;
30
+ }
31
+ async saveClientInformation(clientInformation) {
32
+ await this.store.update(this.options.serverUrl, (current) => ({
33
+ ...current,
34
+ version: 1,
35
+ serverUrl: this.options.serverUrl.toString(),
36
+ clientInformation,
37
+ updatedAt: current?.updatedAt ?? (/* @__PURE__ */ new Date()).toISOString()
38
+ }));
39
+ }
40
+ async tokens() {
41
+ return (await this.store.load(this.options.serverUrl))?.tokens;
42
+ }
43
+ async saveTokens(tokens) {
44
+ await this.store.update(this.options.serverUrl, (current) => ({
45
+ ...current,
46
+ version: 1,
47
+ serverUrl: this.options.serverUrl.toString(),
48
+ tokens,
49
+ tokensSavedAt: Date.now(),
50
+ updatedAt: current?.updatedAt ?? (/* @__PURE__ */ new Date()).toISOString()
51
+ }));
52
+ }
53
+ async redirectToAuthorization(authorizationUrl) {
54
+ if (!this.options.interaction) throw new McpAuthorizationRequiredError();
55
+ await this.options.interaction.onRedirect(authorizationUrl);
56
+ }
57
+ saveCodeVerifier(codeVerifier) {
58
+ this.codeVerifierValue = codeVerifier;
59
+ }
60
+ codeVerifier() {
61
+ if (!this.codeVerifierValue) throw new Error("MCP OAuth code verifier is unavailable");
62
+ return this.codeVerifierValue;
63
+ }
64
+ async saveDiscoveryState(discoveryState) {
65
+ await this.store.update(this.options.serverUrl, (current) => {
66
+ const authorizationServerChanged = Boolean(current?.discoveryState?.authorizationServerUrl && current.discoveryState.authorizationServerUrl !== discoveryState.authorizationServerUrl);
67
+ return {
68
+ ...current,
69
+ version: 1,
70
+ serverUrl: this.options.serverUrl.toString(),
71
+ discoveryState,
72
+ clientInformation: authorizationServerChanged ? void 0 : current?.clientInformation,
73
+ tokens: authorizationServerChanged ? void 0 : current?.tokens,
74
+ tokensSavedAt: authorizationServerChanged ? void 0 : current?.tokensSavedAt,
75
+ updatedAt: current?.updatedAt ?? (/* @__PURE__ */ new Date()).toISOString()
76
+ };
77
+ });
78
+ }
79
+ async discoveryState() {
80
+ return (await this.store.load(this.options.serverUrl))?.discoveryState;
81
+ }
82
+ async invalidateCredentials(scope) {
83
+ if (scope === "verifier") {
84
+ this.codeVerifierValue = void 0;
85
+ return;
86
+ }
87
+ await this.store.update(this.options.serverUrl, (current) => {
88
+ if (!current) return void 0;
89
+ if (scope === "all") return void 0;
90
+ return {
91
+ ...current,
92
+ ...scope === "client" ? { clientInformation: void 0 } : {},
93
+ ...scope === "tokens" ? {
94
+ tokens: void 0,
95
+ tokensSavedAt: void 0
96
+ } : {},
97
+ ...scope === "discovery" ? { discoveryState: void 0 } : {}
98
+ };
99
+ });
100
+ }
101
+ };
102
+ //#endregion
103
+ export { XopcMcpOAuthClientProvider };