@rudderhq/server 0.5.2-canary.2 → 0.6.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 (386) hide show
  1. package/dist/bootstrap/register-api-routes.d.ts.map +1 -1
  2. package/dist/bootstrap/register-api-routes.js +15 -0
  3. package/dist/bootstrap/register-api-routes.js.map +1 -1
  4. package/dist/bootstrap/types.d.ts +11 -0
  5. package/dist/bootstrap/types.d.ts.map +1 -1
  6. package/dist/bundled-plugins/plugin-linear/dist/worker.js +741 -7
  7. package/dist/bundled-plugins/plugin-linear/dist/worker.js.map +3 -3
  8. package/dist/config.d.ts +2 -0
  9. package/dist/config.d.ts.map +1 -1
  10. package/dist/config.js +3 -0
  11. package/dist/config.js.map +1 -1
  12. package/dist/index.d.ts.map +1 -1
  13. package/dist/index.js +28 -1
  14. package/dist/index.js.map +1 -1
  15. package/dist/local-runtime.d.ts +7 -0
  16. package/dist/local-runtime.d.ts.map +1 -1
  17. package/dist/local-runtime.js +15 -1
  18. package/dist/local-runtime.js.map +1 -1
  19. package/dist/middleware/auth.js +2 -2
  20. package/dist/middleware/auth.js.map +1 -1
  21. package/dist/middleware/error-handler.d.ts.map +1 -1
  22. package/dist/middleware/error-handler.js +3 -2
  23. package/dist/middleware/error-handler.js.map +1 -1
  24. package/dist/middleware/logger.d.ts +4 -0
  25. package/dist/middleware/logger.d.ts.map +1 -1
  26. package/dist/middleware/logger.js +82 -7
  27. package/dist/middleware/logger.js.map +1 -1
  28. package/dist/middleware/logger.test.js +94 -1
  29. package/dist/middleware/logger.test.js.map +1 -1
  30. package/dist/routes/chats.annotation-routes.d.ts +47 -0
  31. package/dist/routes/chats.annotation-routes.d.ts.map +1 -0
  32. package/dist/routes/chats.annotation-routes.js +164 -0
  33. package/dist/routes/chats.annotation-routes.js.map +1 -0
  34. package/dist/routes/chats.d.ts.map +1 -1
  35. package/dist/routes/chats.js +467 -165
  36. package/dist/routes/chats.js.map +1 -1
  37. package/dist/routes/chats.stream-routes.d.ts +1 -10
  38. package/dist/routes/chats.stream-routes.d.ts.map +1 -1
  39. package/dist/routes/chats.stream-routes.js +168 -110
  40. package/dist/routes/chats.stream-routes.js.map +1 -1
  41. package/dist/routes/chats.stream-support.d.ts +79 -0
  42. package/dist/routes/chats.stream-support.d.ts.map +1 -0
  43. package/dist/routes/chats.stream-support.js +121 -0
  44. package/dist/routes/chats.stream-support.js.map +1 -0
  45. package/dist/routes/issues.comments-attachments.d.ts.map +1 -1
  46. package/dist/routes/issues.comments-attachments.js +16 -2
  47. package/dist/routes/issues.comments-attachments.js.map +1 -1
  48. package/dist/routes/issues.d.ts.map +1 -1
  49. package/dist/routes/issues.js +21 -4
  50. package/dist/routes/issues.js.map +1 -1
  51. package/dist/routes/issues.mutations.d.ts.map +1 -1
  52. package/dist/routes/issues.mutations.js +20 -33
  53. package/dist/routes/issues.mutations.js.map +1 -1
  54. package/dist/routes/managed-mcp-agent-bindings.d.ts +15 -0
  55. package/dist/routes/managed-mcp-agent-bindings.d.ts.map +1 -0
  56. package/dist/routes/managed-mcp-agent-bindings.js +66 -0
  57. package/dist/routes/managed-mcp-agent-bindings.js.map +1 -0
  58. package/dist/routes/managed-mcp-connections.d.ts +8 -0
  59. package/dist/routes/managed-mcp-connections.d.ts.map +1 -0
  60. package/dist/routes/managed-mcp-connections.js +189 -0
  61. package/dist/routes/managed-mcp-connections.js.map +1 -0
  62. package/dist/routes/managed-mcp-runtime.d.ts +5 -0
  63. package/dist/routes/managed-mcp-runtime.d.ts.map +1 -0
  64. package/dist/routes/managed-mcp-runtime.js +148 -0
  65. package/dist/routes/managed-mcp-runtime.js.map +1 -0
  66. package/dist/routes/messenger.d.ts.map +1 -1
  67. package/dist/routes/messenger.js +1 -1
  68. package/dist/routes/messenger.js.map +1 -1
  69. package/dist/services/access.d.ts.map +1 -1
  70. package/dist/services/access.js +91 -12
  71. package/dist/services/access.js.map +1 -1
  72. package/dist/services/agent-run-context.d.ts +1 -0
  73. package/dist/services/agent-run-context.d.ts.map +1 -1
  74. package/dist/services/agent-run-context.js +5 -1
  75. package/dist/services/agent-run-context.js.map +1 -1
  76. package/dist/services/board-auth.d.ts +2 -2
  77. package/dist/services/chat-annotation-copy-lineage.d.ts +32 -0
  78. package/dist/services/chat-annotation-copy-lineage.d.ts.map +1 -0
  79. package/dist/services/chat-annotation-copy-lineage.js +110 -0
  80. package/dist/services/chat-annotation-copy-lineage.js.map +1 -0
  81. package/dist/services/chat-assistant.annotations.d.ts +16 -0
  82. package/dist/services/chat-assistant.annotations.d.ts.map +1 -0
  83. package/dist/services/chat-assistant.annotations.js +108 -0
  84. package/dist/services/chat-assistant.annotations.js.map +1 -0
  85. package/dist/services/chat-assistant.annotations.test.d.ts +2 -0
  86. package/dist/services/chat-assistant.annotations.test.d.ts.map +1 -0
  87. package/dist/services/chat-assistant.annotations.test.js +257 -0
  88. package/dist/services/chat-assistant.annotations.test.js.map +1 -0
  89. package/dist/services/chat-assistant.d.ts.map +1 -1
  90. package/dist/services/chat-assistant.helpers.d.ts +2 -3
  91. package/dist/services/chat-assistant.helpers.d.ts.map +1 -1
  92. package/dist/services/chat-assistant.helpers.js +37 -53
  93. package/dist/services/chat-assistant.helpers.js.map +1 -1
  94. package/dist/services/chat-assistant.js +61 -5
  95. package/dist/services/chat-assistant.js.map +1 -1
  96. package/dist/services/chat-generation-protocol.d.ts +8 -15
  97. package/dist/services/chat-generation-protocol.d.ts.map +1 -1
  98. package/dist/services/chat-generation-protocol.js +19 -59
  99. package/dist/services/chat-generation-protocol.js.map +1 -1
  100. package/dist/services/chat-generation-protocol.test.js +168 -6
  101. package/dist/services/chat-generation-protocol.test.js.map +1 -1
  102. package/dist/services/chat-generation-provenance.d.ts +14 -0
  103. package/dist/services/chat-generation-provenance.d.ts.map +1 -0
  104. package/dist/services/chat-generation-provenance.js +71 -0
  105. package/dist/services/chat-generation-provenance.js.map +1 -0
  106. package/dist/services/chat-inline-annotation-rendering.d.ts +2 -0
  107. package/dist/services/chat-inline-annotation-rendering.d.ts.map +1 -0
  108. package/dist/services/chat-inline-annotation-rendering.js +265 -0
  109. package/dist/services/chat-inline-annotation-rendering.js.map +1 -0
  110. package/dist/services/chat-inline-annotation-resolved-labels.d.ts +11 -0
  111. package/dist/services/chat-inline-annotation-resolved-labels.d.ts.map +1 -0
  112. package/dist/services/chat-inline-annotation-resolved-labels.js +490 -0
  113. package/dist/services/chat-inline-annotation-resolved-labels.js.map +1 -0
  114. package/dist/services/chat-inline-annotation-validation.d.ts +15 -0
  115. package/dist/services/chat-inline-annotation-validation.d.ts.map +1 -0
  116. package/dist/services/chat-inline-annotation-validation.js +430 -0
  117. package/dist/services/chat-inline-annotation-validation.js.map +1 -0
  118. package/dist/services/chat-inline-annotations.d.ts +18 -0
  119. package/dist/services/chat-inline-annotations.d.ts.map +1 -0
  120. package/dist/services/chat-inline-annotations.js +52 -0
  121. package/dist/services/chat-inline-annotations.js.map +1 -0
  122. package/dist/services/chat-inline-annotations.test.d.ts +2 -0
  123. package/dist/services/chat-inline-annotations.test.d.ts.map +1 -0
  124. package/dist/services/chat-inline-annotations.test.js +1306 -0
  125. package/dist/services/chat-inline-annotations.test.js.map +1 -0
  126. package/dist/services/chat-queued-message-materialization.d.ts +126 -0
  127. package/dist/services/chat-queued-message-materialization.d.ts.map +1 -0
  128. package/dist/services/chat-queued-message-materialization.js +327 -0
  129. package/dist/services/chat-queued-message-materialization.js.map +1 -0
  130. package/dist/services/chat-steer-messages.d.ts +3 -3
  131. package/dist/services/chat-steer-messages.d.ts.map +1 -1
  132. package/dist/services/chat-steer-messages.js +50 -80
  133. package/dist/services/chat-steer-messages.js.map +1 -1
  134. package/dist/services/chat-work-manifest.d.ts.map +1 -1
  135. package/dist/services/chat-work-manifest.js +5 -1
  136. package/dist/services/chat-work-manifest.js.map +1 -1
  137. package/dist/services/chats.annotation-persistence.d.ts +20 -0
  138. package/dist/services/chats.annotation-persistence.d.ts.map +1 -0
  139. package/dist/services/chats.annotation-persistence.js +206 -0
  140. package/dist/services/chats.annotation-persistence.js.map +1 -0
  141. package/dist/services/chats.d.ts +129 -96
  142. package/dist/services/chats.d.ts.map +1 -1
  143. package/dist/services/chats.helpers.d.ts +2 -2
  144. package/dist/services/chats.inline-visual-persistence.d.ts +3 -3
  145. package/dist/services/chats.inline-visual-persistence.d.ts.map +1 -1
  146. package/dist/services/chats.inline-visual-persistence.js +114 -54
  147. package/dist/services/chats.inline-visual-persistence.js.map +1 -1
  148. package/dist/services/chats.js +743 -252
  149. package/dist/services/chats.js.map +1 -1
  150. package/dist/services/finance.d.ts +1 -1
  151. package/dist/services/index.d.ts +8 -0
  152. package/dist/services/index.d.ts.map +1 -1
  153. package/dist/services/index.js +8 -0
  154. package/dist/services/index.js.map +1 -1
  155. package/dist/services/integrations/agent-integrations.d.ts +2 -2
  156. package/dist/services/integrations/custom-integrations.d.ts +3 -1
  157. package/dist/services/integrations/custom-integrations.d.ts.map +1 -1
  158. package/dist/services/integrations/custom-integrations.js +13 -2
  159. package/dist/services/integrations/custom-integrations.js.map +1 -1
  160. package/dist/services/issues.comments-attachments.d.ts +7 -1
  161. package/dist/services/issues.comments-attachments.d.ts.map +1 -1
  162. package/dist/services/issues.comments-attachments.js +13 -1
  163. package/dist/services/issues.comments-attachments.js.map +1 -1
  164. package/dist/services/issues.d.ts +6 -0
  165. package/dist/services/issues.d.ts.map +1 -1
  166. package/dist/services/issues.js +22 -3
  167. package/dist/services/issues.js.map +1 -1
  168. package/dist/services/knowledge-portability/organization-portability.core.d.ts +4 -1
  169. package/dist/services/knowledge-portability/organization-portability.core.d.ts.map +1 -1
  170. package/dist/services/knowledge-portability/organization-portability.core.js +17 -3
  171. package/dist/services/knowledge-portability/organization-portability.core.js.map +1 -1
  172. package/dist/services/knowledge-portability/organization-portability.export.d.ts.map +1 -1
  173. package/dist/services/knowledge-portability/organization-portability.export.js +2 -2
  174. package/dist/services/knowledge-portability/organization-portability.export.js.map +1 -1
  175. package/dist/services/knowledge-portability/organization-portability.import.d.ts.map +1 -1
  176. package/dist/services/knowledge-portability/organization-portability.import.js +13 -3
  177. package/dist/services/knowledge-portability/organization-portability.import.js.map +1 -1
  178. package/dist/services/knowledge-portability/organization-skills.catalog.d.ts +3 -0
  179. package/dist/services/knowledge-portability/organization-skills.catalog.d.ts.map +1 -1
  180. package/dist/services/knowledge-portability/organization-skills.catalog.js +54 -23
  181. package/dist/services/knowledge-portability/organization-skills.catalog.js.map +1 -1
  182. package/dist/services/knowledge-portability/organization-skills.d.ts.map +1 -1
  183. package/dist/services/knowledge-portability/organization-skills.js +627 -124
  184. package/dist/services/knowledge-portability/organization-skills.js.map +1 -1
  185. package/dist/services/knowledge-portability/organization-skills.sources.d.ts +1 -0
  186. package/dist/services/knowledge-portability/organization-skills.sources.d.ts.map +1 -1
  187. package/dist/services/knowledge-portability/organization-skills.sources.js +53 -10
  188. package/dist/services/knowledge-portability/organization-skills.sources.js.map +1 -1
  189. package/dist/services/mcp/authorizer-lock.d.ts +9 -0
  190. package/dist/services/mcp/authorizer-lock.d.ts.map +1 -0
  191. package/dist/services/mcp/authorizer-lock.js +15 -0
  192. package/dist/services/mcp/authorizer-lock.js.map +1 -0
  193. package/dist/services/mcp/managed-bindings.d.ts +17 -0
  194. package/dist/services/mcp/managed-bindings.d.ts.map +1 -0
  195. package/dist/services/mcp/managed-bindings.js +332 -0
  196. package/dist/services/mcp/managed-bindings.js.map +1 -0
  197. package/dist/services/mcp/managed-client.d.ts +64 -0
  198. package/dist/services/mcp/managed-client.d.ts.map +1 -0
  199. package/dist/services/mcp/managed-client.js +238 -0
  200. package/dist/services/mcp/managed-client.js.map +1 -0
  201. package/dist/services/mcp/managed-client.test.d.ts +2 -0
  202. package/dist/services/mcp/managed-client.test.d.ts.map +1 -0
  203. package/dist/services/mcp/managed-client.test.js +398 -0
  204. package/dist/services/mcp/managed-client.test.js.map +1 -0
  205. package/dist/services/mcp/managed-connections.d.ts +81 -0
  206. package/dist/services/mcp/managed-connections.d.ts.map +1 -0
  207. package/dist/services/mcp/managed-connections.js +920 -0
  208. package/dist/services/mcp/managed-connections.js.map +1 -0
  209. package/dist/services/mcp/managed-runtime.d.ts +134 -0
  210. package/dist/services/mcp/managed-runtime.d.ts.map +1 -0
  211. package/dist/services/mcp/managed-runtime.js +282 -0
  212. package/dist/services/mcp/managed-runtime.js.map +1 -0
  213. package/dist/services/mcp/oauth-provider.d.ts +48 -0
  214. package/dist/services/mcp/oauth-provider.d.ts.map +1 -0
  215. package/dist/services/mcp/oauth-provider.js +120 -0
  216. package/dist/services/mcp/oauth-provider.js.map +1 -0
  217. package/dist/services/mcp/oauth-scope.test.d.ts +2 -0
  218. package/dist/services/mcp/oauth-scope.test.d.ts.map +1 -0
  219. package/dist/services/mcp/oauth-scope.test.js +69 -0
  220. package/dist/services/mcp/oauth-scope.test.js.map +1 -0
  221. package/dist/services/mcp/oauth-session-gc.d.ts +14 -0
  222. package/dist/services/mcp/oauth-session-gc.d.ts.map +1 -0
  223. package/dist/services/mcp/oauth-session-gc.js +34 -0
  224. package/dist/services/mcp/oauth-session-gc.js.map +1 -0
  225. package/dist/services/mcp/oauth-session-gc.test.d.ts +2 -0
  226. package/dist/services/mcp/oauth-session-gc.test.d.ts.map +1 -0
  227. package/dist/services/mcp/oauth-session-gc.test.js +66 -0
  228. package/dist/services/mcp/oauth-session-gc.test.js.map +1 -0
  229. package/dist/services/mcp/oauth.d.ts +61 -0
  230. package/dist/services/mcp/oauth.d.ts.map +1 -0
  231. package/dist/services/mcp/oauth.js +1690 -0
  232. package/dist/services/mcp/oauth.js.map +1 -0
  233. package/dist/services/mcp/pinned-fetch.d.ts +15 -0
  234. package/dist/services/mcp/pinned-fetch.d.ts.map +1 -0
  235. package/dist/services/mcp/pinned-fetch.js +400 -0
  236. package/dist/services/mcp/pinned-fetch.js.map +1 -0
  237. package/dist/services/mcp/pinned-fetch.test.d.ts +2 -0
  238. package/dist/services/mcp/pinned-fetch.test.d.ts.map +1 -0
  239. package/dist/services/mcp/pinned-fetch.test.js +190 -0
  240. package/dist/services/mcp/pinned-fetch.test.js.map +1 -0
  241. package/dist/services/mcp/provider-registry.d.ts +77 -0
  242. package/dist/services/mcp/provider-registry.d.ts.map +1 -0
  243. package/dist/services/mcp/provider-registry.js +80 -0
  244. package/dist/services/mcp/provider-registry.js.map +1 -0
  245. package/dist/services/mcp/provider-registry.test.d.ts +2 -0
  246. package/dist/services/mcp/provider-registry.test.d.ts.map +1 -0
  247. package/dist/services/mcp/provider-registry.test.js +80 -0
  248. package/dist/services/mcp/provider-registry.test.js.map +1 -0
  249. package/dist/services/mcp/security-policy.d.ts +48 -0
  250. package/dist/services/mcp/security-policy.d.ts.map +1 -0
  251. package/dist/services/mcp/security-policy.js +344 -0
  252. package/dist/services/mcp/security-policy.js.map +1 -0
  253. package/dist/services/mcp/security-policy.test.d.ts +2 -0
  254. package/dist/services/mcp/security-policy.test.d.ts.map +1 -0
  255. package/dist/services/mcp/security-policy.test.js +226 -0
  256. package/dist/services/mcp/security-policy.test.js.map +1 -0
  257. package/dist/services/mcp/tool-discovery.d.ts +49 -0
  258. package/dist/services/mcp/tool-discovery.d.ts.map +1 -0
  259. package/dist/services/mcp/tool-discovery.js +198 -0
  260. package/dist/services/mcp/tool-discovery.js.map +1 -0
  261. package/dist/services/mcp/tool-discovery.test.d.ts +2 -0
  262. package/dist/services/mcp/tool-discovery.test.d.ts.map +1 -0
  263. package/dist/services/mcp/tool-discovery.test.js +168 -0
  264. package/dist/services/mcp/tool-discovery.test.js.map +1 -0
  265. package/dist/services/messenger.d.ts +1 -1
  266. package/dist/services/messenger.d.ts.map +1 -1
  267. package/dist/services/messenger.js +21 -3
  268. package/dist/services/messenger.js.map +1 -1
  269. package/dist/services/plugin-registry.d.ts +3 -3
  270. package/dist/services/runtime-kernel/heartbeat.core.d.ts +1 -1
  271. package/dist/services/runtime-kernel/heartbeat.core.d.ts.map +1 -1
  272. package/dist/services/runtime-kernel/heartbeat.core.js +30 -4
  273. package/dist/services/runtime-kernel/heartbeat.core.js.map +1 -1
  274. package/dist/services/runtime-kernel/heartbeat.wakeup.d.ts.map +1 -1
  275. package/dist/services/runtime-kernel/heartbeat.wakeup.js +38 -23
  276. package/dist/services/runtime-kernel/heartbeat.wakeup.js.map +1 -1
  277. package/dist/services/secrets.d.ts +64 -6
  278. package/dist/services/secrets.d.ts.map +1 -1
  279. package/dist/services/secrets.js +38 -15
  280. package/dist/services/secrets.js.map +1 -1
  281. package/dist/services/side-chats.d.ts +1 -1
  282. package/dist/services/side-chats.d.ts.map +1 -1
  283. package/dist/services/side-chats.js +56 -14
  284. package/dist/services/side-chats.js.map +1 -1
  285. package/dist/services/workspace-runtime.services.d.ts +2 -2
  286. package/dist/services/workspace-web-preview.js +1 -1
  287. package/package.json +16 -13
  288. package/resources/bundled-skills/rudder-docs/references/operating-practices.md +12 -5
  289. package/skills/rudder-docs/references/operating-practices.md +12 -5
  290. package/ui-dist/assets/LibraryLiveSurface-CKOthw54.js +1 -0
  291. package/ui-dist/assets/{abnfDiagram-VRR7QNED-KGtP7zoC.js → abnfDiagram-VRR7QNED-C6a_wMho.js} +1 -1
  292. package/ui-dist/assets/{arc-JjnKyiOb.js → arc-CP0En6KA.js} +1 -1
  293. package/ui-dist/assets/architectureDiagram-ZJ3FMSHR-AHfOdcaZ.js +36 -0
  294. package/ui-dist/assets/{blockDiagram-677ZJIJ3-D7YzMYrz.js → blockDiagram-677ZJIJ3-Bkl9lp63.js} +1 -1
  295. package/ui-dist/assets/{c4Diagram-LMCZKHZV-Dpf7UQxl.js → c4Diagram-LMCZKHZV-BpZareVt.js} +1 -1
  296. package/ui-dist/assets/channel-DqxL_Zcy.js +1 -0
  297. package/ui-dist/assets/{chunk-2Q5K7J3B-UJ3gsGlQ.js → chunk-2Q5K7J3B-BQAwVuXc.js} +1 -1
  298. package/ui-dist/assets/{chunk-32BRIVSS-BeHl2j2l.js → chunk-32BRIVSS-YkmfA08F.js} +1 -1
  299. package/ui-dist/assets/{chunk-5VM5RSS4-STE9fJd0.js → chunk-5VM5RSS4-DvvjwTnG.js} +1 -1
  300. package/ui-dist/assets/{chunk-EX3LRPZG-Bj8g8j4B.js → chunk-EX3LRPZG-TXD_Yhg5.js} +1 -1
  301. package/ui-dist/assets/{chunk-JWPE2WC7-0V4Pwta-.js → chunk-JWPE2WC7-CgMlj6XI.js} +1 -1
  302. package/ui-dist/assets/{chunk-MOJQB5TN-DNPn50gm.js → chunk-MOJQB5TN-BnJjU8Rc.js} +1 -1
  303. package/ui-dist/assets/{chunk-RYQCIY6F-Befmnv8r.js → chunk-RYQCIY6F-D9B64JKM.js} +1 -1
  304. package/ui-dist/assets/{chunk-V7JOEXUC-Boh8TjHj.js → chunk-V7JOEXUC-PS09QVpl.js} +1 -1
  305. package/ui-dist/assets/{chunk-VR4S4FIN-B_yEQSo3.js → chunk-VR4S4FIN-DQXb7pRS.js} +1 -1
  306. package/ui-dist/assets/{chunk-XXDRQBXY-Cf1GnUFx.js → chunk-XXDRQBXY-B1UdLiF2.js} +1 -1
  307. package/ui-dist/assets/classDiagram-OUVF2IWQ-DMwjzuJE.js +1 -0
  308. package/ui-dist/assets/classDiagram-v2-EOCWNBFH-DMwjzuJE.js +1 -0
  309. package/ui-dist/assets/cose-bilkent-JH36ORCC-lqqmMB3m.js +1 -0
  310. package/ui-dist/assets/{cynefin-VYW2F7L2-Dv1yELYC.js → cynefin-VYW2F7L2-C9hu0XqZ.js} +1 -1
  311. package/ui-dist/assets/{cynefinDiagram-TSTJHNR4-CeFwjFoZ.js → cynefinDiagram-TSTJHNR4-Uuhz4c-1.js} +1 -1
  312. package/ui-dist/assets/{dagre-VKFMJZFB-8idd_4sX.js → dagre-VKFMJZFB-ChDrQYse.js} +1 -1
  313. package/ui-dist/assets/{diagram-FQU43EPY-BBVua6hM.js → diagram-FQU43EPY-DLtjkVSN.js} +1 -1
  314. package/ui-dist/assets/{diagram-G47NLZAW-D1zLQZlp.js → diagram-G47NLZAW-DCvEm4D0.js} +1 -1
  315. package/ui-dist/assets/{diagram-NH7WQ7WH-DE_FTSNv.js → diagram-NH7WQ7WH-Dz5jlsPG.js} +1 -1
  316. package/ui-dist/assets/{diagram-OA4YK3LP-61VSKBEn.js → diagram-OA4YK3LP-BXmQLO-Q.js} +1 -1
  317. package/ui-dist/assets/{diagram-WEI45ONY-C-tED6BJ.js → diagram-WEI45ONY-JnMU3xrx.js} +1 -1
  318. package/ui-dist/assets/{ebnfDiagram-CCIWWBDH-BEB8WGt0.js → ebnfDiagram-CCIWWBDH-Kryuqj4r.js} +1 -1
  319. package/ui-dist/assets/{erDiagram-Q63AITRT-AN_jm1TZ.js → erDiagram-Q63AITRT-Bn7g2mSW.js} +1 -1
  320. package/ui-dist/assets/{flowDiagram-23GEKE2U-BwLC6tI7.js → flowDiagram-23GEKE2U-DcjqTK91.js} +4 -4
  321. package/ui-dist/assets/ganttDiagram-NO4QXBWP-BRkw9-GE.js +292 -0
  322. package/ui-dist/assets/{gitGraphDiagram-IHSO6WYX-D9HCL9rY.js → gitGraphDiagram-IHSO6WYX-Cexcp6kR.js} +1 -1
  323. package/ui-dist/assets/graph-Cu7OV4Oi.js +1 -0
  324. package/ui-dist/assets/{index-BQXnpwke.js → index-ASZMPBYm.js} +5 -5
  325. package/ui-dist/assets/{index-5OM32_rf.js → index-B17BqCTj.js} +1 -1
  326. package/ui-dist/assets/{index-Cf0gLy6a.js → index-B9MccU1g.js} +1 -1
  327. package/ui-dist/assets/{index-BoSJ4Rx1.js → index-BPqbtW_X.js} +1 -1
  328. package/ui-dist/assets/{index-CpIdZ4-7.js → index-C2HjDa98.js} +1 -1
  329. package/ui-dist/assets/index-CMPtpj0A.js +1 -0
  330. package/ui-dist/assets/{index-p0ZGU1_7.js → index-CZXgOYtk.js} +1 -1
  331. package/ui-dist/assets/{index-74cx3ESJ.js → index-CknAauOP.js} +1 -1
  332. package/ui-dist/assets/index-Cu1GuH0a.js +1 -0
  333. package/ui-dist/assets/index-D8PdEImm.css +1 -0
  334. package/ui-dist/assets/{index-DrVDiJhe.js → index-DB1YX9-p.js} +1 -1
  335. package/ui-dist/assets/{index-vHMnAQSb.js → index-DBxLZXK7.js} +624 -610
  336. package/ui-dist/assets/{index-CpEfk5zb.js → index-DOCVOD97.js} +1 -1
  337. package/ui-dist/assets/{index-DMuWG0YN.js → index-DUbakRAC.js} +1 -1
  338. package/ui-dist/assets/{index-AT8juaIi.js → index-Dbg1ZwO2.js} +1 -1
  339. package/ui-dist/assets/index-DwbLsoLt.js +1 -0
  340. package/ui-dist/assets/index-hCLSotmS.js +1 -0
  341. package/ui-dist/assets/index-jrhEFc-j.js +1 -0
  342. package/ui-dist/assets/index-kz8ueXgo.js +1 -0
  343. package/ui-dist/assets/{infoDiagram-FWYZ7A6U-CyO3CAA1.js → infoDiagram-FWYZ7A6U-DugVGI3K.js} +1 -1
  344. package/ui-dist/assets/{ishikawaDiagram-FXEZZL3T-BLLZuF1_.js → ishikawaDiagram-FXEZZL3T-CHy06Oev.js} +1 -1
  345. package/ui-dist/assets/{journeyDiagram-5HDEW3XC-CWzQocvE.js → journeyDiagram-5HDEW3XC-BI0w53rb.js} +1 -1
  346. package/ui-dist/assets/{kanban-definition-HUTT4EX6-Dz4SFU-I.js → kanban-definition-HUTT4EX6-v_bLwx7B.js} +1 -1
  347. package/ui-dist/assets/layout-Dwp1s_bo.js +1 -0
  348. package/ui-dist/assets/{linear-BlzDlAaL.js → linear-DAV4STLZ.js} +1 -1
  349. package/ui-dist/assets/map-Bs6QpaaQ.js +1 -0
  350. package/ui-dist/assets/{mermaid.core-BtCydd-w.js → mermaid.core-fVmaL47V.js} +4 -4
  351. package/ui-dist/assets/{mindmap-definition-LN4V7U3C-BeIkKRBx.js → mindmap-definition-LN4V7U3C-5dWD4dxm.js} +1 -1
  352. package/ui-dist/assets/{pegDiagram-2B236MQR-BZgpT4TN.js → pegDiagram-2B236MQR-DB2XsDPN.js} +1 -1
  353. package/ui-dist/assets/{pieDiagram-ENE6RG2P-BRFggcg2.js → pieDiagram-ENE6RG2P-Bc5teLCS.js} +1 -1
  354. package/ui-dist/assets/{quadrantDiagram-ABIIQ3AL-CibUo3gT.js → quadrantDiagram-ABIIQ3AL-BlfNdETt.js} +1 -1
  355. package/ui-dist/assets/{railroadDiagram-RFXS5EU6-DINJqhgn.js → railroadDiagram-RFXS5EU6-BbXywkq3.js} +1 -1
  356. package/ui-dist/assets/{requirementDiagram-TGXJPOKE-NegluQIe.js → requirementDiagram-TGXJPOKE-DU-CapdF.js} +1 -1
  357. package/ui-dist/assets/{sankeyDiagram-HTMAVEWB-Kq41yHAd.js → sankeyDiagram-HTMAVEWB-Ftvh3MqA.js} +1 -1
  358. package/ui-dist/assets/{sequenceDiagram-DBY2YBRQ-CngfEI4f.js → sequenceDiagram-DBY2YBRQ-CCtHt9V4.js} +1 -1
  359. package/ui-dist/assets/{sizeCapture-X5ZJPWSS-DUWRNlme.js → sizeCapture-X5ZJPWSS-x0jnIKHx.js} +1 -1
  360. package/ui-dist/assets/{stateDiagram-2N3HPSRC-BwHC_Fz4.js → stateDiagram-2N3HPSRC-2qCrydE7.js} +1 -1
  361. package/ui-dist/assets/stateDiagram-v2-6OUMAXLB-CvGRUgRf.js +1 -0
  362. package/ui-dist/assets/{swimlanes-5IMT3BWC-Cqp2rT1K.js → swimlanes-5IMT3BWC-6kqJq5Xf.js} +2 -2
  363. package/ui-dist/assets/swimlanesDiagram-G3AALYLV-EBa7-qSc.js +8 -0
  364. package/ui-dist/assets/{timeline-definition-FHXFAJF6-BG3GYPCu.js → timeline-definition-FHXFAJF6-BuRz8KHZ.js} +1 -1
  365. package/ui-dist/assets/{vennDiagram-L72KCM5P-D1IFU27N.js → vennDiagram-L72KCM5P-BKzMZ_Rv.js} +1 -1
  366. package/ui-dist/assets/{wardleyDiagram-EHGQE667-DboO2kYu.js → wardleyDiagram-EHGQE667-8uXlFtBV.js} +1 -1
  367. package/ui-dist/assets/{xychartDiagram-FW5EYKEG-vI2BGrXP.js → xychartDiagram-FW5EYKEG-CWKGlpF9.js} +1 -1
  368. package/ui-dist/index.html +2 -2
  369. package/ui-dist/assets/architectureDiagram-ZJ3FMSHR-DHyfFgK0.js +0 -36
  370. package/ui-dist/assets/channel-TMGI9Qt9.js +0 -1
  371. package/ui-dist/assets/classDiagram-OUVF2IWQ-r5zIpY6G.js +0 -1
  372. package/ui-dist/assets/classDiagram-v2-EOCWNBFH-r5zIpY6G.js +0 -1
  373. package/ui-dist/assets/cose-bilkent-JH36ORCC-fSNs9447.js +0 -1
  374. package/ui-dist/assets/ganttDiagram-NO4QXBWP-CJYhBF1C.js +0 -292
  375. package/ui-dist/assets/graph-DdBT9W3J.js +0 -1
  376. package/ui-dist/assets/index-6UIO-gg7.js +0 -1
  377. package/ui-dist/assets/index-BVkQVMFn.js +0 -1
  378. package/ui-dist/assets/index-BaAPxkqh.css +0 -1
  379. package/ui-dist/assets/index-CmCERTmS.js +0 -1
  380. package/ui-dist/assets/index-Cr4lUIaJ.js +0 -1
  381. package/ui-dist/assets/index-D0fAqlES.js +0 -1
  382. package/ui-dist/assets/index-DfNcAyZq.js +0 -1
  383. package/ui-dist/assets/layout-D3tY9q4Q.js +0 -1
  384. package/ui-dist/assets/map-Ctg1-a9N.js +0 -1
  385. package/ui-dist/assets/stateDiagram-v2-6OUMAXLB-C6P3NY96.js +0 -1
  386. package/ui-dist/assets/swimlanesDiagram-G3AALYLV-BNdDt62J.js +0 -8
