@stage-labs/metro 0.1.0-beta.24 → 0.1.0-beta.241

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 (473) hide show
  1. package/dist/api.js +9 -129
  2. package/dist/background.js +123 -0
  3. package/dist/claude-settings.js +40 -0
  4. package/dist/claude.js +197 -0
  5. package/dist/cli.js +59 -111
  6. package/dist/control.js +19 -103
  7. package/dist/hold.js +210 -0
  8. package/dist/local.js +43 -0
  9. package/dist/mcp-config.js +27 -0
  10. package/dist/memory.js +222 -0
  11. package/dist/node-name.js +71 -0
  12. package/dist/onboarding.js +44 -0
  13. package/dist/provider-flags.js +9 -0
  14. package/dist/route.js +58 -0
  15. package/dist/runtime-install.js +96 -0
  16. package/dist/runtime.js +29 -52
  17. package/dist/serve.js +157 -0
  18. package/dist/service.js +304 -0
  19. package/dist/tail.js +10 -11
  20. package/dist/update.js +13 -1
  21. package/dist/voice.js +56 -0
  22. package/package.json +2 -23
  23. package/runtime/marketplace/.claude-plugin/marketplace.json +12 -0
  24. package/runtime/marketplace/plugin/.claude-plugin/plugin.json +17 -0
  25. package/runtime/marketplace/plugin/.mcp.json +1 -0
  26. package/runtime/marketplace/plugin/MEMORY.md +78 -0
  27. package/runtime/marketplace/plugin/METRO.md +26 -0
  28. package/runtime/marketplace/plugin/STAGE.md +75 -0
  29. package/runtime/marketplace/plugin/bin/guard.mjs +75 -0
  30. package/runtime/marketplace/plugin/bin/metro-plugin.mjs +30 -0
  31. package/runtime/marketplace/plugin/bin/policy.mjs +97 -0
  32. package/runtime/marketplace/plugin/bin/session-start.mjs +31 -0
  33. package/runtime/marketplace/plugin/hooks/hooks.json +25 -0
  34. package/runtime/node_modules/@metro-labs/core/package.json +51 -0
  35. package/runtime/node_modules/@metro-labs/core/src/endpoints.ts +7 -0
  36. package/runtime/node_modules/@metro-labs/{mcp/src/daemon → core/src}/events.ts +11 -7
  37. package/runtime/node_modules/@metro-labs/{mcp/src/db → core/src}/ids.ts +5 -0
  38. package/runtime/node_modules/@metro-labs/core/src/is-record.ts +2 -0
  39. package/runtime/node_modules/@metro-labs/{mcp/src/stations → core/src}/lines.ts +22 -26
  40. package/runtime/node_modules/@metro-labs/{mcp/src/daemon → core/src}/protocol.ts +7 -4
  41. package/runtime/node_modules/@metro-labs/{mcp/src/daemon → core/src}/secure-fs.ts +17 -0
  42. package/runtime/node_modules/@metro-labs/core/src/station-names.ts +14 -0
  43. package/runtime/node_modules/@metro-labs/core/src/stations/account-files.ts +41 -0
  44. package/runtime/node_modules/@metro-labs/core/src/stations/account-store.ts +83 -0
  45. package/runtime/node_modules/@metro-labs/{mcp → core}/src/stations/attachments.ts +0 -1
  46. package/runtime/node_modules/@metro-labs/core/src/stations/mail-text.ts +72 -0
  47. package/runtime/node_modules/@metro-labs/core/src/stations/mail-trust.ts +29 -0
  48. package/runtime/node_modules/@metro-labs/core/src/stations/mail.ts +212 -0
  49. package/runtime/node_modules/@metro-labs/core/src/stations/messaging-normalize.ts +16 -0
  50. package/runtime/node_modules/@metro-labs/core/src/stations/oauth.ts +126 -0
  51. package/runtime/node_modules/@metro-labs/core/src/stations/profile.ts +58 -0
  52. package/runtime/node_modules/@metro-labs/core/src/stations/sender-profile.ts +64 -0
  53. package/runtime/node_modules/@metro-labs/{mcp → core}/src/stations/station-runtime.ts +6 -11
  54. package/runtime/node_modules/@metro-labs/core/src/stations/train-boot.ts +42 -0
  55. package/runtime/node_modules/@metro-labs/core/src/stations/train-events.ts +84 -0
  56. package/runtime/node_modules/@metro-labs/{mcp → core}/src/stations/types.ts +19 -1
  57. package/runtime/node_modules/@metro-labs/core/src/tickets.ts +37 -0
  58. package/runtime/node_modules/@metro-labs/core/src/version.ts +2 -0
  59. package/runtime/node_modules/@metro-labs/daemon/package.json +51 -0
  60. package/runtime/node_modules/@metro-labs/daemon/src/agent-user/agent-fs.ts +134 -0
  61. package/runtime/node_modules/@metro-labs/daemon/src/agent-user/crontab.ts +44 -0
  62. package/runtime/node_modules/@metro-labs/daemon/src/agent-user/files-api.ts +12 -0
  63. package/runtime/node_modules/@metro-labs/daemon/src/agent-user/files.ts +89 -0
  64. package/runtime/node_modules/@metro-labs/daemon/src/agent-user/home-fs.ts +113 -0
  65. package/runtime/node_modules/@metro-labs/daemon/src/agent-user/job-env.ts +39 -0
  66. package/runtime/node_modules/@metro-labs/daemon/src/agent-user/provision.ts +80 -0
  67. package/runtime/node_modules/@metro-labs/daemon/src/agent-user/schedule-detail.ts +99 -0
  68. package/runtime/node_modules/@metro-labs/daemon/src/agent-user/schedules-api.ts +27 -0
  69. package/runtime/node_modules/@metro-labs/daemon/src/agent-user/schedules.ts +144 -0
  70. package/runtime/node_modules/@metro-labs/daemon/src/agent-user/unit-files.ts +43 -0
  71. package/runtime/node_modules/@metro-labs/daemon/src/agent-user/user.ts +91 -0
  72. package/runtime/node_modules/@metro-labs/daemon/src/agent-user/view.ts +87 -0
  73. package/runtime/node_modules/@metro-labs/daemon/src/agents/account-attach.ts +19 -0
  74. package/runtime/node_modules/@metro-labs/daemon/src/agents/account-lookups.ts +55 -0
  75. package/runtime/node_modules/@metro-labs/daemon/src/agents/account-routes.ts +76 -0
  76. package/runtime/node_modules/@metro-labs/daemon/src/agents/accounts-api.ts +357 -0
  77. package/runtime/node_modules/@metro-labs/daemon/src/agents/admin.ts +30 -0
  78. package/runtime/node_modules/@metro-labs/daemon/src/agents/allowlist.ts +59 -0
  79. package/runtime/node_modules/@metro-labs/daemon/src/agents/api.ts +131 -0
  80. package/runtime/node_modules/@metro-labs/daemon/src/agents/bundle.ts +132 -0
  81. package/runtime/node_modules/@metro-labs/daemon/src/agents/file-admin.ts +305 -0
  82. package/runtime/node_modules/@metro-labs/daemon/src/agents/files.ts +142 -0
  83. package/runtime/node_modules/@metro-labs/{mcp/src/db/key-map.ts → daemon/src/agents/keys.ts} +1 -11
  84. package/runtime/node_modules/@metro-labs/daemon/src/agents/map.ts +133 -0
  85. package/runtime/node_modules/@metro-labs/daemon/src/agents/policy-route.ts +27 -0
  86. package/runtime/node_modules/@metro-labs/{mcp/src/db/agent-scope.ts → daemon/src/agents/scope.ts} +2 -2
  87. package/runtime/node_modules/@metro-labs/daemon/src/agents/sender-cards.ts +94 -0
  88. package/runtime/node_modules/@metro-labs/daemon/src/agents/senders.ts +38 -0
  89. package/runtime/node_modules/@metro-labs/daemon/src/approvals/api.ts +55 -0
  90. package/runtime/node_modules/@metro-labs/daemon/src/approvals/pending.ts +150 -0
  91. package/runtime/node_modules/@metro-labs/daemon/src/approvals/preview.ts +66 -0
  92. package/runtime/node_modules/@metro-labs/daemon/src/boot/boot.ts +231 -0
  93. package/runtime/node_modules/@metro-labs/daemon/src/boot/connect-hint.ts +36 -0
  94. package/runtime/node_modules/@metro-labs/{mcp/src/daemon → daemon/src/boot}/crash-guard.ts +1 -1
  95. package/runtime/node_modules/@metro-labs/daemon/src/boot/local-owner.ts +21 -0
  96. package/runtime/node_modules/@metro-labs/{mcp/src/daemon → daemon/src/boot}/paths.ts +6 -34
  97. package/runtime/node_modules/@metro-labs/daemon/src/channels/addressed.ts +26 -0
  98. package/runtime/node_modules/@metro-labs/{mcp → daemon}/src/channels/inbound.ts +75 -45
  99. package/runtime/node_modules/@metro-labs/{mcp → daemon}/src/channels/media-note.ts +11 -7
  100. package/runtime/node_modules/@metro-labs/{mcp → daemon}/src/channels/pending.ts +4 -1
  101. package/runtime/node_modules/@metro-labs/{mcp → daemon}/src/channels/relay.ts +2 -2
  102. package/runtime/node_modules/@metro-labs/daemon/src/claude/api.ts +380 -0
  103. package/runtime/node_modules/@metro-labs/daemon/src/claude/files.ts +359 -0
  104. package/runtime/node_modules/@metro-labs/daemon/src/claude/login.ts +208 -0
  105. package/runtime/node_modules/@metro-labs/daemon/src/claude/memory-routine.ts +123 -0
  106. package/runtime/node_modules/@metro-labs/daemon/src/claude/memory.ts +32 -0
  107. package/runtime/node_modules/@metro-labs/daemon/src/claude/onboarding.ts +60 -0
  108. package/runtime/node_modules/@metro-labs/daemon/src/claude/plugin-install.ts +149 -0
  109. package/runtime/node_modules/@metro-labs/daemon/src/claude/session-files.ts +75 -0
  110. package/runtime/node_modules/@metro-labs/daemon/src/claude/session.ts +299 -0
  111. package/runtime/node_modules/@metro-labs/daemon/src/claude/settings.ts +109 -0
  112. package/runtime/node_modules/@metro-labs/daemon/src/claude/setup.ts +351 -0
  113. package/runtime/node_modules/@metro-labs/daemon/src/claude/skills.ts +120 -0
  114. package/runtime/node_modules/@metro-labs/daemon/src/claude/usage-probe.ts +127 -0
  115. package/runtime/node_modules/@metro-labs/daemon/src/claude/version.ts +113 -0
  116. package/runtime/node_modules/@metro-labs/{mcp/src/daemon/connector-api.ts → daemon/src/connectors/api.ts} +79 -113
  117. package/runtime/node_modules/@metro-labs/{mcp/src/db/connector-config.ts → daemon/src/connectors/config.ts} +67 -41
  118. package/runtime/node_modules/@metro-labs/daemon/src/connectors/gates.ts +72 -0
  119. package/runtime/node_modules/@metro-labs/daemon/src/connectors/health.ts +18 -0
  120. package/runtime/node_modules/@metro-labs/{mcp/src/daemon → daemon/src/connectors}/oauth-client.ts +14 -17
  121. package/runtime/node_modules/@metro-labs/{mcp/src/daemon → daemon/src/connectors}/oauth-discovery.ts +33 -20
  122. package/runtime/node_modules/@metro-labs/{mcp/src/daemon/connector-oauth-routes.ts → daemon/src/connectors/oauth-routes.ts} +30 -32
  123. package/runtime/node_modules/@metro-labs/{mcp/src/daemon/connector-oauth.ts → daemon/src/connectors/oauth.ts} +61 -22
  124. package/runtime/node_modules/@metro-labs/daemon/src/connectors/plugin-sync.ts +131 -0
  125. package/runtime/node_modules/@metro-labs/daemon/src/connectors/reach.ts +27 -0
  126. package/runtime/node_modules/@metro-labs/daemon/src/connectors/relay-policy.ts +90 -0
  127. package/runtime/node_modules/@metro-labs/daemon/src/connectors/relay.ts +347 -0
  128. package/runtime/node_modules/@metro-labs/daemon/src/connectors/store.ts +385 -0
  129. package/runtime/node_modules/@metro-labs/daemon/src/connectors/tools.ts +81 -0
  130. package/runtime/node_modules/@metro-labs/daemon/src/connectors/transfer-api.ts +116 -0
  131. package/runtime/node_modules/@metro-labs/daemon/src/connectors/transfer-crypto.ts +44 -0
  132. package/runtime/node_modules/@metro-labs/daemon/src/connectors/transfer-store.ts +48 -0
  133. package/runtime/node_modules/@metro-labs/daemon/src/connectors/url.ts +37 -0
  134. package/runtime/node_modules/@metro-labs/daemon/src/connectors/verify.ts +106 -0
  135. package/runtime/node_modules/@metro-labs/{mcp/src/daemon → daemon/src/files}/attach-grant.ts +4 -4
  136. package/runtime/node_modules/@metro-labs/{mcp/src/daemon → daemon/src/files}/attach-owner.ts +3 -3
  137. package/runtime/node_modules/@metro-labs/daemon/src/files/attach-reaper.ts +174 -0
  138. package/runtime/node_modules/@metro-labs/{mcp/src/daemon → daemon/src/files}/attach-serve.ts +12 -13
  139. package/runtime/node_modules/@metro-labs/{mcp/src/daemon → daemon/src/files}/upload-api.ts +10 -27
  140. package/runtime/node_modules/@metro-labs/{mcp/src/daemon → daemon/src/files}/upload-store.ts +4 -4
  141. package/runtime/node_modules/@metro-labs/daemon/src/gateway/bedrock.ts +233 -0
  142. package/runtime/node_modules/@metro-labs/daemon/src/gateway/codex-auth.ts +214 -0
  143. package/runtime/node_modules/@metro-labs/daemon/src/gateway/codex-device.ts +91 -0
  144. package/runtime/node_modules/@metro-labs/daemon/src/gateway/codex-stream.ts +173 -0
  145. package/runtime/node_modules/@metro-labs/daemon/src/gateway/codex-translate.ts +209 -0
  146. package/runtime/node_modules/@metro-labs/daemon/src/gateway/codex-version.ts +44 -0
  147. package/runtime/node_modules/@metro-labs/daemon/src/gateway/codex.ts +155 -0
  148. package/runtime/node_modules/@metro-labs/daemon/src/gateway/effort.ts +93 -0
  149. package/runtime/node_modules/@metro-labs/daemon/src/gateway/eventstream.ts +123 -0
  150. package/runtime/node_modules/@metro-labs/daemon/src/gateway/forward.ts +237 -0
  151. package/runtime/node_modules/@metro-labs/daemon/src/gateway/frames.ts +118 -0
  152. package/runtime/node_modules/@metro-labs/daemon/src/gateway/gateway.ts +307 -0
  153. package/runtime/node_modules/@metro-labs/daemon/src/gateway/gemini-auth.ts +160 -0
  154. package/runtime/node_modules/@metro-labs/daemon/src/gateway/gemini-client.ts +46 -0
  155. package/runtime/node_modules/@metro-labs/daemon/src/gateway/gemini-setup.ts +150 -0
  156. package/runtime/node_modules/@metro-labs/daemon/src/gateway/gemini-stream.ts +139 -0
  157. package/runtime/node_modules/@metro-labs/daemon/src/gateway/gemini-translate.ts +235 -0
  158. package/runtime/node_modules/@metro-labs/daemon/src/gateway/gemini.ts +208 -0
  159. package/runtime/node_modules/@metro-labs/daemon/src/gateway/model-api.ts +203 -0
  160. package/runtime/node_modules/@metro-labs/daemon/src/gateway/model-config.ts +285 -0
  161. package/runtime/node_modules/@metro-labs/daemon/src/gateway/model-lists.ts +57 -0
  162. package/runtime/node_modules/@metro-labs/daemon/src/gateway/model-signin.ts +161 -0
  163. package/runtime/node_modules/@metro-labs/daemon/src/gateway/model-store.ts +72 -0
  164. package/runtime/node_modules/@metro-labs/daemon/src/gateway/openrouter.ts +104 -0
  165. package/runtime/node_modules/@metro-labs/daemon/src/gateway/pkce.ts +36 -0
  166. package/runtime/node_modules/@metro-labs/daemon/src/gateway/provider-models.ts +118 -0
  167. package/runtime/node_modules/@metro-labs/daemon/src/gateway/served.ts +18 -0
  168. package/runtime/node_modules/@metro-labs/daemon/src/gateway/subscription.ts +120 -0
  169. package/runtime/node_modules/@metro-labs/daemon/src/gateway/text.ts +35 -0
  170. package/runtime/node_modules/@metro-labs/daemon/src/gateway/tool-search.ts +126 -0
  171. package/runtime/node_modules/@metro-labs/daemon/src/gateway/usage-refresh.ts +102 -0
  172. package/runtime/node_modules/@metro-labs/daemon/src/gateway/usage.ts +348 -0
  173. package/runtime/node_modules/@metro-labs/{mcp → daemon}/src/mcp/accounts.ts +28 -17
  174. package/runtime/node_modules/@metro-labs/daemon/src/mcp/attachment-schema.ts +91 -0
  175. package/runtime/node_modules/@metro-labs/{mcp → daemon}/src/mcp/call-tools.ts +81 -38
  176. package/runtime/node_modules/@metro-labs/{mcp → daemon}/src/mcp/ctx.ts +4 -4
  177. package/runtime/node_modules/@metro-labs/{mcp → daemon}/src/mcp/event-store.ts +15 -16
  178. package/runtime/node_modules/@metro-labs/{mcp → daemon}/src/mcp/group-tools.ts +2 -2
  179. package/runtime/node_modules/@metro-labs/{mcp → daemon}/src/mcp/index.ts +37 -79
  180. package/runtime/node_modules/@metro-labs/daemon/src/mcp/instructions.ts +30 -0
  181. package/runtime/node_modules/@metro-labs/{mcp → daemon}/src/mcp/member-tools.ts +2 -2
  182. package/runtime/node_modules/@metro-labs/daemon/src/mcp/permission-prompt.ts +92 -0
  183. package/runtime/node_modules/@metro-labs/daemon/src/mcp/permission-relay.ts +88 -0
  184. package/runtime/node_modules/@metro-labs/daemon/src/mcp/policy-gate.ts +82 -0
  185. package/runtime/node_modules/@metro-labs/daemon/src/mcp/policy-snapshot.ts +79 -0
  186. package/runtime/node_modules/@metro-labs/daemon/src/mcp/profile-lookup.ts +60 -0
  187. package/runtime/node_modules/@metro-labs/daemon/src/mcp/profile-tool.ts +96 -0
  188. package/runtime/node_modules/@metro-labs/daemon/src/mcp/read-tool.ts +87 -0
  189. package/runtime/node_modules/@metro-labs/daemon/src/mcp/request-identity.ts +46 -0
  190. package/runtime/node_modules/@metro-labs/daemon/src/mcp/session-slot.ts +75 -0
  191. package/runtime/node_modules/@metro-labs/{mcp → daemon}/src/mcp/session.ts +61 -57
  192. package/runtime/node_modules/@metro-labs/daemon/src/mcp/tool-catalog.ts +93 -0
  193. package/runtime/node_modules/@metro-labs/daemon/src/mcp/tool-def.ts +9 -0
  194. package/runtime/node_modules/@metro-labs/{mcp → daemon}/src/mcp/tool-dispatch.ts +53 -40
  195. package/runtime/node_modules/@metro-labs/{mcp → daemon}/src/mcp/tool-schemas.ts +97 -114
  196. package/runtime/node_modules/@metro-labs/{mcp → daemon}/src/mcp/upload-tool.ts +6 -11
  197. package/runtime/node_modules/@metro-labs/daemon/src/metro-user/helper-script.ts +126 -0
  198. package/runtime/node_modules/@metro-labs/daemon/src/metro-user/install.ts +37 -0
  199. package/runtime/node_modules/@metro-labs/daemon/src/metro-user/privilege.ts +48 -0
  200. package/runtime/node_modules/@metro-labs/daemon/src/monitor/api.ts +132 -0
  201. package/runtime/node_modules/@metro-labs/daemon/src/net/tunnel.ts +316 -0
  202. package/runtime/node_modules/@metro-labs/daemon/src/policy/policy.ts +118 -0
  203. package/runtime/node_modules/@metro-labs/daemon/src/routes/bearer.ts +35 -0
  204. package/runtime/node_modules/@metro-labs/daemon/src/routes/body.ts +24 -0
  205. package/runtime/node_modules/@metro-labs/{mcp/src/daemon → daemon/src/routes}/http.ts +65 -52
  206. package/runtime/node_modules/@metro-labs/daemon/src/routes/local-mode.ts +209 -0
  207. package/runtime/node_modules/@metro-labs/daemon/src/routes/session-apis.ts +71 -0
  208. package/runtime/node_modules/@metro-labs/daemon/src/routes/session.ts +29 -0
  209. package/runtime/node_modules/@metro-labs/daemon/src/routes/threema-callback.ts +103 -0
  210. package/runtime/node_modules/@metro-labs/daemon/src/server/cloudwatch.ts +178 -0
  211. package/runtime/node_modules/@metro-labs/daemon/src/server/control.ts +39 -0
  212. package/runtime/node_modules/@metro-labs/daemon/src/server/machine.ts +58 -0
  213. package/runtime/node_modules/@metro-labs/daemon/src/server/owner.ts +26 -0
  214. package/runtime/node_modules/@metro-labs/daemon/src/server/update.ts +90 -0
  215. package/runtime/node_modules/@metro-labs/daemon/src/server.ts +2 -0
  216. package/runtime/node_modules/@metro-labs/daemon/src/stations/attach-browser.ts +102 -0
  217. package/runtime/node_modules/@metro-labs/daemon/src/stations/attach-driver.ts +42 -0
  218. package/runtime/node_modules/@metro-labs/{mcp → daemon}/src/stations/attach-inline.ts +29 -1
  219. package/runtime/node_modules/@metro-labs/{mcp → daemon}/src/stations/attach-interactive.ts +5 -31
  220. package/runtime/node_modules/@metro-labs/{mcp → daemon}/src/stations/attach-resolve.ts +38 -13
  221. package/runtime/node_modules/@metro-labs/{mcp/src/daemon → daemon/src/stations}/attach-session.ts +32 -22
  222. package/runtime/node_modules/@metro-labs/{mcp → daemon}/src/stations/attach-xmtp.ts +8 -9
  223. package/runtime/node_modules/@metro-labs/{mcp → daemon}/src/stations/attach.ts +69 -3
  224. package/runtime/node_modules/@metro-labs/{mcp/src/db → daemon/src/stations}/materialize.ts +60 -175
  225. package/runtime/node_modules/@metro-labs/{mcp → daemon}/src/stations/registry.ts +20 -2
  226. package/runtime/node_modules/@metro-labs/daemon/src/stations/runtime-deps.ts +82 -0
  227. package/runtime/node_modules/@metro-labs/{mcp/src/daemon → daemon/src/stations}/supervisor-io.ts +3 -3
  228. package/runtime/node_modules/@metro-labs/{mcp/src/daemon → daemon/src/stations}/supervisor.ts +6 -9
  229. package/runtime/node_modules/@metro-labs/daemon/src/stations/threema-callbacks.ts +32 -0
  230. package/runtime/node_modules/@metro-labs/{mcp/src/daemon → daemon/src/stations}/train-call.ts +1 -1
  231. package/runtime/node_modules/@metro-labs/daemon/src/stations/webhook-endpoints.ts +51 -0
  232. package/runtime/node_modules/@metro-labs/daemon/src/terminal/api.ts +84 -0
  233. package/runtime/node_modules/@metro-labs/daemon/src/terminal/socket.ts +124 -0
  234. package/runtime/node_modules/@metro-labs/daemon/src/terminal/tickets.ts +15 -0
  235. package/runtime/node_modules/@metro-labs/daemon/src/vault/api.ts +45 -0
  236. package/runtime/node_modules/@metro-labs/daemon/src/vault/config.ts +51 -0
  237. package/runtime/node_modules/@metro-labs/daemon/src/vault/firewall.ts +9 -0
  238. package/runtime/node_modules/@metro-labs/daemon/src/vault/index.ts +96 -0
  239. package/runtime/node_modules/@metro-labs/daemon/src/vault/install.ts +56 -0
  240. package/runtime/node_modules/@metro-labs/daemon/src/vault/paths.ts +26 -0
  241. package/runtime/node_modules/@metro-labs/daemon/src/vault/proxy.ts +147 -0
  242. package/runtime/node_modules/@metro-labs/daemon/src/vault/store.ts +129 -0
  243. package/runtime/node_modules/@metro-labs/daemon/src/vault/trust.ts +44 -0
  244. package/runtime/node_modules/@metro-labs/daemon/src/voice/api.ts +14 -0
  245. package/runtime/node_modules/@metro-labs/daemon/src/voice/approvals.ts +43 -0
  246. package/runtime/node_modules/@metro-labs/daemon/src/voice/audio.ts +153 -0
  247. package/runtime/node_modules/@metro-labs/daemon/src/voice/brain.ts +135 -0
  248. package/runtime/node_modules/@metro-labs/daemon/src/voice/call.ts +200 -0
  249. package/runtime/node_modules/@metro-labs/daemon/src/voice/calls.ts +130 -0
  250. package/runtime/node_modules/@metro-labs/daemon/src/voice/peer.ts +84 -0
  251. package/runtime/node_modules/@metro-labs/daemon/src/voice/scribe.ts +103 -0
  252. package/runtime/node_modules/@metro-labs/daemon/src/voice/speakable.ts +54 -0
  253. package/runtime/node_modules/@metro-labs/daemon/src/voice/speech.ts +104 -0
  254. package/runtime/node_modules/@metro-labs/daemon/src/voice/store.ts +116 -0
  255. package/runtime/node_modules/@metro-labs/daemon/src/voice/talk.ts +256 -0
  256. package/runtime/node_modules/@metro-labs/discord-bot/package.json +2 -4
  257. package/runtime/node_modules/@metro-labs/discord-bot/src/accounts.ts +3 -23
  258. package/runtime/node_modules/@metro-labs/discord-bot/src/actions.ts +19 -187
  259. package/runtime/node_modules/@metro-labs/discord-bot/src/attachments.ts +2 -2
  260. package/runtime/node_modules/@metro-labs/discord-bot/src/format.ts +26 -67
  261. package/runtime/node_modules/@metro-labs/discord-bot/src/group-actions.ts +1 -1
  262. package/runtime/node_modules/@metro-labs/discord-bot/src/group.ts +2 -2
  263. package/runtime/node_modules/@metro-labs/discord-bot/src/index.ts +8 -14
  264. package/runtime/node_modules/@metro-labs/discord-bot/src/members.ts +2 -2
  265. package/runtime/node_modules/@metro-labs/discord-bot/src/profile.ts +68 -0
  266. package/runtime/node_modules/@metro-labs/discord-bot/src/send-files.ts +12 -13
  267. package/runtime/node_modules/@metro-labs/discord-bot/src/station.ts +5 -1
  268. package/runtime/node_modules/@metro-labs/gmail/package.json +25 -0
  269. package/runtime/node_modules/@metro-labs/gmail/src/accounts.ts +81 -0
  270. package/runtime/node_modules/@metro-labs/gmail/src/actions.ts +14 -0
  271. package/runtime/node_modules/@metro-labs/gmail/src/api.ts +31 -0
  272. package/runtime/node_modules/@metro-labs/gmail/src/attachments.ts +35 -0
  273. package/runtime/node_modules/@metro-labs/gmail/src/auth.ts +105 -0
  274. package/runtime/node_modules/@metro-labs/gmail/src/config.ts +13 -0
  275. package/runtime/node_modules/@metro-labs/gmail/src/inbound.ts +96 -0
  276. package/runtime/node_modules/@metro-labs/gmail/src/index.ts +12 -0
  277. package/runtime/node_modules/@metro-labs/gmail/src/login.ts +37 -0
  278. package/runtime/node_modules/@metro-labs/gmail/src/message.ts +125 -0
  279. package/runtime/node_modules/@metro-labs/gmail/src/mime.ts +70 -0
  280. package/runtime/node_modules/@metro-labs/gmail/src/outbound.ts +124 -0
  281. package/runtime/node_modules/@metro-labs/gmail/src/query.ts +99 -0
  282. package/runtime/node_modules/@metro-labs/gmail/src/state.ts +24 -0
  283. package/runtime/node_modules/@metro-labs/gmail/src/station.ts +15 -0
  284. package/runtime/node_modules/@metro-labs/gmail/src/trust.ts +42 -0
  285. package/runtime/node_modules/@metro-labs/http/package.json +30 -0
  286. package/runtime/node_modules/@metro-labs/http/src/api-http.ts +135 -0
  287. package/runtime/node_modules/@metro-labs/{mcp/src/daemon/session-api.ts → http/src/mode-api.ts} +13 -9
  288. package/runtime/node_modules/@metro-labs/http/src/return-to.ts +21 -0
  289. package/runtime/node_modules/@metro-labs/http/src/sigv4.ts +90 -0
  290. package/runtime/node_modules/@metro-labs/http/src/workos-token.ts +149 -0
  291. package/runtime/node_modules/@metro-labs/outlook/package.json +25 -0
  292. package/runtime/node_modules/@metro-labs/outlook/src/accounts.ts +78 -0
  293. package/runtime/node_modules/@metro-labs/outlook/src/actions.ts +14 -0
  294. package/runtime/node_modules/@metro-labs/outlook/src/attachments.ts +81 -0
  295. package/runtime/node_modules/@metro-labs/outlook/src/auth.ts +120 -0
  296. package/runtime/node_modules/@metro-labs/outlook/src/browser.ts +42 -0
  297. package/runtime/node_modules/@metro-labs/outlook/src/config.ts +23 -0
  298. package/runtime/node_modules/@metro-labs/outlook/src/format.ts +59 -0
  299. package/runtime/node_modules/@metro-labs/outlook/src/graph.ts +55 -0
  300. package/runtime/node_modules/@metro-labs/outlook/src/inbound.ts +96 -0
  301. package/runtime/node_modules/@metro-labs/outlook/src/index.ts +12 -0
  302. package/runtime/node_modules/@metro-labs/outlook/src/login.ts +129 -0
  303. package/runtime/node_modules/@metro-labs/outlook/src/me.ts +31 -0
  304. package/runtime/node_modules/@metro-labs/outlook/src/outbound.ts +103 -0
  305. package/runtime/node_modules/@metro-labs/outlook/src/query.ts +84 -0
  306. package/runtime/node_modules/@metro-labs/outlook/src/state.ts +28 -0
  307. package/runtime/node_modules/@metro-labs/outlook/src/station.ts +15 -0
  308. package/runtime/node_modules/@metro-labs/outlook/src/trust.ts +41 -0
  309. package/runtime/node_modules/@metro-labs/telegram/package.json +1 -3
  310. package/runtime/node_modules/@metro-labs/telegram/src/accounts.ts +5 -24
  311. package/runtime/node_modules/@metro-labs/telegram/src/actions.ts +8 -6
  312. package/runtime/node_modules/@metro-labs/telegram/src/attachments.ts +1 -1
  313. package/runtime/node_modules/@metro-labs/telegram/src/client.ts +2 -2
  314. package/runtime/node_modules/@metro-labs/telegram/src/format.ts +19 -34
  315. package/runtime/node_modules/@metro-labs/telegram/src/group.ts +3 -3
  316. package/runtime/node_modules/@metro-labs/telegram/src/inbound.ts +13 -34
  317. package/runtime/node_modules/@metro-labs/telegram/src/index.ts +4 -43
  318. package/runtime/node_modules/@metro-labs/telegram/src/media-actions.ts +2 -3
  319. package/runtime/node_modules/@metro-labs/telegram/src/members.ts +1 -1
  320. package/runtime/node_modules/@metro-labs/telegram/src/profile.ts +70 -0
  321. package/runtime/node_modules/@metro-labs/telegram/src/reactions.ts +2 -2
  322. package/runtime/node_modules/@metro-labs/telegram/src/station.ts +4 -1
  323. package/runtime/node_modules/@metro-labs/telegram/src/types.ts +0 -1
  324. package/runtime/node_modules/@metro-labs/telegram-bot/package.json +1 -1
  325. package/runtime/node_modules/@metro-labs/telegram-bot/src/accounts.ts +7 -41
  326. package/runtime/node_modules/@metro-labs/telegram-bot/src/actions.ts +22 -77
  327. package/runtime/node_modules/@metro-labs/telegram-bot/src/attachments.ts +2 -2
  328. package/runtime/node_modules/@metro-labs/telegram-bot/src/format.ts +46 -48
  329. package/runtime/node_modules/@metro-labs/telegram-bot/src/index.ts +15 -15
  330. package/runtime/node_modules/@metro-labs/telegram-bot/src/media-actions.ts +6 -82
  331. package/runtime/node_modules/@metro-labs/telegram-bot/src/members.ts +1 -1
  332. package/runtime/node_modules/@metro-labs/telegram-bot/src/profile.ts +85 -0
  333. package/runtime/node_modules/@metro-labs/telegram-bot/src/station.ts +5 -1
  334. package/runtime/node_modules/@metro-labs/telegram-bot/src/types.ts +20 -12
  335. package/runtime/node_modules/@metro-labs/threema/package.json +26 -0
  336. package/runtime/node_modules/@metro-labs/threema/src/accounts.ts +96 -0
  337. package/runtime/node_modules/@metro-labs/threema/src/actions.ts +124 -0
  338. package/runtime/node_modules/@metro-labs/threema/src/api.ts +152 -0
  339. package/runtime/node_modules/@metro-labs/threema/src/crypto.ts +100 -0
  340. package/runtime/node_modules/@metro-labs/threema/src/files.ts +47 -0
  341. package/runtime/node_modules/@metro-labs/threema/src/format.ts +164 -0
  342. package/runtime/node_modules/@metro-labs/threema/src/groups.ts +96 -0
  343. package/runtime/node_modules/@metro-labs/threema/src/ids.ts +21 -0
  344. package/runtime/node_modules/@metro-labs/threema/src/inbound.ts +87 -0
  345. package/runtime/node_modules/@metro-labs/threema/src/index.ts +24 -0
  346. package/runtime/node_modules/@metro-labs/threema/src/messages.ts +264 -0
  347. package/runtime/node_modules/@metro-labs/threema/src/outbound.ts +160 -0
  348. package/runtime/node_modules/@metro-labs/threema/src/station.ts +13 -0
  349. package/runtime/node_modules/@metro-labs/threema/src/verify.ts +117 -0
  350. package/runtime/node_modules/@metro-labs/webhook/package.json +1 -1
  351. package/runtime/node_modules/@metro-labs/webhook/src/station.ts +5 -8
  352. package/runtime/node_modules/@metro-labs/whatsapp/package.json +2 -5
  353. package/runtime/node_modules/@metro-labs/whatsapp/src/accounts.ts +6 -28
  354. package/runtime/node_modules/@metro-labs/whatsapp/src/ack.ts +1 -1
  355. package/runtime/node_modules/@metro-labs/whatsapp/src/actions.ts +54 -11
  356. package/runtime/node_modules/@metro-labs/whatsapp/src/attachments.ts +2 -2
  357. package/runtime/node_modules/@metro-labs/whatsapp/src/auth-state.ts +1 -1
  358. package/runtime/node_modules/@metro-labs/whatsapp/src/client.ts +86 -4
  359. package/runtime/node_modules/@metro-labs/whatsapp/src/format.ts +7 -58
  360. package/runtime/node_modules/@metro-labs/whatsapp/src/inbound.ts +11 -28
  361. package/runtime/node_modules/@metro-labs/whatsapp/src/index.ts +4 -37
  362. package/runtime/node_modules/@metro-labs/whatsapp/src/keys.ts +1 -1
  363. package/runtime/node_modules/@metro-labs/whatsapp/src/login.ts +1 -1
  364. package/runtime/node_modules/@metro-labs/whatsapp/src/media.ts +1 -1
  365. package/runtime/node_modules/@metro-labs/whatsapp/src/names.ts +75 -0
  366. package/runtime/node_modules/@metro-labs/whatsapp/src/parse.ts +44 -0
  367. package/runtime/node_modules/@metro-labs/whatsapp/src/resolve.ts +52 -0
  368. package/runtime/node_modules/@metro-labs/whatsapp/src/station.ts +16 -1
  369. package/runtime/node_modules/@metro-labs/whatsapp/src/token-store.ts +5 -9
  370. package/runtime/node_modules/@metro-labs/whatsapp/src/types.ts +0 -1
  371. package/runtime/node_modules/@metro-labs/xmtp/package.json +3 -2
  372. package/runtime/node_modules/@metro-labs/xmtp/src/accounts.ts +10 -20
  373. package/runtime/node_modules/@metro-labs/xmtp/src/actions-close.ts +2 -2
  374. package/runtime/node_modules/@metro-labs/xmtp/src/actions-conv.ts +35 -220
  375. package/runtime/node_modules/@metro-labs/xmtp/src/actions-meta.ts +40 -53
  376. package/runtime/node_modules/@metro-labs/xmtp/src/actions.ts +95 -222
  377. package/runtime/node_modules/@metro-labs/xmtp/src/attachments.ts +3 -3
  378. package/runtime/node_modules/@metro-labs/xmtp/src/call-leftovers.ts +48 -0
  379. package/runtime/node_modules/@metro-labs/xmtp/src/codecs.ts +95 -3
  380. package/runtime/node_modules/@metro-labs/xmtp/src/conv-helpers.ts +11 -7
  381. package/runtime/node_modules/@metro-labs/xmtp/src/delete-requests.ts +34 -0
  382. package/runtime/node_modules/@metro-labs/xmtp/src/emit-payloads.ts +37 -25
  383. package/runtime/node_modules/@metro-labs/xmtp/src/emit.ts +8 -18
  384. package/runtime/node_modules/@metro-labs/xmtp/src/frames.ts +178 -0
  385. package/runtime/node_modules/@metro-labs/xmtp/src/group-members.ts +1 -1
  386. package/runtime/node_modules/@metro-labs/xmtp/src/group.ts +2 -2
  387. package/runtime/node_modules/@metro-labs/xmtp/src/identity.ts +30 -16
  388. package/runtime/node_modules/@metro-labs/xmtp/src/index.ts +13 -20
  389. package/runtime/node_modules/@metro-labs/xmtp/src/labels.ts +57 -33
  390. package/runtime/node_modules/@metro-labs/xmtp/src/member-args.ts +1 -1
  391. package/runtime/node_modules/@metro-labs/xmtp/src/names.ts +61 -0
  392. package/runtime/node_modules/@metro-labs/xmtp/src/profile.ts +153 -0
  393. package/runtime/node_modules/@metro-labs/xmtp/src/resolve.ts +44 -0
  394. package/runtime/node_modules/@metro-labs/xmtp/src/sender.ts +112 -0
  395. package/runtime/node_modules/@metro-labs/xmtp/src/smart.ts +72 -0
  396. package/runtime/node_modules/@metro-labs/xmtp/src/station.ts +8 -2
  397. package/runtime/node_modules/@metro-labs/xmtp/src/tools-handlers.ts +22 -58
  398. package/runtime/node_modules/@metro-labs/xmtp/src/tools.ts +55 -48
  399. package/runtime/node_modules/@metro-labs/xmtp/src/transcribe.ts +4 -6
  400. package/runtime/node_modules/@metro-labs/xmtp/src/verify.ts +19 -5
  401. package/runtime/node_modules/@metro-labs/xmtp/src/wire.ts +14 -4
  402. package/runtime/runtime.json +1 -1
  403. package/runtime/server.ts +1 -0
  404. package/runtime/stations.json +40 -0
  405. package/dist/prompt.js +0 -61
  406. package/dist/store.js +0 -70
  407. package/runtime/node_modules/@metro-labs/discord-bot/src/voice-speak.ts +0 -195
  408. package/runtime/node_modules/@metro-labs/discord-bot/src/voice-transcribe.ts +0 -292
  409. package/runtime/node_modules/@metro-labs/discord-bot/src/voice.ts +0 -197
  410. package/runtime/node_modules/@metro-labs/discord-bot/src/wire.ts +0 -5
  411. package/runtime/node_modules/@metro-labs/mcp/package.json +0 -66
  412. package/runtime/node_modules/@metro-labs/mcp/src/channels/dedupe.ts +0 -24
  413. package/runtime/node_modules/@metro-labs/mcp/src/daemon/account-api.ts +0 -311
  414. package/runtime/node_modules/@metro-labs/mcp/src/daemon/agent-api.ts +0 -341
  415. package/runtime/node_modules/@metro-labs/mcp/src/daemon/api-http.ts +0 -129
  416. package/runtime/node_modules/@metro-labs/mcp/src/daemon/boot.ts +0 -320
  417. package/runtime/node_modules/@metro-labs/mcp/src/daemon/cli-pair-api.ts +0 -111
  418. package/runtime/node_modules/@metro-labs/mcp/src/daemon/cli-pair.ts +0 -20
  419. package/runtime/node_modules/@metro-labs/mcp/src/daemon/collection-api.ts +0 -202
  420. package/runtime/node_modules/@metro-labs/mcp/src/daemon/connector-json.ts +0 -31
  421. package/runtime/node_modules/@metro-labs/mcp/src/daemon/connector-tools.ts +0 -100
  422. package/runtime/node_modules/@metro-labs/mcp/src/daemon/connector-url.ts +0 -57
  423. package/runtime/node_modules/@metro-labs/mcp/src/daemon/connector-verify.ts +0 -333
  424. package/runtime/node_modules/@metro-labs/mcp/src/daemon/google-auth.ts +0 -164
  425. package/runtime/node_modules/@metro-labs/mcp/src/daemon/google-oauth.ts +0 -208
  426. package/runtime/node_modules/@metro-labs/mcp/src/daemon/identity.ts +0 -79
  427. package/runtime/node_modules/@metro-labs/mcp/src/daemon/oauth-pending.ts +0 -65
  428. package/runtime/node_modules/@metro-labs/mcp/src/daemon/pair-codes.ts +0 -58
  429. package/runtime/node_modules/@metro-labs/mcp/src/daemon/project-api.ts +0 -214
  430. package/runtime/node_modules/@metro-labs/mcp/src/daemon/run-api.ts +0 -125
  431. package/runtime/node_modules/@metro-labs/mcp/src/daemon/run-pair.ts +0 -18
  432. package/runtime/node_modules/@metro-labs/mcp/src/daemon/runtime-source.ts +0 -105
  433. package/runtime/node_modules/@metro-labs/mcp/src/daemon/session-apis.ts +0 -41
  434. package/runtime/node_modules/@metro-labs/mcp/src/daemon/session.ts +0 -218
  435. package/runtime/node_modules/@metro-labs/mcp/src/daemon/tunnel.ts +0 -169
  436. package/runtime/node_modules/@metro-labs/mcp/src/db/account-attach.ts +0 -91
  437. package/runtime/node_modules/@metro-labs/mcp/src/db/agent-admin.ts +0 -215
  438. package/runtime/node_modules/@metro-labs/mcp/src/db/agent-map.ts +0 -71
  439. package/runtime/node_modules/@metro-labs/mcp/src/db/client.ts +0 -37
  440. package/runtime/node_modules/@metro-labs/mcp/src/db/connector-collections.ts +0 -218
  441. package/runtime/node_modules/@metro-labs/mcp/src/db/connectors.ts +0 -329
  442. package/runtime/node_modules/@metro-labs/mcp/src/db/projects.ts +0 -300
  443. package/runtime/node_modules/@metro-labs/mcp/src/db/runtime-admin.ts +0 -31
  444. package/runtime/node_modules/@metro-labs/mcp/src/db/runtimes.ts +0 -105
  445. package/runtime/node_modules/@metro-labs/mcp/src/db/schema.ts +0 -131
  446. package/runtime/node_modules/@metro-labs/mcp/src/db/token-carry.ts +0 -45
  447. package/runtime/node_modules/@metro-labs/mcp/src/db/users.ts +0 -57
  448. package/runtime/node_modules/@metro-labs/mcp/src/db/whatsapp-login.ts +0 -18
  449. package/runtime/node_modules/@metro-labs/mcp/src/mcp/channel-owner.ts +0 -29
  450. package/runtime/node_modules/@metro-labs/mcp/src/mcp/frame-scope.ts +0 -21
  451. package/runtime/node_modules/@metro-labs/mcp/src/mcp/permission-relay.ts +0 -66
  452. package/runtime/node_modules/@metro-labs/mcp/src/mcp/request-identity.ts +0 -73
  453. package/runtime/node_modules/@metro-labs/mcp/src/mcp/session-registry.ts +0 -172
  454. package/runtime/node_modules/@metro-labs/mcp/src/mcp/session-route.ts +0 -43
  455. package/runtime/node_modules/@metro-labs/mcp/src/monitor/api.ts +0 -240
  456. package/runtime/node_modules/@metro-labs/mcp/src/server.ts +0 -2
  457. package/runtime/node_modules/@metro-labs/mcp/src/stations/account-store.ts +0 -80
  458. package/runtime/node_modules/@metro-labs/mcp/src/stations/messaging-normalize.ts +0 -88
  459. package/runtime/node_modules/@metro-labs/telegram/src/normalize.ts +0 -22
  460. package/runtime/node_modules/@metro-labs/telegram/src/wire.ts +0 -1
  461. package/runtime/node_modules/@metro-labs/telegram-bot/src/wire.ts +0 -3
  462. package/runtime/node_modules/@metro-labs/whatsapp/src/normalize.ts +0 -22
  463. package/runtime/node_modules/@metro-labs/whatsapp/src/wire.ts +0 -5
  464. package/runtime/node_modules/@metro-labs/xmtp/src/actions-push.ts +0 -87
  465. package/runtime/node_modules/@metro-labs/xmtp/src/emit-core.ts +0 -55
  466. package/runtime/node_modules/@metro-labs/xmtp/src/push.ts +0 -349
  467. /package/runtime/node_modules/@metro-labs/{mcp/src/daemon → core/src}/log.ts +0 -0
  468. /package/runtime/node_modules/@metro-labs/{mcp/src/mcp → core/src}/str.ts +0 -0
  469. /package/runtime/node_modules/@metro-labs/{mcp/src/daemon → core/src}/train-error.ts +0 -0
  470. /package/runtime/node_modules/@metro-labs/{mcp → daemon}/src/channels/webhook-note.ts +0 -0
  471. /package/runtime/node_modules/@metro-labs/{mcp → daemon}/src/mcp/raw-get-stream.ts +0 -0
  472. /package/runtime/node_modules/@metro-labs/{mcp/src/daemon → http/src}/api-error.ts +0 -0
  473. /package/runtime/node_modules/@metro-labs/{mcp/src/daemon → http/src}/cors.ts +0 -0
@@ -1,91 +0,0 @@
1
- import { isUniqueViolation } from './users.js';
2
- import { and, eq, sql } from 'drizzle-orm';
3
- import { newId } from './ids.js';
4
- import { getDb } from './client.js';
5
- import { AgentAdminError, ownedAgentOrThrow, } from './agent-admin.js';
6
- import { stations, STATIONS, type StationName } from './schema.js';
7
-
8
- const ACCOUNT_ID_RE = /^[A-Za-z0-9][A-Za-z0-9_-]{0,63}$/;
9
- const ID_ATTEMPTS = 5;
10
-
11
- export interface AccountRef {
12
- agentId: string;
13
- station: StationName;
14
- accountId: string;
15
- }
16
-
17
- export function isStationName(raw: unknown): raw is StationName {
18
- return (
19
- typeof raw === 'string' && (STATIONS as readonly string[]).includes(raw)
20
- );
21
- }
22
-
23
- export function parseAccountId(raw: string): string | null {
24
- return ACCOUNT_ID_RE.test(raw) ? raw : null;
25
- }
26
-
27
- async function assertTokenFree(
28
- station: StationName,
29
- token: string,
30
- ): Promise<void> {
31
- const rows = await getDb()
32
- .select({ id: stations.id })
33
- .from(stations)
34
- .where(
35
- and(
36
- eq(stations.station, station),
37
- sql`${stations.config}->>'token' = ${token}`,
38
- ),
39
- );
40
- if (rows.length > 0)
41
- throw new AgentAdminError(
42
- 'that bot token is already attached to a Metro account',
43
- 409,
44
- );
45
- }
46
-
47
- export async function attachAccountToAgent(
48
- email: string,
49
- agentId: string,
50
- station: StationName,
51
- config: Record<string, unknown>,
52
- ): Promise<AccountRef> {
53
- const { agent } = await ownedAgentOrThrow(email, agentId);
54
- const token = config.token;
55
- if (typeof token === 'string') await assertTokenFree(station, token);
56
- const db = getDb();
57
- for (let attempt = 0; attempt < ID_ATTEMPTS; attempt++) {
58
- const accountId = newId();
59
- try {
60
- await db
61
- .insert(stations)
62
- .values({ id: accountId, agentId: agent.id, station, config });
63
- return { agentId: agent.id, station, accountId };
64
- } catch (err) {
65
- if (!isUniqueViolation(err)) throw err;
66
- }
67
- }
68
- throw new AgentAdminError('could not allocate a free account id', 500);
69
- }
70
-
71
- export async function detachAccountFromAgent(
72
- email: string,
73
- agentId: string,
74
- station: StationName,
75
- accountId: string,
76
- ): Promise<AccountRef> {
77
- const { agent } = await ownedAgentOrThrow(email, agentId);
78
- const gone = await getDb()
79
- .delete(stations)
80
- .where(
81
- and(
82
- eq(stations.agentId, agent.id),
83
- eq(stations.station, station),
84
- eq(stations.id, accountId),
85
- ),
86
- )
87
- .returning({ id: stations.id });
88
- if (gone.length === 0)
89
- throw new AgentAdminError('no such account on this agent', 404);
90
- return { agentId: agent.id, station, accountId };
91
- }
@@ -1,215 +0,0 @@
1
- import { randomBytes } from 'node:crypto';
2
- import { and, asc, eq, inArray } from 'drizzle-orm';
3
- import { ApiError } from '../daemon/api-error.js';
4
- import { getDb } from './client.js';
5
- import { registerKey, rotateAgentKey, unregisterAgentKey } from './key-map.js';
6
- import { newId, parseId } from './ids.js';
7
- import { agents, stations } from './schema.js';
8
- import { isUniqueViolation } from './users.js';
9
- import { projectIdOrThrow } from './projects.js';
10
-
11
- export const AGENT_NAME_RE = /^[A-Za-z0-9][A-Za-z0-9_-]{1,31}$/;
12
- const KEY_ATTEMPTS = 5;
13
-
14
- export class AgentAdminError extends ApiError {}
15
-
16
- export interface AgentSummary {
17
- id: string;
18
- name: string;
19
- owned: boolean;
20
- key: string | null;
21
- }
22
-
23
- export interface CreatedAgent {
24
- id: string;
25
- name: string;
26
- key: string;
27
- }
28
-
29
- export interface OwnedAgent {
30
- id: string;
31
- name: string;
32
- }
33
-
34
- export type DeletedAgent = OwnedAgent;
35
-
36
- export interface ResetAgentKey extends OwnedAgent {
37
- key: string;
38
- }
39
-
40
- export function normalizeAgentName(raw: unknown): string {
41
- const name = typeof raw === 'string' ? raw.trim() : '';
42
- if (!AGENT_NAME_RE.test(name))
43
- throw new AgentAdminError(
44
- 'name must be 2-32 characters of A-Z, a-z, 0-9, - or _, starting with a letter or digit',
45
- 400,
46
- );
47
- return name;
48
- }
49
-
50
- export function newApiKey(): string {
51
- return `mk_${randomBytes(32).toString('base64url')}`;
52
- }
53
-
54
- const agentPin = (): string => process.env.METRO_AGENT?.trim() ?? '';
55
-
56
- export function servesEveryAgent(): boolean {
57
- return agentPin() === '';
58
- }
59
-
60
- export function daemonServesAgent(id: string): boolean {
61
- const pin = agentPin();
62
- return pin === '' || pin === id;
63
- }
64
-
65
- interface AgentRow {
66
- id: string;
67
- name: string;
68
- projectId: string;
69
- }
70
-
71
- interface KeyRow {
72
- agentId: string;
73
- key: string | null;
74
- }
75
-
76
- export function toAgentSummaries(
77
- rows: AgentRow[],
78
- keyRows: KeyRow[],
79
- ): AgentSummary[] {
80
- return rows.map((r) => ({
81
- id: r.id,
82
- name: r.name,
83
- owned: true,
84
- key: keyRows.find((k) => k.agentId === r.id)?.key ?? null,
85
- }));
86
- }
87
-
88
- async function selectKeyRows(ids: string[]): Promise<KeyRow[]> {
89
- if (ids.length === 0) return [];
90
- return getDb()
91
- .select({ agentId: agents.id, key: agents.key })
92
- .from(agents)
93
- .where(inArray(agents.id, ids));
94
- }
95
-
96
- export async function listAgentsForEmail(
97
- email: string,
98
- project: string,
99
- ): Promise<AgentSummary[]> {
100
- const projectId = await projectIdOrThrow(email, project);
101
- const rows = await getDb()
102
- .select({ id: agents.id, name: agents.name, projectId: agents.projectId })
103
- .from(agents)
104
- .where(eq(agents.projectId, projectId))
105
- .orderBy(asc(agents.name), asc(agents.id));
106
- if (rows.length === 0) return [];
107
- const keyRows = await selectKeyRows(rows.map((r) => r.id));
108
- return toAgentSummaries(rows, keyRows);
109
- }
110
-
111
- async function insertAgent(
112
- projectId: string,
113
- name: string,
114
- key: string,
115
- ): Promise<string> {
116
- const inserted = await getDb()
117
- .insert(agents)
118
- .values({ id: newId(), name, projectId, key })
119
- .returning({ id: agents.id });
120
- const id = inserted[0]?.id;
121
- if (id === undefined)
122
- throw new AgentAdminError('agent insert returned no id', 500);
123
- return id;
124
- }
125
-
126
- export async function createAgentForEmail(
127
- email: string,
128
- project: string,
129
- rawName: string,
130
- ): Promise<CreatedAgent> {
131
- const name = normalizeAgentName(rawName);
132
- const key = newApiKey();
133
- const id = await insertAgent(await projectIdOrThrow(email, project), name, key);
134
- if (servesEveryAgent()) registerKey(key, id);
135
- return { id, name, key };
136
- }
137
-
138
- export function parseAgentId(raw: string): string | null {
139
- return parseId(raw);
140
- }
141
-
142
- interface Deletable {
143
- agent: DeletedAgent;
144
- projectId: string;
145
- }
146
-
147
- export async function ownedAgentOrThrow(
148
- email: string,
149
- id: string,
150
- ): Promise<Deletable> {
151
- const rows = await getDb().select().from(agents).where(eq(agents.id, id));
152
- const row = rows[0];
153
- const missing = new AgentAdminError('no such agent', 404);
154
- if (!row) throw missing;
155
- try {
156
- await projectIdOrThrow(email, row.projectId);
157
- } catch {
158
- throw missing;
159
- }
160
- return { agent: { id: row.id, name: row.name }, projectId: row.projectId };
161
- }
162
-
163
- async function writeNewKey(id: string, projectId: string): Promise<string> {
164
- for (let attempt = 0; attempt < KEY_ATTEMPTS; attempt += 1) {
165
- const key = newApiKey();
166
- try {
167
- const changed = await getDb()
168
- .update(agents)
169
- .set({ key })
170
- .where(and(eq(agents.id, id), eq(agents.projectId, projectId)))
171
- .returning({ id: agents.id });
172
- if (changed.length === 0)
173
- throw new AgentAdminError('no such agent', 404);
174
- return key;
175
- } catch (err) {
176
- if (!isUniqueViolation(err)) throw err;
177
- }
178
- }
179
- throw new AgentAdminError('could not allocate a free api key', 500);
180
- }
181
-
182
- export async function resetAgentKeyForEmail(
183
- email: string,
184
- id: string,
185
- ): Promise<ResetAgentKey> {
186
- const { agent, projectId } = await ownedAgentOrThrow(email, id);
187
- const key = await writeNewKey(agent.id, projectId);
188
- rotateAgentKey(agent.id, daemonServesAgent(agent.id) ? key : null);
189
- return { id: agent.id, name: agent.name, key };
190
- }
191
-
192
- export async function deleteAgentForEmail(
193
- email: string,
194
- id: string,
195
- ): Promise<DeletedAgent> {
196
- const { agent, projectId } = await ownedAgentOrThrow(email, id);
197
- await getDb().transaction(async (tx) => {
198
- const attached = await tx
199
- .select({ id: stations.id })
200
- .from(stations)
201
- .where(eq(stations.agentId, id));
202
- if (attached.length > 0)
203
- throw new AgentAdminError(
204
- `agent '${agent.name}' still has ${attached.length} station account(s) attached — an operator must remove them first`,
205
- 409,
206
- );
207
- const gone = await tx
208
- .delete(agents)
209
- .where(and(eq(agents.id, id), eq(agents.projectId, projectId)))
210
- .returning({ id: agents.id });
211
- if (gone.length === 0) throw new AgentAdminError('no such agent', 404);
212
- });
213
- unregisterAgentKey(id);
214
- return agent;
215
- }
@@ -1,71 +0,0 @@
1
- export type AgentMap = Record<string, string>;
2
- export type AgentNameMap = Record<string, string>;
3
- export type AllowlistMap = Record<string, string[]>;
4
-
5
- const mapKey = (station: string, accountId: string): string =>
6
- `${station}/${accountId}`;
7
-
8
- let agentMap: AgentMap = {};
9
- let agentNames: AgentNameMap = {};
10
- let allowlistMap: AllowlistMap = {};
11
-
12
- export function setAgentMap(map: AgentMap, names: AgentNameMap): void {
13
- agentMap = map;
14
- agentNames = names;
15
- }
16
-
17
- export function setAllowlistMap(map: AllowlistMap): void {
18
- allowlistMap = map;
19
- }
20
-
21
- export function accountFromLine(
22
- line: string,
23
- ): { station: string; accountId: string } | undefined {
24
- const parts = line.split('/');
25
- const station = parts[2];
26
- const accountId = parts[3];
27
- if (!station || !accountId) return undefined;
28
- return { station, accountId };
29
- }
30
-
31
- export function agentIdForAccount(
32
- station: string,
33
- accountId: string,
34
- ): string | undefined {
35
- return agentMap[mapKey(station, accountId)];
36
- }
37
-
38
- export function agentIdForLine(line: string): string | undefined {
39
- const a = accountFromLine(line);
40
- return a ? agentIdForAccount(a.station, a.accountId) : undefined;
41
- }
42
-
43
- export function agentForLine(line: string): string | undefined {
44
- const id = agentIdForLine(line);
45
- return id === undefined ? undefined : agentNames[id];
46
- }
47
-
48
- export function stationAgentIds(station: string): string[] {
49
- const prefix = `${station}/`;
50
- return Object.entries(agentMap)
51
- .filter(([key]) => key.startsWith(prefix))
52
- .map(([, id]) => id);
53
- }
54
-
55
- export function allowlistForLine(line: string): string[] | undefined {
56
- const a = accountFromLine(line);
57
- return a ? allowlistMap[mapKey(a.station, a.accountId)] : undefined;
58
- }
59
-
60
- export function senderMatchesAllowlist(
61
- allowlist: string[],
62
- from: string,
63
- ): boolean {
64
- if (allowlist.length === 0 || allowlist.includes('*')) return true;
65
- const f = (from ?? '').toLowerCase();
66
- const id = f.split('/').pop() ?? f;
67
- return allowlist.some((a) => {
68
- const v = a.toLowerCase();
69
- return v === f || v === id;
70
- });
71
- }
@@ -1,37 +0,0 @@
1
- import { drizzle, type PostgresJsDatabase } from 'drizzle-orm/postgres-js';
2
- import postgres from 'postgres';
3
- import { log } from '../daemon/log.js';
4
- import * as schema from './schema.js';
5
-
6
- export type Db = PostgresJsDatabase<typeof schema>;
7
-
8
- let sql: ReturnType<typeof postgres> | null = null;
9
- let db: Db | null = null;
10
-
11
- export function databaseUrl(): string | undefined {
12
- const url = process.env.DATABASE_URL?.trim();
13
- if (!url) return undefined;
14
- return url;
15
- }
16
-
17
- export function getDb(): Db {
18
- const url = databaseUrl();
19
- if (!url) throw new Error('DATABASE_URL is not set');
20
- if (!db) {
21
- sql = postgres(url, {
22
- max: 4,
23
- prepare: false,
24
- onnotice: (notice) => {
25
- log.debug({ notice: notice.message }, 'postgres notice');
26
- },
27
- });
28
- db = drizzle(sql, { schema });
29
- }
30
- return db;
31
- }
32
-
33
- export async function closeDb(): Promise<void> {
34
- if (sql) await sql.end({ timeout: 5 });
35
- sql = null;
36
- db = null;
37
- }
@@ -1,218 +0,0 @@
1
- import { isUniqueViolation } from './users.js';
2
- import { projectIdOrThrow } from './projects.js';
3
- import { and, asc, eq, inArray, ne } from 'drizzle-orm';
4
- import { getDb } from './client.js';
5
- import { newId } from './ids.js';
6
- import { ConnectorError, connectorName } from './connector-config.js';
7
- import { collectionItems, collections, connectors } from './schema.js';
8
-
9
- export interface ConnectorCollectionRow {
10
- id: string;
11
- name: string;
12
- connectorIds: string[];
13
- }
14
-
15
- interface CollectionRow {
16
- id: string;
17
- projectId: string;
18
- name: string;
19
- }
20
-
21
- const missing = (): ConnectorError =>
22
- new ConnectorError('no such collection', 404);
23
-
24
- const duplicate = (name: string): ConnectorError =>
25
- new ConnectorError(`you already have a collection named '${name}'`, 409);
26
-
27
- const nameClash = (name: string, collection: string): ConnectorError =>
28
- new ConnectorError(
29
- `the collection '${collection}' already has a connector named '${name}'`,
30
- 409,
31
- );
32
-
33
- async function collidingCollection(
34
- collectionIds: string[],
35
- name: string,
36
- exceptConnectorId: string,
37
- ): Promise<string | null> {
38
- if (collectionIds.length === 0) return null;
39
- const rows = await getDb()
40
- .select({ collection: collections.name })
41
- .from(collectionItems)
42
- .innerJoin(connectors, eq(connectors.id, collectionItems.connectorId))
43
- .innerJoin(collections, eq(collections.id, collectionItems.collectionId))
44
- .where(
45
- and(
46
- inArray(collectionItems.collectionId, collectionIds),
47
- eq(connectors.name, name),
48
- ne(connectors.id, exceptConnectorId),
49
- ),
50
- )
51
- .limit(1);
52
- return rows[0]?.collection ?? null;
53
- }
54
-
55
- export async function assertRenameFreeOfClash(
56
- connectorId: string,
57
- name: string,
58
- ): Promise<void> {
59
- const rows = await getDb()
60
- .select({ collectionId: collectionItems.collectionId })
61
- .from(collectionItems)
62
- .where(eq(collectionItems.connectorId, connectorId));
63
- const clash = await collidingCollection(
64
- rows.map((r) => r.collectionId),
65
- name,
66
- connectorId,
67
- );
68
- if (clash !== null) throw nameClash(name, clash);
69
- }
70
-
71
- async function ownedCollectionOrThrow(
72
- email: string,
73
- id: string,
74
- ): Promise<CollectionRow> {
75
- const rows = await getDb()
76
- .select()
77
- .from(collections)
78
- .where(eq(collections.id, id));
79
- const row = rows[0];
80
- if (row === undefined) throw missing();
81
- try {
82
- await projectIdOrThrow(email, row.projectId);
83
- } catch {
84
- throw missing();
85
- }
86
- return row;
87
- }
88
-
89
- async function itemsOf(collectionId: string): Promise<string[]> {
90
- const rows = await getDb()
91
- .select({ connectorId: collectionItems.connectorId })
92
- .from(collectionItems)
93
- .where(eq(collectionItems.collectionId, collectionId))
94
- .orderBy(asc(collectionItems.id));
95
- return rows.map((r) => r.connectorId);
96
- }
97
-
98
- async function withItems(row: CollectionRow): Promise<ConnectorCollectionRow> {
99
- return { id: row.id, name: row.name, connectorIds: await itemsOf(row.id) };
100
- }
101
-
102
- export async function listCollectionsForEmail(
103
- email: string,
104
- project: string,
105
- ): Promise<ConnectorCollectionRow[]> {
106
- const projectId = await projectIdOrThrow(email, project);
107
- const rows = await getDb()
108
- .select()
109
- .from(collections)
110
- .where(eq(collections.projectId, projectId))
111
- .orderBy(asc(collections.id));
112
- return Promise.all(rows.map(withItems));
113
- }
114
-
115
- export async function getCollectionForEmail(
116
- email: string,
117
- id: string,
118
- ): Promise<ConnectorCollectionRow> {
119
- return withItems(await ownedCollectionOrThrow(email, id));
120
- }
121
-
122
- export async function createCollectionForEmail(
123
- email: string,
124
- project: string,
125
- raw: string,
126
- ): Promise<ConnectorCollectionRow> {
127
- const name = connectorName(raw);
128
- const projectId = await projectIdOrThrow(email, project);
129
- try {
130
- const rows = await getDb()
131
- .insert(collections)
132
- .values({ id: newId(), projectId, name })
133
- .returning();
134
- const row = rows[0];
135
- if (row === undefined)
136
- throw new ConnectorError('collection insert returned no row', 500);
137
- return { id: row.id, name: row.name, connectorIds: [] };
138
- } catch (err) {
139
- if (!isUniqueViolation(err)) throw err;
140
- throw duplicate(name);
141
- }
142
- }
143
-
144
- export async function renameCollectionForEmail(
145
- email: string,
146
- id: string,
147
- raw: string,
148
- ): Promise<ConnectorCollectionRow> {
149
- const name = connectorName(raw);
150
- const row = await ownedCollectionOrThrow(email, id);
151
- try {
152
- await getDb()
153
- .update(collections)
154
- .set({ name })
155
- .where(eq(collections.id, row.id));
156
- } catch (err) {
157
- if (!isUniqueViolation(err)) throw err;
158
- throw duplicate(name);
159
- }
160
- return withItems({ ...row, name });
161
- }
162
-
163
- export async function deleteCollectionForEmail(
164
- email: string,
165
- id: string,
166
- ): Promise<{ id: string; name: string }> {
167
- const row = await ownedCollectionOrThrow(email, id);
168
- await getDb().delete(collections).where(eq(collections.id, row.id));
169
- return { id: row.id, name: row.name };
170
- }
171
-
172
- async function connectorNameIn(
173
- projectId: string,
174
- connectorId: string,
175
- ): Promise<string | null> {
176
- const rows = await getDb()
177
- .select({ name: connectors.name })
178
- .from(connectors)
179
- .where(and(eq(connectors.id, connectorId), eq(connectors.projectId, projectId)));
180
- return rows[0]?.name ?? null;
181
- }
182
-
183
- export async function addToCollectionForEmail(
184
- email: string,
185
- id: string,
186
- connectorId: string,
187
- ): Promise<ConnectorCollectionRow> {
188
- const row = await ownedCollectionOrThrow(email, id);
189
- const name = await connectorNameIn(row.projectId, connectorId);
190
- if (name === null) throw new ConnectorError('no such connector', 404);
191
- const clash = await collidingCollection([row.id], name, connectorId);
192
- if (clash !== null) throw nameClash(name, clash);
193
- try {
194
- await getDb()
195
- .insert(collectionItems)
196
- .values({ id: newId(), collectionId: row.id, connectorId });
197
- } catch (err) {
198
- if (!isUniqueViolation(err)) throw err;
199
- }
200
- return withItems(row);
201
- }
202
-
203
- export async function removeFromCollectionForEmail(
204
- email: string,
205
- id: string,
206
- connectorId: string,
207
- ): Promise<ConnectorCollectionRow> {
208
- const row = await ownedCollectionOrThrow(email, id);
209
- await getDb()
210
- .delete(collectionItems)
211
- .where(
212
- and(
213
- eq(collectionItems.collectionId, row.id),
214
- eq(collectionItems.connectorId, connectorId),
215
- ),
216
- );
217
- return withItems(row);
218
- }