@@ -0,0 +1,920 @@
1
+ import { activityLog, customIntegrationTools, mcpConnections, mcpOAuthGrants, organizationSecrets, organizationSecretVersions, } from "@rudderhq/db";
2
+ import { createMcpConnectionSchema, MCP_PROVIDER_CATALOG, mcpConnectionMergedConfigSchema, mcpConnectionMutationConfigSchema, updateMcpConnectionSchema, } from "@rudderhq/shared";
3
+ import { and, asc, eq, sql } from "drizzle-orm";
4
+ import { randomUUID } from "node:crypto";
5
+ import { conflict, HttpError, notFound, unprocessable } from "../../errors.js";
6
+ import { getSecretProvider } from "../../secrets/provider-registry.js";
7
+ import { secretService } from "../secrets.js";
8
+ import { createManagedMcpClient, resolveMcpHttpCredentials, } from "./managed-client.js";
9
+ import { MCP_PROVIDER_REGISTRY, resolveCuratedMcpEndpoint, } from "./provider-registry.js";
10
+ import { assertSafeMcpCredentialHeaders, assertSafeMcpHeaders, resolveMcpHttpTarget, validateMcpStdioPolicy, } from "./security-policy.js";
11
+ import { normalizeMcpDiscoveredTools, reconcileMcpToolCatalog, } from "./tool-discovery.js";
12
+ const EMPTY_ALLOWLISTS = {
13
+ httpOrigins: [],
14
+ stdioCommands: [],
15
+ stdioWorkingDirectories: [],
16
+ stdioEnvironmentNames: [],
17
+ };
18
+ const SENSITIVE_STATIC_NAME_RE = /(api[-_]?key|client[-_]?key|access[-_]?token|auth(?:[-_]?token)?|authorization|bearer|secret|passwd|password|credential|cookie|jwt|private[-_]?key|connectionstring|(?:^|[-_])(?:token|key)(?:$|[-_]))/iu;
19
+ const RECONNECT_REQUIRED_STATUSES = new Set([
20
+ "disabled",
21
+ "revoked",
22
+ "needs_reauth",
23
+ "error",
24
+ ]);
25
+ export class ManagedMcpConnectionPolicyError extends HttpError {
26
+ code = "managed_mcp_policy_rejected";
27
+ constructor(message = "Managed MCP connection policy rejected the configuration") {
28
+ super(422, message);
29
+ this.name = "ManagedMcpConnectionPolicyError";
30
+ }
31
+ }
32
+ export class ManagedMcpDiscoveryStaleError extends HttpError {
33
+ code = "managed_mcp_discovery_stale";
34
+ constructor() {
35
+ super(409, "Managed MCP connection changed while tools were being discovered");
36
+ this.name = "ManagedMcpDiscoveryStaleError";
37
+ }
38
+ }
39
+ function discoverySnapshot(row) {
40
+ return {
41
+ enabled: row.enabled,
42
+ lastDiscoveredAt: row.lastDiscoveredAt?.getTime() ?? null,
43
+ lifecycleRevision: row.lifecycleRevision,
44
+ status: row.status,
45
+ updatedAt: row.updatedAt.getTime(),
46
+ };
47
+ }
48
+ function nextConnectionMutationTime(row) {
49
+ return new Date(Math.max(Date.now(), row.updatedAt.getTime() + 1));
50
+ }
51
+ function assertDiscoverySnapshot(row, snapshot) {
52
+ if (row.enabled !== snapshot.enabled
53
+ || row.lifecycleRevision !== snapshot.lifecycleRevision
54
+ || row.status !== snapshot.status
55
+ || row.updatedAt.getTime() !== snapshot.updatedAt
56
+ || (row.lastDiscoveredAt?.getTime() ?? null) !== snapshot.lastDiscoveredAt) {
57
+ throw new ManagedMcpDiscoveryStaleError();
58
+ }
59
+ }
60
+ function managedMcpActivityValues(input) {
61
+ const actorType = input.actor.agentId
62
+ ? "agent"
63
+ : input.actor.userId
64
+ ? "user"
65
+ : "system";
66
+ const actorId = input.actor.agentId ?? input.actor.userId ?? "system";
67
+ return {
68
+ orgId: input.orgId,
69
+ actorType,
70
+ actorId,
71
+ action: input.action,
72
+ entityType: "mcp_connection",
73
+ entityId: input.connectionId,
74
+ agentId: input.actor.agentId ?? null,
75
+ details: input.details,
76
+ };
77
+ }
78
+ function isRecord(value) {
79
+ return Boolean(value) && typeof value === "object" && !Array.isArray(value);
80
+ }
81
+ function asStdioConfig(config) {
82
+ return config;
83
+ }
84
+ function asHttpConfig(config) {
85
+ return config;
86
+ }
87
+ function discoveryFilter(row) {
88
+ if (row.provider !== "custom")
89
+ return {};
90
+ const config = row.transport === "stdio"
91
+ ? asStdioConfig(row.safeConfig)
92
+ : asHttpConfig(row.safeConfig);
93
+ return {
94
+ toolAllowlist: config.toolAllowlist,
95
+ toolDenylist: config.toolDenylist,
96
+ };
97
+ }
98
+ function declaredSecretShape(transport, safeConfig) {
99
+ if (transport === "stdio") {
100
+ const config = asStdioConfig(safeConfig);
101
+ return {
102
+ env: [...(config.secretEnvNames ?? [])].sort(),
103
+ headers: [],
104
+ bearerToken: false,
105
+ };
106
+ }
107
+ if (transport === "streamable_http") {
108
+ const config = asHttpConfig(safeConfig);
109
+ return {
110
+ env: [],
111
+ headers: [...(config.secretHeaderNames ?? [])]
112
+ .map((name) => name.toLowerCase())
113
+ .sort(),
114
+ bearerToken: config.hasBearerToken === true,
115
+ };
116
+ }
117
+ return { env: [], headers: [], bearerToken: false };
118
+ }
119
+ function equalSecretShape(left, right) {
120
+ return JSON.stringify(left) === JSON.stringify(right);
121
+ }
122
+ function hasDeclaredSecrets(shape) {
123
+ return shape.env.length > 0 || shape.headers.length > 0 || shape.bearerToken;
124
+ }
125
+ function assertNoSensitiveStaticNames(values, kind) {
126
+ const sensitiveName = Object.keys(values ?? {}).find((name) => (SENSITIVE_STATIC_NAME_RE.test(name)));
127
+ if (sensitiveName) {
128
+ throw new ManagedMcpConnectionPolicyError(`Managed MCP static ${kind} names that look sensitive must use encrypted credentials`);
129
+ }
130
+ }
131
+ function assertCustomHttpHeaderPolicy(config, credentials) {
132
+ try {
133
+ assertSafeMcpHeaders(config.staticHeaders ?? {});
134
+ assertSafeMcpCredentialHeaders(Object.fromEntries(Object.keys(config.headersFromEnv ?? {}).map((name) => [name, "environment-reference"])));
135
+ assertSafeMcpCredentialHeaders(Object.fromEntries((config.secretHeaderNames ?? []).map((name) => [name, "encrypted-reference"])));
136
+ if (credentials?.headers) {
137
+ assertSafeMcpCredentialHeaders(credentials.headers);
138
+ }
139
+ }
140
+ catch {
141
+ throw new ManagedMcpConnectionPolicyError("Managed MCP header configuration is rejected by deployment policy");
142
+ }
143
+ assertNoSensitiveStaticNames(config.staticHeaders, "header");
144
+ }
145
+ function reconnectRequiredError() {
146
+ return unprocessable("Reconnect the managed MCP connection before enabling or discovering tools");
147
+ }
148
+ function discoveryNotReadyError() {
149
+ return unprocessable("Managed MCP connection is not ready for tool discovery; reconnect or complete authorization first");
150
+ }
151
+ function canDiscoverTools(row) {
152
+ if (!row.enabled)
153
+ return false;
154
+ if (row.provider === "custom") {
155
+ return row.status === "draft" || row.status === "active";
156
+ }
157
+ return row.status === "active";
158
+ }
159
+ function publicSummary(row) {
160
+ return {
161
+ id: row.id,
162
+ orgId: row.orgId,
163
+ name: row.name,
164
+ displayName: row.displayName,
165
+ provider: row.provider,
166
+ transport: row.transport,
167
+ externalScope: row.externalScope,
168
+ accessMode: row.accessMode,
169
+ status: row.status,
170
+ safeConfig: row.safeConfig,
171
+ startupTimeoutMs: row.startupTimeoutMs,
172
+ toolTimeoutMs: row.toolTimeoutMs,
173
+ enabled: row.enabled,
174
+ required: row.required,
175
+ hasCredentials: Boolean(row.credentialSecretId),
176
+ lastDiscoveredAt: row.lastDiscoveredAt,
177
+ activatedAt: row.activatedAt,
178
+ disabledAt: row.disabledAt,
179
+ revokedAt: row.revokedAt,
180
+ createdAt: row.createdAt,
181
+ updatedAt: row.updatedAt,
182
+ };
183
+ }
184
+ function publicTool(row) {
185
+ if (!row.connectionId) {
186
+ throw new Error("Managed MCP tool is missing its connection");
187
+ }
188
+ return {
189
+ id: row.id,
190
+ connectionId: row.connectionId,
191
+ externalToolName: row.externalToolName,
192
+ rudderToolName: row.rudderToolName,
193
+ description: row.description,
194
+ inputSchema: row.inputSchema,
195
+ outputSchema: row.outputSchema,
196
+ enabled: row.enabled,
197
+ removedAt: row.removedAt,
198
+ };
199
+ }
200
+ function parseCredentialPayload(value) {
201
+ try {
202
+ const parsed = JSON.parse(value);
203
+ if (!isRecord(parsed))
204
+ throw new Error("invalid");
205
+ return {
206
+ env: isRecord(parsed.env)
207
+ ? Object.fromEntries(Object.entries(parsed.env).filter((entry) => (typeof entry[1] === "string")))
208
+ : undefined,
209
+ headers: isRecord(parsed.headers)
210
+ ? Object.fromEntries(Object.entries(parsed.headers).filter((entry) => (typeof entry[1] === "string")))
211
+ : undefined,
212
+ bearerToken: typeof parsed.bearerToken === "string" ? parsed.bearerToken : undefined,
213
+ };
214
+ }
215
+ catch {
216
+ throw unprocessable("Managed MCP credential material is invalid");
217
+ }
218
+ }
219
+ function customSecretPayload(input) {
220
+ return {
221
+ ...(input.env ? { env: input.env } : {}),
222
+ ...(input.headers ? { headers: input.headers } : {}),
223
+ ...(input.bearerToken ? { bearerToken: input.bearerToken } : {}),
224
+ };
225
+ }
226
+ function assertLegacyMutable(row) {
227
+ if (row.transport === "legacy_manual") {
228
+ throw unprocessable("Legacy manual MCP definitions are read-only; create and reconnect a new managed connection");
229
+ }
230
+ }
231
+ function redactedDiscoveryError() {
232
+ return unprocessable("Managed MCP tool discovery failed");
233
+ }
234
+ export function managedMcpConnectionService(db, options) {
235
+ const secrets = secretService(db);
236
+ const createClient = options.createClient ?? createManagedMcpClient;
237
+ const hostEnv = options.hostEnv ?? process.env;
238
+ const allowlists = options.allowlists ?? EMPTY_ALLOWLISTS;
239
+ async function findRow(orgId, connectionId) {
240
+ const row = await db
241
+ .select()
242
+ .from(mcpConnections)
243
+ .where(and(eq(mcpConnections.orgId, orgId), eq(mcpConnections.id, connectionId)))
244
+ .then((rows) => rows[0] ?? null);
245
+ if (!row)
246
+ throw notFound("MCP connection not found");
247
+ return row;
248
+ }
249
+ function assertHttpEnvironmentPolicy(config) {
250
+ if (options.deploymentMode !== "authenticated")
251
+ return;
252
+ const allowed = new Set(allowlists.stdioEnvironmentNames);
253
+ const requested = [
254
+ ...Object.values(config.headersFromEnv ?? {}),
255
+ ...(config.bearerTokenEnvVar ? [config.bearerTokenEnvVar] : []),
256
+ ];
257
+ if (requested.some((name) => !allowed.has(name))) {
258
+ throw unprocessable("Managed MCP HTTP environment name is not allowed by deployment policy");
259
+ }
260
+ }
261
+ async function validateBoundary(input) {
262
+ try {
263
+ if (input.transport === "legacy_manual")
264
+ return;
265
+ if (input.transport === "stdio") {
266
+ const config = asStdioConfig(input.safeConfig);
267
+ assertNoSensitiveStaticNames(config.staticEnv, "environment variable");
268
+ await validateMcpStdioPolicy({
269
+ command: config.command,
270
+ args: config.args,
271
+ cwd: config.cwd,
272
+ environmentNames: [
273
+ ...Object.keys(config.staticEnv ?? {}),
274
+ ...(config.forwardedEnv ?? []),
275
+ ...(config.secretEnvNames ?? []),
276
+ ],
277
+ }, {
278
+ deploymentMode: options.deploymentMode,
279
+ stdioCommands: allowlists.stdioCommands,
280
+ stdioWorkingDirectories: allowlists.stdioWorkingDirectories,
281
+ stdioEnvironmentNames: allowlists.stdioEnvironmentNames,
282
+ });
283
+ return;
284
+ }
285
+ let url;
286
+ let curatedOrigin;
287
+ if (input.provider === "custom") {
288
+ const config = asHttpConfig(input.safeConfig);
289
+ if (!config.url)
290
+ throw unprocessable("Custom Streamable HTTP connection requires a URL");
291
+ assertCustomHttpHeaderPolicy(config, input.credentials);
292
+ assertHttpEnvironmentPolicy(config);
293
+ url = config.url;
294
+ }
295
+ else {
296
+ // Supabase is allowed to remain draft before project selection.
297
+ if (input.provider === "supabase" && !input.externalScope) {
298
+ return;
299
+ }
300
+ const endpoint = resolveCuratedMcpEndpoint({
301
+ provider: input.provider,
302
+ accessMode: input.accessMode,
303
+ externalScope: input.externalScope,
304
+ });
305
+ url = endpoint.href;
306
+ curatedOrigin = new URL(MCP_PROVIDER_REGISTRY[input.provider].endpoint).origin;
307
+ }
308
+ await resolveMcpHttpTarget(url, {
309
+ allowedOrigins: allowlists.httpOrigins,
310
+ curatedOrigin,
311
+ lookup: options.dnsLookup,
312
+ });
313
+ }
314
+ catch (error) {
315
+ if (error instanceof HttpError) {
316
+ throw error;
317
+ }
318
+ throw new ManagedMcpConnectionPolicyError();
319
+ }
320
+ }
321
+ async function prepareCredentialReplacement(connectionName, value) {
322
+ const id = randomUUID();
323
+ const prepared = await getSecretProvider("local_encrypted").createVersion({
324
+ value: JSON.stringify(customSecretPayload(value)),
325
+ externalRef: null,
326
+ });
327
+ return {
328
+ id,
329
+ name: `Managed MCP credentials - ${connectionName} - ${id}`,
330
+ externalRef: prepared.externalRef,
331
+ material: prepared.material,
332
+ valueSha256: prepared.valueSha256,
333
+ };
334
+ }
335
+ async function resolveCredentialPayload(row) {
336
+ if (!row.credentialSecretId)
337
+ return {};
338
+ return parseCredentialPayload(await secrets.resolveSecretValue(row.orgId, row.credentialSecretId, "latest"));
339
+ }
340
+ async function buildClientOptions(row) {
341
+ assertLegacyMutable(row);
342
+ await validateBoundary({
343
+ provider: row.provider,
344
+ transport: row.transport,
345
+ accessMode: row.accessMode,
346
+ externalScope: row.externalScope,
347
+ safeConfig: row.safeConfig,
348
+ });
349
+ if (row.transport === "stdio") {
350
+ const config = asStdioConfig(row.safeConfig);
351
+ const credential = await resolveCredentialPayload(row);
352
+ return {
353
+ transport: "stdio",
354
+ command: config.command,
355
+ args: config.args,
356
+ cwd: config.cwd,
357
+ staticEnv: config.staticEnv ?? {},
358
+ forwardedEnv: config.forwardedEnv ?? [],
359
+ secretEnv: credential.env ?? {},
360
+ hostEnv,
361
+ deploymentPolicy: {
362
+ deploymentMode: options.deploymentMode,
363
+ stdioCommands: allowlists.stdioCommands,
364
+ stdioWorkingDirectories: allowlists.stdioWorkingDirectories,
365
+ stdioEnvironmentNames: allowlists.stdioEnvironmentNames,
366
+ },
367
+ startupTimeoutMs: row.startupTimeoutMs,
368
+ toolTimeoutMs: row.toolTimeoutMs,
369
+ };
370
+ }
371
+ let url;
372
+ let curatedOrigin;
373
+ let credential = {};
374
+ let oauthCredential;
375
+ if (row.provider === "custom") {
376
+ const config = asHttpConfig(row.safeConfig);
377
+ if (!config.url)
378
+ throw unprocessable("Custom Streamable HTTP connection requires a URL");
379
+ url = config.url;
380
+ credential = await resolveCredentialPayload(row);
381
+ for (const [headerName, environmentName] of Object.entries(config.headersFromEnv ?? {})) {
382
+ const value = hostEnv[environmentName];
383
+ if (value !== undefined) {
384
+ credential.headers = { ...(credential.headers ?? {}), [headerName]: value };
385
+ }
386
+ }
387
+ if (config.bearerTokenEnvVar) {
388
+ credential.bearerToken = hostEnv[config.bearerTokenEnvVar];
389
+ }
390
+ assertCustomHttpHeaderPolicy(config, credential);
391
+ }
392
+ else {
393
+ const endpoint = resolveCuratedMcpEndpoint({
394
+ provider: row.provider,
395
+ accessMode: row.accessMode,
396
+ externalScope: row.externalScope,
397
+ });
398
+ url = endpoint.href;
399
+ curatedOrigin = new URL(MCP_PROVIDER_REGISTRY[row.provider].endpoint).origin;
400
+ const grant = await db
401
+ .select()
402
+ .from(mcpOAuthGrants)
403
+ .where(and(eq(mcpOAuthGrants.orgId, row.orgId), eq(mcpOAuthGrants.connectionId, row.id), eq(mcpOAuthGrants.status, "active")))
404
+ .then((rows) => rows[0] ?? null);
405
+ if (!grant?.credentialSecretId) {
406
+ throw unprocessable("Managed MCP OAuth authorization is required");
407
+ }
408
+ if (!options.createOAuthCredential) {
409
+ throw unprocessable("Managed MCP OAuth credential factory is not configured");
410
+ }
411
+ oauthCredential = options.createOAuthCredential(row.orgId, row.id);
412
+ }
413
+ const config = asHttpConfig(row.safeConfig);
414
+ return {
415
+ transport: "streamable_http",
416
+ url,
417
+ staticHeaders: row.provider === "custom" ? config.staticHeaders ?? {} : {},
418
+ credentials: resolveMcpHttpCredentials({
419
+ bearerToken: credential.bearerToken,
420
+ secretHeaders: credential.headers,
421
+ oauth: oauthCredential,
422
+ }),
423
+ network: {
424
+ allowedOrigins: allowlists.httpOrigins,
425
+ curatedOrigin,
426
+ lookup: options.dnsLookup,
427
+ },
428
+ startupTimeoutMs: row.startupTimeoutMs,
429
+ toolTimeoutMs: row.toolTimeoutMs,
430
+ };
431
+ }
432
+ async function listTools(orgId, connectionId) {
433
+ await findRow(orgId, connectionId);
434
+ return db
435
+ .select()
436
+ .from(customIntegrationTools)
437
+ .where(and(eq(customIntegrationTools.orgId, orgId), eq(customIntegrationTools.connectionId, connectionId)))
438
+ .orderBy(asc(customIntegrationTools.externalToolName))
439
+ .then((rows) => rows.map(publicTool));
440
+ }
441
+ return {
442
+ catalog: () => MCP_PROVIDER_CATALOG.map((entry) => ({
443
+ ...entry,
444
+ transports: [...entry.transports],
445
+ accessModes: [...entry.accessModes],
446
+ })),
447
+ list: (orgId) => db
448
+ .select()
449
+ .from(mcpConnections)
450
+ .where(eq(mcpConnections.orgId, orgId))
451
+ .orderBy(asc(mcpConnections.displayName))
452
+ .then((rows) => rows.map(publicSummary)),
453
+ get: async (orgId, connectionId) => publicSummary(await findRow(orgId, connectionId)),
454
+ openRuntimeClient: async (orgId, connectionId) => {
455
+ const connection = await findRow(orgId, connectionId);
456
+ if (connection.status !== "active"
457
+ || !connection.enabled
458
+ || connection.transport === "legacy_manual") {
459
+ throw unprocessable("Managed MCP connection is unavailable");
460
+ }
461
+ return createClient(await buildClientOptions(connection));
462
+ },
463
+ create: async (orgId, rawInput, actor = {}) => {
464
+ const input = createMcpConnectionSchema.parse(rawInput);
465
+ if (input.transport === "legacy_manual") {
466
+ throw unprocessable("Legacy manual MCP definitions cannot be created as managed connections");
467
+ }
468
+ await validateBoundary({
469
+ provider: input.provider,
470
+ transport: input.transport,
471
+ accessMode: input.accessMode,
472
+ externalScope: input.externalScope ?? null,
473
+ safeConfig: input.safeConfig,
474
+ credentials: input.secrets ? customSecretPayload(input.secrets) : undefined,
475
+ });
476
+ const credential = input.secrets
477
+ ? await prepareCredentialReplacement(input.name, input.secrets)
478
+ : null;
479
+ try {
480
+ const row = await db.transaction(async (tx) => {
481
+ if (credential) {
482
+ await tx.insert(organizationSecrets).values({
483
+ id: credential.id,
484
+ orgId,
485
+ name: credential.name,
486
+ provider: "local_encrypted",
487
+ purpose: "managed_mcp_connection",
488
+ externalRef: credential.externalRef,
489
+ latestVersion: 1,
490
+ description: "Encrypted managed MCP credentials",
491
+ createdByAgentId: actor.agentId ?? null,
492
+ createdByUserId: actor.userId ?? null,
493
+ });
494
+ await tx.insert(organizationSecretVersions).values({
495
+ secretId: credential.id,
496
+ version: 1,
497
+ material: credential.material,
498
+ valueSha256: credential.valueSha256,
499
+ createdByAgentId: actor.agentId ?? null,
500
+ createdByUserId: actor.userId ?? null,
501
+ });
502
+ }
503
+ const created = await tx.insert(mcpConnections).values({
504
+ orgId,
505
+ credentialSecretId: credential?.id ?? null,
506
+ name: input.name,
507
+ displayName: input.displayName,
508
+ provider: input.provider,
509
+ transport: input.transport,
510
+ externalScope: input.externalScope ?? null,
511
+ accessMode: input.accessMode,
512
+ status: "draft",
513
+ safeConfig: input.safeConfig,
514
+ startupTimeoutMs: input.startupTimeoutMs,
515
+ toolTimeoutMs: input.toolTimeoutMs,
516
+ enabled: input.enabled,
517
+ required: input.required,
518
+ })
519
+ .returning()
520
+ .then((rows) => rows[0]);
521
+ await tx.insert(activityLog).values(managedMcpActivityValues({
522
+ orgId,
523
+ connectionId: created.id,
524
+ action: "mcp_connection.created",
525
+ actor,
526
+ details: {
527
+ provider: created.provider,
528
+ transport: created.transport,
529
+ status: created.status,
530
+ },
531
+ }));
532
+ return created;
533
+ });
534
+ return publicSummary(row);
535
+ }
536
+ catch (error) {
537
+ if (error instanceof Error && /unique|duplicate/iu.test(error.message)) {
538
+ throw conflict("MCP connection name or provider scope already exists");
539
+ }
540
+ throw error;
541
+ }
542
+ },
543
+ update: async (orgId, connectionId, rawPatch, actor = {}, control = {}) => {
544
+ const existing = await findRow(orgId, connectionId);
545
+ assertLegacyMutable(existing);
546
+ const patch = updateMcpConnectionSchema.parse(rawPatch);
547
+ if (patch.enabled === true
548
+ && RECONNECT_REQUIRED_STATUSES.has(existing.status)) {
549
+ throw reconnectRequiredError();
550
+ }
551
+ const merged = {
552
+ provider: existing.provider,
553
+ transport: existing.transport,
554
+ accessMode: patch.accessMode ?? existing.accessMode,
555
+ safeConfig: patch.safeConfig ?? existing.safeConfig,
556
+ enabled: patch.enabled ?? existing.enabled,
557
+ };
558
+ mcpConnectionMergedConfigSchema.parse(merged);
559
+ if (patch.accessMode !== undefined
560
+ && existing.provider !== "custom"
561
+ && !control.allowCuratedAccessMode) {
562
+ throw unprocessable("Curated MCP access mode must be changed through the dedicated access-mode operation");
563
+ }
564
+ if (existing.provider === "linear"
565
+ && patch.accessMode !== undefined
566
+ && patch.accessMode !== existing.accessMode
567
+ && (existing.status === "active" || existing.status === "authorizing")) {
568
+ throw unprocessable("Linear access-mode changes require reauthorization: disconnect, select the new access mode, then reconnect OAuth");
569
+ }
570
+ const previousShape = declaredSecretShape(existing.transport, existing.safeConfig);
571
+ const nextShape = declaredSecretShape(existing.transport, merged.safeConfig);
572
+ const declarationChanged = !equalSecretShape(previousShape, nextShape);
573
+ if (patch.secrets || declarationChanged) {
574
+ if (hasDeclaredSecrets(nextShape) && !patch.secrets) {
575
+ throw unprocessable("Changed managed MCP secret declarations require exact replacement values");
576
+ }
577
+ mcpConnectionMutationConfigSchema.parse({
578
+ ...merged,
579
+ ...(patch.secrets ? { secrets: patch.secrets } : {}),
580
+ });
581
+ }
582
+ await validateBoundary({
583
+ ...merged,
584
+ externalScope: patch.externalScope === undefined
585
+ ? existing.externalScope
586
+ : patch.externalScope ?? null,
587
+ credentials: patch.secrets ? customSecretPayload(patch.secrets) : undefined,
588
+ });
589
+ let credentialSecretId = existing.credentialSecretId;
590
+ let oldSecretIdToDelete = null;
591
+ const replacement = patch.secrets
592
+ ? await prepareCredentialReplacement(existing.name, patch.secrets)
593
+ : null;
594
+ if (replacement) {
595
+ oldSecretIdToDelete = credentialSecretId;
596
+ credentialSecretId = replacement.id;
597
+ }
598
+ else if (declarationChanged && !hasDeclaredSecrets(nextShape) && credentialSecretId) {
599
+ oldSecretIdToDelete = credentialSecretId;
600
+ credentialSecretId = null;
601
+ }
602
+ const row = await db.transaction(async (tx) => {
603
+ const locked = await tx
604
+ .select()
605
+ .from(mcpConnections)
606
+ .where(and(eq(mcpConnections.orgId, orgId), eq(mcpConnections.id, connectionId)))
607
+ .for("update")
608
+ .then((rows) => rows[0] ?? null);
609
+ if (!locked)
610
+ throw notFound("MCP connection not found");
611
+ if (locked.credentialSecretId !== existing.credentialSecretId) {
612
+ throw conflict("Managed MCP credentials changed; retry the connection update");
613
+ }
614
+ if (patch.enabled === true
615
+ && RECONNECT_REQUIRED_STATUSES.has(locked.status)) {
616
+ throw reconnectRequiredError();
617
+ }
618
+ if (locked.provider === "linear"
619
+ && patch.accessMode !== undefined
620
+ && patch.accessMode !== locked.accessMode
621
+ && (locked.status === "active" || locked.status === "authorizing")) {
622
+ throw unprocessable("Linear access-mode changes require reauthorization: disconnect, select the new access mode, then reconnect OAuth");
623
+ }
624
+ if (replacement) {
625
+ await tx.insert(organizationSecrets).values({
626
+ id: replacement.id,
627
+ orgId,
628
+ name: replacement.name,
629
+ provider: "local_encrypted",
630
+ purpose: "managed_mcp_connection",
631
+ externalRef: replacement.externalRef,
632
+ latestVersion: 1,
633
+ description: "Encrypted managed MCP credentials",
634
+ createdByAgentId: actor.agentId ?? null,
635
+ createdByUserId: actor.userId ?? null,
636
+ });
637
+ await tx.insert(organizationSecretVersions).values({
638
+ secretId: replacement.id,
639
+ version: 1,
640
+ material: replacement.material,
641
+ valueSha256: replacement.valueSha256,
642
+ createdByAgentId: actor.agentId ?? null,
643
+ createdByUserId: actor.userId ?? null,
644
+ });
645
+ }
646
+ const updated = await tx
647
+ .update(mcpConnections)
648
+ .set({
649
+ credentialSecretId,
650
+ ...(patch.displayName !== undefined ? { displayName: patch.displayName } : {}),
651
+ ...(patch.externalScope !== undefined ? { externalScope: patch.externalScope ?? null } : {}),
652
+ ...(patch.accessMode !== undefined ? { accessMode: patch.accessMode } : {}),
653
+ ...(patch.safeConfig !== undefined ? { safeConfig: patch.safeConfig } : {}),
654
+ ...(patch.startupTimeoutMs !== undefined ? { startupTimeoutMs: patch.startupTimeoutMs } : {}),
655
+ ...(patch.toolTimeoutMs !== undefined ? { toolTimeoutMs: patch.toolTimeoutMs } : {}),
656
+ ...(patch.enabled !== undefined ? {
657
+ enabled: patch.enabled,
658
+ disabledAt: patch.enabled ? null : new Date(),
659
+ status: patch.enabled ? locked.status : "disabled",
660
+ } : {}),
661
+ ...(patch.required !== undefined ? { required: patch.required } : {}),
662
+ lifecycleRevision: locked.lifecycleRevision + 1,
663
+ updatedAt: nextConnectionMutationTime(locked),
664
+ })
665
+ .where(and(eq(mcpConnections.orgId, orgId), eq(mcpConnections.id, connectionId)))
666
+ .returning()
667
+ .then((rows) => rows[0] ?? null);
668
+ if (!updated)
669
+ throw notFound("MCP connection not found");
670
+ if (oldSecretIdToDelete) {
671
+ await tx
672
+ .delete(organizationSecrets)
673
+ .where(eq(organizationSecrets.id, oldSecretIdToDelete));
674
+ }
675
+ await tx.insert(activityLog).values(managedMcpActivityValues({
676
+ orgId,
677
+ connectionId,
678
+ action: "mcp_connection.updated",
679
+ actor,
680
+ details: {
681
+ provider: updated.provider,
682
+ status: updated.status,
683
+ accessMode: updated.accessMode,
684
+ },
685
+ }));
686
+ return updated;
687
+ });
688
+ return publicSummary(row);
689
+ },
690
+ reconnect: async (orgId, connectionId, actor = {}) => {
691
+ const existing = await findRow(orgId, connectionId);
692
+ assertLegacyMutable(existing);
693
+ const now = nextConnectionMutationTime(existing);
694
+ const row = await db.transaction(async (tx) => {
695
+ const updated = await tx
696
+ .update(mcpConnections)
697
+ .set({
698
+ status: existing.provider === "custom" ? "draft" : "authorizing",
699
+ enabled: true,
700
+ disabledAt: null,
701
+ revokedAt: null,
702
+ lifecycleRevision: sql `${mcpConnections.lifecycleRevision} + 1`,
703
+ updatedAt: now,
704
+ })
705
+ .where(and(eq(mcpConnections.orgId, orgId), eq(mcpConnections.id, connectionId)))
706
+ .returning()
707
+ .then((rows) => rows[0] ?? null);
708
+ if (!updated)
709
+ throw notFound("MCP connection not found");
710
+ if (existing.provider !== "custom") {
711
+ const activeGrant = await tx.select().from(mcpOAuthGrants)
712
+ .where(and(eq(mcpOAuthGrants.orgId, orgId), eq(mcpOAuthGrants.connectionId, connectionId), eq(mcpOAuthGrants.status, "active")))
713
+ .for("update")
714
+ .then((rows) => rows[0] ?? null);
715
+ if (activeGrant) {
716
+ await tx.update(mcpOAuthGrants).set({
717
+ status: "needs_reauth",
718
+ statusMetadata: { reason: "connection_reconnect" },
719
+ credentialSecretId: null,
720
+ refreshLeaseNonce: null,
721
+ refreshLeaseExpiresAt: null,
722
+ updatedAt: now,
723
+ }).where(eq(mcpOAuthGrants.id, activeGrant.id));
724
+ if (activeGrant.credentialSecretId) {
725
+ await tx.delete(organizationSecrets)
726
+ .where(eq(organizationSecrets.id, activeGrant.credentialSecretId));
727
+ }
728
+ }
729
+ }
730
+ await tx.insert(activityLog).values(managedMcpActivityValues({
731
+ orgId,
732
+ connectionId,
733
+ action: "mcp_connection.reconnect_requested",
734
+ actor,
735
+ details: {
736
+ provider: updated.provider,
737
+ status: updated.status,
738
+ },
739
+ }));
740
+ return updated;
741
+ });
742
+ return publicSummary(row);
743
+ },
744
+ disconnect: async (orgId, connectionId, actor = {}) => {
745
+ const existing = await findRow(orgId, connectionId);
746
+ assertLegacyMutable(existing);
747
+ const now = nextConnectionMutationTime(existing);
748
+ const row = await db.transaction(async (tx) => {
749
+ const updated = await tx
750
+ .update(mcpConnections)
751
+ .set({
752
+ status: "disabled",
753
+ enabled: false,
754
+ disabledAt: now,
755
+ lifecycleRevision: sql `${mcpConnections.lifecycleRevision} + 1`,
756
+ updatedAt: now,
757
+ })
758
+ .where(and(eq(mcpConnections.orgId, orgId), eq(mcpConnections.id, connectionId)))
759
+ .returning()
760
+ .then((rows) => rows[0] ?? null);
761
+ if (!updated)
762
+ throw notFound("MCP connection not found");
763
+ await tx.insert(activityLog).values(managedMcpActivityValues({
764
+ orgId,
765
+ connectionId,
766
+ action: "mcp_connection.disconnected",
767
+ actor,
768
+ details: {
769
+ provider: updated.provider,
770
+ status: updated.status,
771
+ },
772
+ }));
773
+ return updated;
774
+ });
775
+ return publicSummary(row);
776
+ },
777
+ listTools,
778
+ refreshTools: async (orgId, connectionId, actor = {}) => {
779
+ const existing = await findRow(orgId, connectionId);
780
+ assertLegacyMutable(existing);
781
+ if (existing.provider === "supabase" && !existing.externalScope) {
782
+ throw unprocessable("Supabase MCP connections require a selected project before discovery");
783
+ }
784
+ if (!canDiscoverTools(existing)) {
785
+ throw discoveryNotReadyError();
786
+ }
787
+ const snapshot = discoverySnapshot(existing);
788
+ let client = null;
789
+ try {
790
+ client = await createClient(await buildClientOptions(existing));
791
+ const normalized = normalizeMcpDiscoveredTools(existing.name, await client.discoverTools(), discoveryFilter(existing));
792
+ const normalizedByName = new Map(normalized.map((tool) => [tool.externalToolName, tool]));
793
+ await db.transaction(async (tx) => {
794
+ const locked = await tx
795
+ .select()
796
+ .from(mcpConnections)
797
+ .where(and(eq(mcpConnections.orgId, orgId), eq(mcpConnections.id, connectionId)))
798
+ .for("update")
799
+ .then((rows) => rows[0] ?? null);
800
+ if (!locked)
801
+ throw notFound("MCP connection not found");
802
+ assertDiscoverySnapshot(locked, snapshot);
803
+ const now = nextConnectionMutationTime(locked);
804
+ const existingTools = await tx
805
+ .select()
806
+ .from(customIntegrationTools)
807
+ .where(and(eq(customIntegrationTools.orgId, orgId), eq(customIntegrationTools.connectionId, connectionId)));
808
+ const reconciled = reconcileMcpToolCatalog(existingTools, normalized);
809
+ const existingByName = new Map(existingTools.map((tool) => [tool.externalToolName, tool]));
810
+ for (const tool of reconciled) {
811
+ const prior = existingByName.get(tool.externalToolName);
812
+ const current = normalizedByName.get(tool.externalToolName);
813
+ if (prior) {
814
+ await tx
815
+ .update(customIntegrationTools)
816
+ .set({
817
+ ...(current ? {
818
+ rudderToolName: current.rudderToolName,
819
+ description: current.description,
820
+ rawInputSchema: current.rawInputSchema,
821
+ inputSchema: current.inputSchema,
822
+ rawOutputSchema: current.rawOutputSchema,
823
+ outputSchema: current.outputSchema,
824
+ discoveredAt: now,
825
+ } : {}),
826
+ status: tool.status,
827
+ enabled: tool.enabled,
828
+ removedAt: tool.status === "removed" ? now : null,
829
+ updatedAt: now,
830
+ })
831
+ .where(eq(customIntegrationTools.id, prior.id));
832
+ }
833
+ else if (current) {
834
+ await tx.insert(customIntegrationTools).values({
835
+ orgId,
836
+ connectionId,
837
+ externalToolName: current.externalToolName,
838
+ rudderToolName: current.rudderToolName,
839
+ description: current.description,
840
+ rawInputSchema: current.rawInputSchema,
841
+ inputSchema: current.inputSchema,
842
+ rawOutputSchema: current.rawOutputSchema,
843
+ outputSchema: current.outputSchema,
844
+ status: "active",
845
+ enabled: true,
846
+ discoveredAt: now,
847
+ });
848
+ }
849
+ }
850
+ await tx
851
+ .update(mcpConnections)
852
+ .set({
853
+ status: "active",
854
+ enabled: true,
855
+ activatedAt: locked.activatedAt ?? now,
856
+ lastDiscoveredAt: now,
857
+ disabledAt: null,
858
+ lifecycleRevision: locked.lifecycleRevision + 1,
859
+ updatedAt: now,
860
+ })
861
+ .where(and(eq(mcpConnections.orgId, orgId), eq(mcpConnections.id, connectionId)));
862
+ await tx.insert(activityLog).values(managedMcpActivityValues({
863
+ orgId,
864
+ connectionId,
865
+ action: "mcp_connection.tools_refreshed",
866
+ actor,
867
+ details: {
868
+ provider: locked.provider,
869
+ toolCount: normalized.length,
870
+ },
871
+ }));
872
+ });
873
+ return listTools(orgId, connectionId);
874
+ }
875
+ catch (error) {
876
+ if (error instanceof ManagedMcpDiscoveryStaleError) {
877
+ throw error;
878
+ }
879
+ await db.transaction(async (tx) => {
880
+ const locked = await tx
881
+ .select()
882
+ .from(mcpConnections)
883
+ .where(and(eq(mcpConnections.orgId, orgId), eq(mcpConnections.id, connectionId)))
884
+ .for("update")
885
+ .then((rows) => rows[0] ?? null);
886
+ if (!locked)
887
+ throw notFound("MCP connection not found");
888
+ assertDiscoverySnapshot(locked, snapshot);
889
+ const now = nextConnectionMutationTime(locked);
890
+ await tx
891
+ .update(mcpConnections)
892
+ .set({
893
+ status: "error",
894
+ lifecycleRevision: locked.lifecycleRevision + 1,
895
+ updatedAt: now,
896
+ })
897
+ .where(and(eq(mcpConnections.orgId, orgId), eq(mcpConnections.id, connectionId)));
898
+ await tx.insert(activityLog).values(managedMcpActivityValues({
899
+ orgId,
900
+ connectionId,
901
+ action: "mcp_connection.discovery_failed",
902
+ actor,
903
+ details: {
904
+ provider: locked.provider,
905
+ reason: "upstream_discovery_failed",
906
+ },
907
+ }));
908
+ });
909
+ if (error instanceof HttpError) {
910
+ throw error;
911
+ }
912
+ throw redactedDiscoveryError();
913
+ }
914
+ finally {
915
+ await client?.close().catch(() => undefined);
916
+ }
917
+ },
918
+ };
919
+ }
920
+ //# sourceMappingURL=managed-connections.js.map