agent-relay 2.0.21 → 2.0.23

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 (412) hide show
  1. package/bin/relay-pty-linux-arm64 +0 -0
  2. package/dist/src/cli/index.d.ts +3 -3
  3. package/dist/src/cli/index.js +31 -100
  4. package/package.json +22 -29
  5. package/packages/api-types/package.json +1 -1
  6. package/packages/bridge/package.json +8 -8
  7. package/packages/cli-tester/package.json +1 -1
  8. package/packages/cloud/dist/server.js +25 -4
  9. package/packages/cloud/package.json +6 -6
  10. package/packages/config/package.json +2 -2
  11. package/packages/continuity/package.json +1 -1
  12. package/packages/daemon/dist/orchestrator.js +21 -1
  13. package/packages/daemon/dist/router.d.ts +5 -0
  14. package/packages/daemon/dist/router.js +31 -0
  15. package/packages/daemon/dist/server.d.ts +5 -0
  16. package/packages/daemon/dist/server.js +131 -1
  17. package/packages/daemon/package.json +12 -12
  18. package/packages/hooks/package.json +4 -4
  19. package/packages/mcp/dist/client.d.ts +15 -0
  20. package/packages/mcp/dist/client.js +9 -0
  21. package/packages/mcp/dist/server.js +13 -1
  22. package/packages/mcp/dist/tools/index.d.ts +2 -0
  23. package/packages/mcp/dist/tools/index.js +2 -0
  24. package/packages/mcp/dist/tools/relay-connected.d.ts +17 -0
  25. package/packages/mcp/dist/tools/relay-connected.js +40 -0
  26. package/packages/mcp/dist/tools/relay-remove-agent.d.ts +20 -0
  27. package/packages/mcp/dist/tools/relay-remove-agent.js +50 -0
  28. package/packages/mcp/package.json +2 -2
  29. package/packages/memory/package.json +2 -2
  30. package/packages/policy/package.json +2 -2
  31. package/packages/protocol/dist/types.d.ts +46 -1
  32. package/packages/protocol/package.json +1 -1
  33. package/packages/resiliency/package.json +1 -1
  34. package/packages/sdk/dist/client.d.ts +22 -1
  35. package/packages/sdk/dist/client.js +31 -0
  36. package/packages/sdk/dist/protocol/index.d.ts +1 -1
  37. package/packages/sdk/dist/protocol/types.d.ts +35 -1
  38. package/packages/sdk/package.json +2 -2
  39. package/packages/spawner/package.json +1 -1
  40. package/packages/state/package.json +1 -1
  41. package/packages/storage/dist/adapter.d.ts +4 -0
  42. package/packages/storage/dist/sqlite-adapter.d.ts +10 -0
  43. package/packages/storage/dist/sqlite-adapter.js +26 -0
  44. package/packages/storage/package.json +2 -2
  45. package/packages/telemetry/package.json +1 -1
  46. package/packages/trajectory/package.json +2 -2
  47. package/packages/user-directory/package.json +2 -2
  48. package/packages/utils/dist/update-checker.js +4 -0
  49. package/packages/utils/package.json +1 -1
  50. package/packages/wrapper/package.json +6 -6
  51. package/deploy/workspace/codex.config.toml +0 -20
  52. package/deploy/workspace/entrypoint-browser.sh +0 -118
  53. package/deploy/workspace/entrypoint.sh +0 -612
  54. package/deploy/workspace/gh-credential-relay +0 -90
  55. package/deploy/workspace/gh-relay +0 -156
  56. package/deploy/workspace/git-credential-relay +0 -330
  57. package/deploy/workspace/git-credential-relay.test.sh +0 -230
  58. package/dist/dashboard/out/404.html +0 -1
  59. package/dist/dashboard/out/_next/static/7MZPqYkVGw3EGzVBkVmY9/_buildManifest.js +0 -1
  60. package/dist/dashboard/out/_next/static/7MZPqYkVGw3EGzVBkVmY9/_ssgManifest.js +0 -1
  61. package/dist/dashboard/out/_next/static/chunks/116-a883fca163f3a5bc.js +0 -1
  62. package/dist/dashboard/out/_next/static/chunks/117-c8afed19e821a35d.js +0 -2
  63. package/dist/dashboard/out/_next/static/chunks/282-980c2eb8fff20123.js +0 -1
  64. package/dist/dashboard/out/_next/static/chunks/320-a6304232cd0ee2ce.js +0 -1
  65. package/dist/dashboard/out/_next/static/chunks/532-bace199897eeab37.js +0 -9
  66. package/dist/dashboard/out/_next/static/chunks/631-16b905e5920f9b59.js +0 -1
  67. package/dist/dashboard/out/_next/static/chunks/648-acb2ff9f77cbfbd3.js +0 -1
  68. package/dist/dashboard/out/_next/static/chunks/766-2aea80818f7eb0d8.js +0 -1
  69. package/dist/dashboard/out/_next/static/chunks/83-26d2bde54616ee90.js +0 -1
  70. package/dist/dashboard/out/_next/static/chunks/847-f1f467060f32afff.js +0 -1
  71. package/dist/dashboard/out/_next/static/chunks/891-5cb1513eeb97a891.js +0 -1
  72. package/dist/dashboard/out/_next/static/chunks/app/_not-found/page-60501fddbafba9dc.js +0 -1
  73. package/dist/dashboard/out/_next/static/chunks/app/app/onboarding/page-9914652442f7e4fb.js +0 -1
  74. package/dist/dashboard/out/_next/static/chunks/app/app/page-366fb7c078d4e9e0.js +0 -1
  75. package/dist/dashboard/out/_next/static/chunks/app/cloud/link/page-fa1d5842aa90e8a6.js +0 -1
  76. package/dist/dashboard/out/_next/static/chunks/app/complete-profile/page-dd64bbdf66b639cd.js +0 -1
  77. package/dist/dashboard/out/_next/static/chunks/app/connect-repos/page-113060009ef35bc2.js +0 -1
  78. package/dist/dashboard/out/_next/static/chunks/app/history/page-9965d2483011b846.js +0 -1
  79. package/dist/dashboard/out/_next/static/chunks/app/layout-6b91e33784c20610.js +0 -1
  80. package/dist/dashboard/out/_next/static/chunks/app/login/page-435eceb0073be027.js +0 -1
  81. package/dist/dashboard/out/_next/static/chunks/app/metrics/page-1e37ef8e73940b40.js +0 -1
  82. package/dist/dashboard/out/_next/static/chunks/app/page-8119d4246743574e.js +0 -1
  83. package/dist/dashboard/out/_next/static/chunks/app/pricing/page-9db3ebdfa567a7c9.js +0 -1
  84. package/dist/dashboard/out/_next/static/chunks/app/providers/page-ecb16ffd3b36262b.js +0 -1
  85. package/dist/dashboard/out/_next/static/chunks/app/providers/setup/[provider]/page-4dbe33f0f7691b7c.js +0 -1
  86. package/dist/dashboard/out/_next/static/chunks/app/signup/page-c7a0a28341365ae0.js +0 -1
  87. package/dist/dashboard/out/_next/static/chunks/e868780c-48e5f147c90a3a41.js +0 -18
  88. package/dist/dashboard/out/_next/static/chunks/fd9d1056-609918ca7b6280bb.js +0 -1
  89. package/dist/dashboard/out/_next/static/chunks/framework-f66176bb897dc684.js +0 -1
  90. package/dist/dashboard/out/_next/static/chunks/main-311c3db74dcfadb7.js +0 -1
  91. package/dist/dashboard/out/_next/static/chunks/main-app-fdbeb09028f57c9f.js +0 -1
  92. package/dist/dashboard/out/_next/static/chunks/pages/_app-72b849fbd24ac258.js +0 -1
  93. package/dist/dashboard/out/_next/static/chunks/pages/_error-7ba65e1336b92748.js +0 -1
  94. package/dist/dashboard/out/_next/static/chunks/polyfills-42372ed130431b0a.js +0 -1
  95. package/dist/dashboard/out/_next/static/chunks/webpack-1cdd8ed57114d5e1.js +0 -1
  96. package/dist/dashboard/out/_next/static/css/4034f236dd1a3178.css +0 -1
  97. package/dist/dashboard/out/_next/static/css/6892f8422896ef7a.css +0 -1
  98. package/dist/dashboard/out/alt-logos/agent-relay-logo-128.png +0 -0
  99. package/dist/dashboard/out/alt-logos/agent-relay-logo-256.png +0 -0
  100. package/dist/dashboard/out/alt-logos/agent-relay-logo-32.png +0 -0
  101. package/dist/dashboard/out/alt-logos/agent-relay-logo-512.png +0 -0
  102. package/dist/dashboard/out/alt-logos/agent-relay-logo-64.png +0 -0
  103. package/dist/dashboard/out/alt-logos/agent-relay-logo.svg +0 -45
  104. package/dist/dashboard/out/alt-logos/logo.svg +0 -38
  105. package/dist/dashboard/out/alt-logos/monogram-logo-128.png +0 -0
  106. package/dist/dashboard/out/alt-logos/monogram-logo-256.png +0 -0
  107. package/dist/dashboard/out/alt-logos/monogram-logo-32.png +0 -0
  108. package/dist/dashboard/out/alt-logos/monogram-logo-512.png +0 -0
  109. package/dist/dashboard/out/alt-logos/monogram-logo-64.png +0 -0
  110. package/dist/dashboard/out/alt-logos/monogram-logo.svg +0 -38
  111. package/dist/dashboard/out/app/onboarding.html +0 -1
  112. package/dist/dashboard/out/app/onboarding.txt +0 -7
  113. package/dist/dashboard/out/app.html +0 -1
  114. package/dist/dashboard/out/app.txt +0 -7
  115. package/dist/dashboard/out/apple-icon.png +0 -0
  116. package/dist/dashboard/out/cloud/link.html +0 -1
  117. package/dist/dashboard/out/cloud/link.txt +0 -7
  118. package/dist/dashboard/out/complete-profile.html +0 -5
  119. package/dist/dashboard/out/complete-profile.txt +0 -7
  120. package/dist/dashboard/out/connect-repos.html +0 -1
  121. package/dist/dashboard/out/connect-repos.txt +0 -7
  122. package/dist/dashboard/out/history.html +0 -1
  123. package/dist/dashboard/out/history.txt +0 -7
  124. package/dist/dashboard/out/index.html +0 -1
  125. package/dist/dashboard/out/index.txt +0 -7
  126. package/dist/dashboard/out/login.html +0 -5
  127. package/dist/dashboard/out/login.txt +0 -7
  128. package/dist/dashboard/out/metrics.html +0 -1
  129. package/dist/dashboard/out/metrics.txt +0 -7
  130. package/dist/dashboard/out/pricing.html +0 -13
  131. package/dist/dashboard/out/pricing.txt +0 -7
  132. package/dist/dashboard/out/providers/setup/claude.html +0 -1
  133. package/dist/dashboard/out/providers/setup/claude.txt +0 -8
  134. package/dist/dashboard/out/providers/setup/codex.html +0 -1
  135. package/dist/dashboard/out/providers/setup/codex.txt +0 -8
  136. package/dist/dashboard/out/providers/setup/cursor.html +0 -1
  137. package/dist/dashboard/out/providers/setup/cursor.txt +0 -8
  138. package/dist/dashboard/out/providers.html +0 -1
  139. package/dist/dashboard/out/providers.txt +0 -7
  140. package/dist/dashboard/out/signup.html +0 -6
  141. package/dist/dashboard/out/signup.txt +0 -7
  142. package/dist/src/dashboard-server/index.d.ts +0 -8
  143. package/dist/src/dashboard-server/index.js +0 -8
  144. package/packages/dashboard/README.md +0 -48
  145. package/packages/dashboard/dist/health-worker-manager.d.ts +0 -62
  146. package/packages/dashboard/dist/health-worker-manager.js +0 -144
  147. package/packages/dashboard/dist/health-worker.d.ts +0 -9
  148. package/packages/dashboard/dist/health-worker.js +0 -79
  149. package/packages/dashboard/dist/index.d.ts +0 -20
  150. package/packages/dashboard/dist/index.js +0 -19
  151. package/packages/dashboard/dist/metrics.d.ts +0 -105
  152. package/packages/dashboard/dist/metrics.js +0 -193
  153. package/packages/dashboard/dist/needs-attention.d.ts +0 -24
  154. package/packages/dashboard/dist/needs-attention.js +0 -78
  155. package/packages/dashboard/dist/server.d.ts +0 -25
  156. package/packages/dashboard/dist/server.js +0 -5270
  157. package/packages/dashboard/dist/start.d.ts +0 -6
  158. package/packages/dashboard/dist/start.js +0 -13
  159. package/packages/dashboard/dist/types/threading.d.ts +0 -8
  160. package/packages/dashboard/dist/types/threading.js +0 -2
  161. package/packages/dashboard/dist/user-bridge.d.ts +0 -154
  162. package/packages/dashboard/dist/user-bridge.js +0 -372
  163. package/packages/dashboard/package.json +0 -65
  164. package/packages/dashboard/ui/app/app/onboarding/page.tsx +0 -394
  165. package/packages/dashboard/ui/app/app/page.tsx +0 -667
  166. package/packages/dashboard/ui/app/apple-icon.png +0 -0
  167. package/packages/dashboard/ui/app/cloud/link/page.tsx +0 -464
  168. package/packages/dashboard/ui/app/complete-profile/page.tsx +0 -204
  169. package/packages/dashboard/ui/app/connect-repos/page.tsx +0 -410
  170. package/packages/dashboard/ui/app/favicon.png +0 -0
  171. package/packages/dashboard/ui/app/globals.css +0 -59
  172. package/packages/dashboard/ui/app/history/page.tsx +0 -658
  173. package/packages/dashboard/ui/app/layout.tsx +0 -25
  174. package/packages/dashboard/ui/app/login/page.tsx +0 -424
  175. package/packages/dashboard/ui/app/metrics/page.tsx +0 -751
  176. package/packages/dashboard/ui/app/page.tsx +0 -59
  177. package/packages/dashboard/ui/app/pricing/page.tsx +0 -7
  178. package/packages/dashboard/ui/app/providers/page.tsx +0 -193
  179. package/packages/dashboard/ui/app/providers/setup/[provider]/ProviderSetupClient.tsx +0 -148
  180. package/packages/dashboard/ui/app/providers/setup/[provider]/constants.ts +0 -35
  181. package/packages/dashboard/ui/app/providers/setup/[provider]/page.tsx +0 -42
  182. package/packages/dashboard/ui/app/signup/page.tsx +0 -533
  183. package/packages/dashboard/ui/index.ts +0 -49
  184. package/packages/dashboard/ui/landing/LandingPage.tsx +0 -713
  185. package/packages/dashboard/ui/landing/PricingPage.tsx +0 -559
  186. package/packages/dashboard/ui/landing/index.ts +0 -6
  187. package/packages/dashboard/ui/landing/styles.css +0 -2850
  188. package/packages/dashboard/ui/lib/agent-merge.ts +0 -35
  189. package/packages/dashboard/ui/lib/api.ts +0 -1155
  190. package/packages/dashboard/ui/lib/cloudApi.ts +0 -877
  191. package/packages/dashboard/ui/lib/colors.ts +0 -218
  192. package/packages/dashboard/ui/lib/hierarchy.ts +0 -242
  193. package/packages/dashboard/ui/lib/stuckDetection.ts +0 -142
  194. package/packages/dashboard/ui/next-env.d.ts +0 -5
  195. package/packages/dashboard/ui/next.config.js +0 -41
  196. package/packages/dashboard/ui/package-lock.json +0 -2882
  197. package/packages/dashboard/ui/package.json +0 -33
  198. package/packages/dashboard/ui/postcss.config.js +0 -5
  199. package/packages/dashboard/ui/react-components/ActivityFeed.tsx +0 -216
  200. package/packages/dashboard/ui/react-components/AddWorkspaceModal.tsx +0 -170
  201. package/packages/dashboard/ui/react-components/AgentCard.tsx +0 -587
  202. package/packages/dashboard/ui/react-components/AgentList.tsx +0 -411
  203. package/packages/dashboard/ui/react-components/AgentProfilePanel.tsx +0 -564
  204. package/packages/dashboard/ui/react-components/App.tsx +0 -3033
  205. package/packages/dashboard/ui/react-components/BillingPanel.tsx +0 -922
  206. package/packages/dashboard/ui/react-components/BillingResult.tsx +0 -447
  207. package/packages/dashboard/ui/react-components/BroadcastComposer.tsx +0 -690
  208. package/packages/dashboard/ui/react-components/ChannelAdminPanel.tsx +0 -773
  209. package/packages/dashboard/ui/react-components/ChannelBrowser.tsx +0 -385
  210. package/packages/dashboard/ui/react-components/ChannelChat.tsx +0 -261
  211. package/packages/dashboard/ui/react-components/ChannelSidebar.tsx +0 -399
  212. package/packages/dashboard/ui/react-components/CloudSessionProvider.tsx +0 -130
  213. package/packages/dashboard/ui/react-components/CommandPalette.tsx +0 -815
  214. package/packages/dashboard/ui/react-components/ConfirmationDialog.tsx +0 -133
  215. package/packages/dashboard/ui/react-components/ConversationHistory.tsx +0 -518
  216. package/packages/dashboard/ui/react-components/CoordinatorPanel.tsx +0 -944
  217. package/packages/dashboard/ui/react-components/DecisionQueue.tsx +0 -717
  218. package/packages/dashboard/ui/react-components/DirectMessageView.tsx +0 -164
  219. package/packages/dashboard/ui/react-components/FileAutocomplete.tsx +0 -368
  220. package/packages/dashboard/ui/react-components/FleetOverview.tsx +0 -278
  221. package/packages/dashboard/ui/react-components/LogViewer.tsx +0 -310
  222. package/packages/dashboard/ui/react-components/LogViewerPanel.tsx +0 -482
  223. package/packages/dashboard/ui/react-components/Logo.tsx +0 -284
  224. package/packages/dashboard/ui/react-components/MentionAutocomplete.tsx +0 -384
  225. package/packages/dashboard/ui/react-components/MessageComposer.tsx +0 -457
  226. package/packages/dashboard/ui/react-components/MessageList.tsx +0 -649
  227. package/packages/dashboard/ui/react-components/MessageSenderName.tsx +0 -91
  228. package/packages/dashboard/ui/react-components/MessageStatusIndicator.tsx +0 -142
  229. package/packages/dashboard/ui/react-components/NewConversationModal.tsx +0 -400
  230. package/packages/dashboard/ui/react-components/NotificationToast.tsx +0 -488
  231. package/packages/dashboard/ui/react-components/OnlineUsersIndicator.tsx +0 -164
  232. package/packages/dashboard/ui/react-components/Pagination.tsx +0 -124
  233. package/packages/dashboard/ui/react-components/PricingPlans.tsx +0 -386
  234. package/packages/dashboard/ui/react-components/ProjectList.tsx +0 -625
  235. package/packages/dashboard/ui/react-components/ProviderAuthFlow.tsx +0 -853
  236. package/packages/dashboard/ui/react-components/ProviderConnectionList.tsx +0 -378
  237. package/packages/dashboard/ui/react-components/ProvisioningProgress.tsx +0 -730
  238. package/packages/dashboard/ui/react-components/RepoAccessPanel.tsx +0 -549
  239. package/packages/dashboard/ui/react-components/ServerCard.tsx +0 -202
  240. package/packages/dashboard/ui/react-components/SessionExpiredModal.tsx +0 -128
  241. package/packages/dashboard/ui/react-components/SpawnModal.tsx +0 -804
  242. package/packages/dashboard/ui/react-components/TaskAssignmentUI.tsx +0 -375
  243. package/packages/dashboard/ui/react-components/TerminalProviderSetup.tsx +0 -608
  244. package/packages/dashboard/ui/react-components/ThemeProvider.tsx +0 -325
  245. package/packages/dashboard/ui/react-components/ThinkingIndicator.tsx +0 -231
  246. package/packages/dashboard/ui/react-components/ThreadList.tsx +0 -198
  247. package/packages/dashboard/ui/react-components/ThreadPanel.tsx +0 -346
  248. package/packages/dashboard/ui/react-components/TrajectoryViewer.tsx +0 -698
  249. package/packages/dashboard/ui/react-components/TypingIndicator.tsx +0 -69
  250. package/packages/dashboard/ui/react-components/UsageBanner.tsx +0 -231
  251. package/packages/dashboard/ui/react-components/UserProfilePanel.tsx +0 -233
  252. package/packages/dashboard/ui/react-components/WorkspaceContext.tsx +0 -107
  253. package/packages/dashboard/ui/react-components/WorkspaceSelector.tsx +0 -234
  254. package/packages/dashboard/ui/react-components/WorkspaceStatusIndicator.tsx +0 -370
  255. package/packages/dashboard/ui/react-components/XTermInteractive.tsx +0 -510
  256. package/packages/dashboard/ui/react-components/XTermLogViewer.tsx +0 -719
  257. package/packages/dashboard/ui/react-components/channels/ChannelDialogs.tsx +0 -1411
  258. package/packages/dashboard/ui/react-components/channels/ChannelHeader.tsx +0 -317
  259. package/packages/dashboard/ui/react-components/channels/ChannelMessageList.tsx +0 -463
  260. package/packages/dashboard/ui/react-components/channels/ChannelViewV1.tsx +0 -146
  261. package/packages/dashboard/ui/react-components/channels/MessageInput.tsx +0 -288
  262. package/packages/dashboard/ui/react-components/channels/SearchInput.tsx +0 -172
  263. package/packages/dashboard/ui/react-components/channels/SearchResults.tsx +0 -336
  264. package/packages/dashboard/ui/react-components/channels/api.ts +0 -697
  265. package/packages/dashboard/ui/react-components/channels/index.ts +0 -76
  266. package/packages/dashboard/ui/react-components/channels/mockApi.ts +0 -344
  267. package/packages/dashboard/ui/react-components/channels/types.ts +0 -566
  268. package/packages/dashboard/ui/react-components/hooks/index.ts +0 -57
  269. package/packages/dashboard/ui/react-components/hooks/useAgentLogs.ts +0 -394
  270. package/packages/dashboard/ui/react-components/hooks/useAgents.ts +0 -127
  271. package/packages/dashboard/ui/react-components/hooks/useBroadcastDedup.ts +0 -86
  272. package/packages/dashboard/ui/react-components/hooks/useChannelAdmin.ts +0 -329
  273. package/packages/dashboard/ui/react-components/hooks/useChannelBrowser.ts +0 -239
  274. package/packages/dashboard/ui/react-components/hooks/useChannelCommands.ts +0 -138
  275. package/packages/dashboard/ui/react-components/hooks/useChannels.ts +0 -328
  276. package/packages/dashboard/ui/react-components/hooks/useDebounce.ts +0 -29
  277. package/packages/dashboard/ui/react-components/hooks/useDirectMessage.ts +0 -141
  278. package/packages/dashboard/ui/react-components/hooks/useMessages.ts +0 -309
  279. package/packages/dashboard/ui/react-components/hooks/useOrchestrator.ts +0 -364
  280. package/packages/dashboard/ui/react-components/hooks/usePinnedAgents.ts +0 -140
  281. package/packages/dashboard/ui/react-components/hooks/usePresence.ts +0 -340
  282. package/packages/dashboard/ui/react-components/hooks/useRecentRepos.ts +0 -130
  283. package/packages/dashboard/ui/react-components/hooks/useSession.ts +0 -209
  284. package/packages/dashboard/ui/react-components/hooks/useTrajectory.ts +0 -265
  285. package/packages/dashboard/ui/react-components/hooks/useWebSocket.ts +0 -169
  286. package/packages/dashboard/ui/react-components/hooks/useWorkspaceMembers.ts +0 -120
  287. package/packages/dashboard/ui/react-components/hooks/useWorkspaceRepos.ts +0 -73
  288. package/packages/dashboard/ui/react-components/hooks/useWorkspaceStatus.ts +0 -237
  289. package/packages/dashboard/ui/react-components/index.ts +0 -81
  290. package/packages/dashboard/ui/react-components/layout/Header.tsx +0 -355
  291. package/packages/dashboard/ui/react-components/layout/RepoContextHeader.tsx +0 -361
  292. package/packages/dashboard/ui/react-components/layout/Sidebar.archive.test.tsx +0 -126
  293. package/packages/dashboard/ui/react-components/layout/Sidebar.test.tsx +0 -691
  294. package/packages/dashboard/ui/react-components/layout/Sidebar.tsx +0 -930
  295. package/packages/dashboard/ui/react-components/layout/index.ts +0 -7
  296. package/packages/dashboard/ui/react-components/settings/BillingSettingsPanel.tsx +0 -564
  297. package/packages/dashboard/ui/react-components/settings/SettingsPage.tsx +0 -544
  298. package/packages/dashboard/ui/react-components/settings/TeamSettingsPanel.tsx +0 -560
  299. package/packages/dashboard/ui/react-components/settings/WorkspaceSettingsPanel.tsx +0 -1386
  300. package/packages/dashboard/ui/react-components/settings/index.ts +0 -11
  301. package/packages/dashboard/ui/react-components/settings/types.ts +0 -53
  302. package/packages/dashboard/ui/react-components/utils/messageFormatting.tsx +0 -370
  303. package/packages/dashboard/ui/tailwind.config.js +0 -148
  304. package/packages/dashboard/ui/types/index.ts +0 -304
  305. package/packages/dashboard/ui/types/threading.ts +0 -7
  306. package/packages/dashboard/ui-dist/404.html +0 -1
  307. package/packages/dashboard/ui-dist/_next/static/7MZPqYkVGw3EGzVBkVmY9/_buildManifest.js +0 -1
  308. package/packages/dashboard/ui-dist/_next/static/7MZPqYkVGw3EGzVBkVmY9/_ssgManifest.js +0 -1
  309. package/packages/dashboard/ui-dist/_next/static/chunks/116-a883fca163f3a5bc.js +0 -1
  310. package/packages/dashboard/ui-dist/_next/static/chunks/117-c8afed19e821a35d.js +0 -2
  311. package/packages/dashboard/ui-dist/_next/static/chunks/282-980c2eb8fff20123.js +0 -1
  312. package/packages/dashboard/ui-dist/_next/static/chunks/320-a6304232cd0ee2ce.js +0 -1
  313. package/packages/dashboard/ui-dist/_next/static/chunks/532-bace199897eeab37.js +0 -9
  314. package/packages/dashboard/ui-dist/_next/static/chunks/631-16b905e5920f9b59.js +0 -1
  315. package/packages/dashboard/ui-dist/_next/static/chunks/648-acb2ff9f77cbfbd3.js +0 -1
  316. package/packages/dashboard/ui-dist/_next/static/chunks/766-2aea80818f7eb0d8.js +0 -1
  317. package/packages/dashboard/ui-dist/_next/static/chunks/83-26d2bde54616ee90.js +0 -1
  318. package/packages/dashboard/ui-dist/_next/static/chunks/847-f1f467060f32afff.js +0 -1
  319. package/packages/dashboard/ui-dist/_next/static/chunks/891-5cb1513eeb97a891.js +0 -1
  320. package/packages/dashboard/ui-dist/_next/static/chunks/app/_not-found/page-60501fddbafba9dc.js +0 -1
  321. package/packages/dashboard/ui-dist/_next/static/chunks/app/app/onboarding/page-9914652442f7e4fb.js +0 -1
  322. package/packages/dashboard/ui-dist/_next/static/chunks/app/app/page-366fb7c078d4e9e0.js +0 -1
  323. package/packages/dashboard/ui-dist/_next/static/chunks/app/cloud/link/page-fa1d5842aa90e8a6.js +0 -1
  324. package/packages/dashboard/ui-dist/_next/static/chunks/app/complete-profile/page-dd64bbdf66b639cd.js +0 -1
  325. package/packages/dashboard/ui-dist/_next/static/chunks/app/connect-repos/page-113060009ef35bc2.js +0 -1
  326. package/packages/dashboard/ui-dist/_next/static/chunks/app/history/page-9965d2483011b846.js +0 -1
  327. package/packages/dashboard/ui-dist/_next/static/chunks/app/layout-6b91e33784c20610.js +0 -1
  328. package/packages/dashboard/ui-dist/_next/static/chunks/app/login/page-435eceb0073be027.js +0 -1
  329. package/packages/dashboard/ui-dist/_next/static/chunks/app/metrics/page-1e37ef8e73940b40.js +0 -1
  330. package/packages/dashboard/ui-dist/_next/static/chunks/app/page-8119d4246743574e.js +0 -1
  331. package/packages/dashboard/ui-dist/_next/static/chunks/app/pricing/page-9db3ebdfa567a7c9.js +0 -1
  332. package/packages/dashboard/ui-dist/_next/static/chunks/app/providers/page-ecb16ffd3b36262b.js +0 -1
  333. package/packages/dashboard/ui-dist/_next/static/chunks/app/providers/setup/[provider]/page-4dbe33f0f7691b7c.js +0 -1
  334. package/packages/dashboard/ui-dist/_next/static/chunks/app/signup/page-c7a0a28341365ae0.js +0 -1
  335. package/packages/dashboard/ui-dist/_next/static/chunks/e868780c-48e5f147c90a3a41.js +0 -18
  336. package/packages/dashboard/ui-dist/_next/static/chunks/fd9d1056-609918ca7b6280bb.js +0 -1
  337. package/packages/dashboard/ui-dist/_next/static/chunks/framework-f66176bb897dc684.js +0 -1
  338. package/packages/dashboard/ui-dist/_next/static/chunks/main-311c3db74dcfadb7.js +0 -1
  339. package/packages/dashboard/ui-dist/_next/static/chunks/main-app-fdbeb09028f57c9f.js +0 -1
  340. package/packages/dashboard/ui-dist/_next/static/chunks/pages/_app-72b849fbd24ac258.js +0 -1
  341. package/packages/dashboard/ui-dist/_next/static/chunks/pages/_error-7ba65e1336b92748.js +0 -1
  342. package/packages/dashboard/ui-dist/_next/static/chunks/polyfills-42372ed130431b0a.js +0 -1
  343. package/packages/dashboard/ui-dist/_next/static/chunks/webpack-1cdd8ed57114d5e1.js +0 -1
  344. package/packages/dashboard/ui-dist/_next/static/css/4034f236dd1a3178.css +0 -1
  345. package/packages/dashboard/ui-dist/_next/static/css/6892f8422896ef7a.css +0 -1
  346. package/packages/dashboard/ui-dist/_next/static/iJ3Uiz3IrqUJL7IxKZHiV/_buildManifest.js +0 -1
  347. package/packages/dashboard/ui-dist/_next/static/iJ3Uiz3IrqUJL7IxKZHiV/_ssgManifest.js +0 -1
  348. package/packages/dashboard/ui-dist/_next/static/l-jd878zUJ_IlraqEWMZc/_buildManifest.js +0 -1
  349. package/packages/dashboard/ui-dist/_next/static/l-jd878zUJ_IlraqEWMZc/_ssgManifest.js +0 -1
  350. package/packages/dashboard/ui-dist/alt-logos/agent-relay-logo-128.png +0 -0
  351. package/packages/dashboard/ui-dist/alt-logos/agent-relay-logo-256.png +0 -0
  352. package/packages/dashboard/ui-dist/alt-logos/agent-relay-logo-32.png +0 -0
  353. package/packages/dashboard/ui-dist/alt-logos/agent-relay-logo-512.png +0 -0
  354. package/packages/dashboard/ui-dist/alt-logos/agent-relay-logo-64.png +0 -0
  355. package/packages/dashboard/ui-dist/alt-logos/agent-relay-logo.svg +0 -45
  356. package/packages/dashboard/ui-dist/alt-logos/logo.svg +0 -38
  357. package/packages/dashboard/ui-dist/alt-logos/monogram-logo-128.png +0 -0
  358. package/packages/dashboard/ui-dist/alt-logos/monogram-logo-256.png +0 -0
  359. package/packages/dashboard/ui-dist/alt-logos/monogram-logo-32.png +0 -0
  360. package/packages/dashboard/ui-dist/alt-logos/monogram-logo-512.png +0 -0
  361. package/packages/dashboard/ui-dist/alt-logos/monogram-logo-64.png +0 -0
  362. package/packages/dashboard/ui-dist/alt-logos/monogram-logo.svg +0 -38
  363. package/packages/dashboard/ui-dist/app/onboarding.html +0 -1
  364. package/packages/dashboard/ui-dist/app/onboarding.txt +0 -7
  365. package/packages/dashboard/ui-dist/app.html +0 -1
  366. package/packages/dashboard/ui-dist/app.txt +0 -7
  367. package/packages/dashboard/ui-dist/apple-icon.png +0 -0
  368. package/packages/dashboard/ui-dist/cloud/link.html +0 -1
  369. package/packages/dashboard/ui-dist/cloud/link.txt +0 -7
  370. package/packages/dashboard/ui-dist/complete-profile.html +0 -5
  371. package/packages/dashboard/ui-dist/complete-profile.txt +0 -7
  372. package/packages/dashboard/ui-dist/connect-repos.html +0 -1
  373. package/packages/dashboard/ui-dist/connect-repos.txt +0 -7
  374. package/packages/dashboard/ui-dist/history.html +0 -1
  375. package/packages/dashboard/ui-dist/history.txt +0 -7
  376. package/packages/dashboard/ui-dist/index.html +0 -1
  377. package/packages/dashboard/ui-dist/index.txt +0 -7
  378. package/packages/dashboard/ui-dist/login.html +0 -5
  379. package/packages/dashboard/ui-dist/login.txt +0 -7
  380. package/packages/dashboard/ui-dist/metrics.html +0 -1
  381. package/packages/dashboard/ui-dist/metrics.txt +0 -7
  382. package/packages/dashboard/ui-dist/pricing.html +0 -13
  383. package/packages/dashboard/ui-dist/pricing.txt +0 -7
  384. package/packages/dashboard/ui-dist/providers/setup/claude.html +0 -1
  385. package/packages/dashboard/ui-dist/providers/setup/claude.txt +0 -8
  386. package/packages/dashboard/ui-dist/providers/setup/codex.html +0 -1
  387. package/packages/dashboard/ui-dist/providers/setup/codex.txt +0 -8
  388. package/packages/dashboard/ui-dist/providers/setup/cursor.html +0 -1
  389. package/packages/dashboard/ui-dist/providers/setup/cursor.txt +0 -8
  390. package/packages/dashboard/ui-dist/providers.html +0 -1
  391. package/packages/dashboard/ui-dist/providers.txt +0 -7
  392. package/packages/dashboard/ui-dist/signup.html +0 -6
  393. package/packages/dashboard/ui-dist/signup.txt +0 -7
  394. package/packages/dashboard-server/dist/health-worker-manager.d.ts +0 -62
  395. package/packages/dashboard-server/dist/health-worker-manager.js +0 -144
  396. package/packages/dashboard-server/dist/health-worker.d.ts +0 -9
  397. package/packages/dashboard-server/dist/health-worker.js +0 -79
  398. package/packages/dashboard-server/dist/index.d.ts +0 -18
  399. package/packages/dashboard-server/dist/index.js +0 -17
  400. package/packages/dashboard-server/dist/metrics.d.ts +0 -105
  401. package/packages/dashboard-server/dist/metrics.js +0 -193
  402. package/packages/dashboard-server/dist/needs-attention.d.ts +0 -24
  403. package/packages/dashboard-server/dist/needs-attention.js +0 -78
  404. package/packages/dashboard-server/dist/server.d.ts +0 -25
  405. package/packages/dashboard-server/dist/server.js +0 -5158
  406. package/packages/dashboard-server/dist/start.d.ts +0 -6
  407. package/packages/dashboard-server/dist/start.js +0 -13
  408. package/packages/dashboard-server/dist/types/threading.d.ts +0 -8
  409. package/packages/dashboard-server/dist/types/threading.js +0 -2
  410. package/packages/dashboard-server/dist/user-bridge.d.ts +0 -158
  411. package/packages/dashboard-server/dist/user-bridge.js +0 -390
  412. package/packages/dashboard-server/package.json +0 -55
@@ -1,309 +0,0 @@
1
- /**
2
- * useMessages Hook
3
- *
4
- * React hook for managing message state with filtering,
5
- * threading, and send functionality.
6
- */
7
-
8
- import { useState, useMemo, useCallback, useEffect } from 'react';
9
- import type { Message, SendMessageRequest } from '../../types';
10
- import { api } from '../../lib/api';
11
-
12
- export interface UseMessagesOptions {
13
- messages: Message[];
14
- currentChannel?: string;
15
- /** Optional sender name for cloud mode (GitHub username). Falls back to 'Dashboard' if not provided. */
16
- senderName?: string;
17
- }
18
-
19
- export interface ThreadInfo {
20
- id: string;
21
- name: string;
22
- lastMessage: Message;
23
- messageCount: number;
24
- unreadCount: number;
25
- participants: string[];
26
- }
27
-
28
- export interface UseMessagesReturn {
29
- // Filtered messages
30
- messages: Message[];
31
- threadMessages: (threadId: string) => Message[];
32
-
33
- // Channel/thread state
34
- currentChannel: string;
35
- setCurrentChannel: (channel: string) => void;
36
- currentThread: string | null;
37
- setCurrentThread: (threadId: string | null) => void;
38
-
39
- // Thread info
40
- activeThreads: ThreadInfo[];
41
- totalUnreadThreadCount: number;
42
-
43
- // Message actions
44
- sendMessage: (to: string, content: string, thread?: string, attachmentIds?: string[]) => Promise<boolean>;
45
- isSending: boolean;
46
- sendError: string | null;
47
-
48
- // Stats
49
- totalCount: number;
50
- unreadCount: number;
51
- }
52
-
53
- export function useMessages({
54
- messages,
55
- currentChannel: initialChannel = 'general',
56
- senderName,
57
- }: UseMessagesOptions): UseMessagesReturn {
58
- const [currentChannel, setCurrentChannel] = useState(initialChannel);
59
- const [currentThreadInternal, setCurrentThreadInternal] = useState<string | null>(null);
60
- const [isSending, setIsSending] = useState(false);
61
- const [sendError, setSendError] = useState<string | null>(null);
62
-
63
- // Track seen threads with timestamp of when they were last viewed
64
- // This allows us to show new messages that arrive after viewing
65
- const [seenThreads, setSeenThreads] = useState<Map<string, number>>(new Map());
66
-
67
- // Effective sender name for the current user (used for filtering own messages)
68
- const effectiveSenderName = senderName || 'Dashboard';
69
-
70
- // Optimistic messages: shown immediately before server confirms
71
- // These have status='sending' and a temp ID prefixed with 'optimistic-'
72
- const [optimisticMessages, setOptimisticMessages] = useState<Message[]>([]);
73
-
74
- // Clean up optimistic messages when they appear in the real messages list
75
- // Match by to + content only (not from, since server may use different sender like '_DashboardUI')
76
- useEffect(() => {
77
- if (optimisticMessages.length === 0) return;
78
-
79
- // Create a set of "fingerprints" for real messages (recent ones only)
80
- // Use to + content only - the 'from' field may differ between optimistic (user's name)
81
- // and real message (server may use '_DashboardUI' as relay client name)
82
- const recentMessages = messages.slice(-50); // Only check recent messages for performance
83
- const realFingerprints = new Set(
84
- recentMessages.map((m) => `${m.to}:${m.content.slice(0, 100)}`)
85
- );
86
-
87
- // Remove optimistic messages that now exist in real messages
88
- setOptimisticMessages((prev) =>
89
- prev.filter((opt) => {
90
- const fingerprint = `${opt.to}:${opt.content.slice(0, 100)}`;
91
- return !realFingerprints.has(fingerprint);
92
- })
93
- );
94
- }, [messages, optimisticMessages.length]);
95
-
96
- // Combine real messages with optimistic messages
97
- const allMessages = useMemo(() => {
98
- if (optimisticMessages.length === 0) return messages;
99
- // Append optimistic messages at the end (they're the most recent)
100
- return [...messages, ...optimisticMessages];
101
- }, [messages, optimisticMessages]);
102
-
103
- // Filter messages by current channel
104
- // Only exclude reply-chain replies (where thread is another message's ID)
105
- // Keep topic thread messages (where thread is a topic name, not a message ID)
106
- const filteredMessages = useMemo(() => {
107
- // Build set of message IDs for efficient lookup
108
- const messageIds = new Set(allMessages.map((m) => m.id));
109
-
110
- // Filter out reply-chain replies (thread points to existing message ID)
111
- // Keep topic thread messages (thread is a name, not a message ID)
112
- const mainViewMessages = allMessages.filter((m) => {
113
- if (!m.thread) return true; // No thread - show it
114
- // If thread is a message ID, it's a reply - hide it from main view
115
- // If thread is a topic name, show it
116
- return !messageIds.has(m.thread);
117
- });
118
-
119
- if (currentChannel === 'general') {
120
- return mainViewMessages;
121
- }
122
- return mainViewMessages.filter(
123
- (m) => m.from === currentChannel || m.to === currentChannel
124
- );
125
- }, [allMessages, currentChannel]);
126
-
127
- // Get messages for a specific thread
128
- const threadMessages = useCallback(
129
- (threadId: string) => allMessages.filter((m) => m.thread === threadId),
130
- [allMessages]
131
- );
132
-
133
- // Calculate active threads with unread counts
134
- const activeThreads = useMemo((): ThreadInfo[] => {
135
- const threadMap = new Map<string, Message[]>();
136
- const messageIds = new Set(allMessages.map((m) => m.id));
137
-
138
- // Group messages by thread
139
- for (const msg of allMessages) {
140
- if (msg.thread) {
141
- const existing = threadMap.get(msg.thread) || [];
142
- existing.push(msg);
143
- threadMap.set(msg.thread, existing);
144
- }
145
- }
146
-
147
- // Convert to ThreadInfo array
148
- const threads: ThreadInfo[] = [];
149
- for (const [threadId, threadMsgs] of threadMap.entries()) {
150
- // Sort by timestamp to get the last message
151
- const sorted = [...threadMsgs].sort(
152
- (a, b) => new Date(b.timestamp).getTime() - new Date(a.timestamp).getTime()
153
- );
154
-
155
- // Get unique participants
156
- const participants = [...new Set(threadMsgs.flatMap((m) => [m.from, m.to]))].filter(
157
- (p) => p !== '*'
158
- );
159
-
160
- // Count unread messages in thread
161
- // Consider messages as "read" if they arrived before we last viewed this thread
162
- // Exclude messages from current user - users shouldn't get notifications for their own messages
163
- const seenTimestamp = seenThreads.get(threadId);
164
- const unreadCount = threadMsgs.filter((m) => {
165
- if (m.from === effectiveSenderName) return false; // Don't count own messages as unread
166
- if (m.isRead) return false; // Already marked as read
167
- if (seenTimestamp) {
168
- // If we've seen this thread, only count messages after that time
169
- return new Date(m.timestamp).getTime() > seenTimestamp;
170
- }
171
- return true; // Not seen yet, count as unread
172
- }).length;
173
-
174
- // Determine thread name: if threadId is a message ID, use first message content as name
175
- let name = threadId;
176
- if (messageIds.has(threadId)) {
177
- // Find the original message that started the thread
178
- const originalMsg = allMessages.find((m) => m.id === threadId);
179
- if (originalMsg) {
180
- // Use first line of content, truncated
181
- const firstLine = originalMsg.content.split('\n')[0];
182
- name = firstLine.length > 30 ? firstLine.substring(0, 30) + '...' : firstLine;
183
- }
184
- }
185
-
186
- threads.push({
187
- id: threadId,
188
- name,
189
- lastMessage: sorted[0],
190
- messageCount: threadMsgs.length,
191
- unreadCount,
192
- participants,
193
- });
194
- }
195
-
196
- // Sort by last activity (most recent first)
197
- return threads.sort(
198
- (a, b) =>
199
- new Date(b.lastMessage.timestamp).getTime() - new Date(a.lastMessage.timestamp).getTime()
200
- );
201
- }, [allMessages, seenThreads]);
202
-
203
- // Wrapper for setCurrentThread that also marks the thread as seen
204
- const setCurrentThread = useCallback((threadId: string | null) => {
205
- setCurrentThreadInternal(threadId);
206
- if (threadId) {
207
- // Mark thread as seen with current timestamp
208
- setSeenThreads((prev) => {
209
- const next = new Map(prev);
210
- next.set(threadId, Date.now());
211
- return next;
212
- });
213
- }
214
- }, []);
215
-
216
- // Calculate total unread threads
217
- const totalUnreadThreadCount = useMemo(
218
- () => activeThreads.filter((t) => t.unreadCount > 0).length,
219
- [activeThreads]
220
- );
221
-
222
- // Calculate stats
223
- const stats = useMemo(() => {
224
- const unread = allMessages.filter((m) => !m.isRead).length;
225
- return {
226
- totalCount: allMessages.length,
227
- unreadCount: unread,
228
- };
229
- }, [allMessages]);
230
-
231
- // Send message function with optimistic updates
232
- const sendMessage = useCallback(
233
- async (to: string, content: string, thread?: string, attachmentIds?: string[]): Promise<boolean> => {
234
- setIsSending(true);
235
- setSendError(null);
236
-
237
- // Create optimistic message and add it immediately for snappy UX
238
- const from = effectiveSenderName;
239
- const optimisticId = `optimistic-${Date.now()}-${Math.random().toString(36).slice(2, 9)}`;
240
- const optimisticMsg: Message = {
241
- id: optimisticId,
242
- from,
243
- to,
244
- content,
245
- timestamp: new Date().toISOString(),
246
- status: 'sending',
247
- thread,
248
- isRead: true, // User's own messages are always "read"
249
- };
250
-
251
- // Add optimistic message immediately - UI updates instantly
252
- setOptimisticMessages((prev) => [...prev, optimisticMsg]);
253
-
254
- try {
255
- const request: SendMessageRequest & { from?: string } = {
256
- to,
257
- message: content,
258
- thread,
259
- attachments: attachmentIds,
260
- };
261
-
262
- // Include sender name for cloud mode (GitHub username)
263
- if (senderName) {
264
- request.from = senderName;
265
- }
266
-
267
- // Use api.sendMessage which handles:
268
- // - Workspace proxy routing (in cloud mode)
269
- // - CSRF token headers
270
- // - Credentials
271
- const result = await api.sendMessage(request);
272
-
273
- if (result.success) {
274
- // Success! The optimistic message will be cleaned up when
275
- // the real message arrives via WebSocket
276
- return true;
277
- }
278
-
279
- // Failed - remove the optimistic message and show error
280
- setOptimisticMessages((prev) => prev.filter((m) => m.id !== optimisticId));
281
- setSendError(result.error || 'Failed to send message');
282
- return false;
283
- } catch (_error) {
284
- // Network error - remove optimistic message
285
- setOptimisticMessages((prev) => prev.filter((m) => m.id !== optimisticId));
286
- setSendError('Network error');
287
- return false;
288
- } finally {
289
- setIsSending(false);
290
- }
291
- },
292
- [effectiveSenderName, senderName]
293
- );
294
-
295
- return {
296
- messages: filteredMessages,
297
- threadMessages,
298
- currentChannel,
299
- setCurrentChannel,
300
- currentThread: currentThreadInternal,
301
- setCurrentThread,
302
- activeThreads,
303
- totalUnreadThreadCount,
304
- sendMessage,
305
- isSending,
306
- sendError,
307
- ...stats,
308
- };
309
- }
@@ -1,364 +0,0 @@
1
- /**
2
- * useOrchestrator Hook
3
- *
4
- * Connects to the daemon orchestrator for workspace and agent management.
5
- * Provides real-time updates via WebSocket.
6
- */
7
-
8
- import { useState, useEffect, useCallback, useRef } from 'react';
9
- import type { Workspace } from '../WorkspaceSelector';
10
-
11
- export interface OrchestratorAgent {
12
- id: string;
13
- name: string;
14
- workspaceId: string;
15
- provider: string;
16
- status: 'running' | 'idle' | 'crashed' | 'restarting' | 'stopped';
17
- pid?: number;
18
- task?: string;
19
- spawnedAt: Date;
20
- restartCount: number;
21
- }
22
-
23
- export interface OrchestratorEvent {
24
- type: string;
25
- workspaceId?: string;
26
- agentId?: string;
27
- data: unknown;
28
- timestamp: Date;
29
- }
30
-
31
- export interface UseOrchestratorOptions {
32
- /** Orchestrator API URL (default: http://localhost:3456) */
33
- apiUrl?: string;
34
- /** Enable orchestrator connection (default: false - orchestrator is optional) */
35
- enabled?: boolean;
36
- }
37
-
38
- export interface UseOrchestratorResult {
39
- /** All workspaces */
40
- workspaces: Workspace[];
41
- /** Currently active workspace ID */
42
- activeWorkspaceId?: string;
43
- /** Active workspace agents */
44
- agents: OrchestratorAgent[];
45
- /** Connection status */
46
- isConnected: boolean;
47
- /** Loading state */
48
- isLoading: boolean;
49
- /** Error state */
50
- error: Error | null;
51
- /** Switch to a workspace */
52
- switchWorkspace: (workspaceId: string) => Promise<void>;
53
- /** Add a new workspace */
54
- addWorkspace: (path: string, name?: string) => Promise<Workspace>;
55
- /** Remove a workspace */
56
- removeWorkspace: (workspaceId: string) => Promise<void>;
57
- /** Spawn an agent */
58
- spawnAgent: (name: string, task?: string, provider?: string) => Promise<OrchestratorAgent>;
59
- /** Stop an agent */
60
- stopAgent: (agentName: string) => Promise<void>;
61
- /** Refresh data */
62
- refresh: () => Promise<void>;
63
- }
64
-
65
- export function useOrchestrator(options: UseOrchestratorOptions = {}): UseOrchestratorResult {
66
- const { apiUrl = 'http://localhost:3456', enabled = false } = options;
67
-
68
- const [workspaces, setWorkspaces] = useState<Workspace[]>([]);
69
- const [activeWorkspaceId, setActiveWorkspaceId] = useState<string>();
70
- const [agents, setAgents] = useState<OrchestratorAgent[]>([]);
71
- const [isConnected, setIsConnected] = useState(false);
72
- const [isLoading, setIsLoading] = useState(enabled);
73
- const [error, setError] = useState<Error | null>(null);
74
-
75
- const wsRef = useRef<WebSocket | null>(null);
76
- const reconnectTimeoutRef = useRef<ReturnType<typeof setTimeout>>();
77
-
78
- // Convert API URL to WebSocket URL
79
- const wsUrl = apiUrl.replace(/^http/, 'ws');
80
-
81
- // Fetch initial data - only if enabled
82
- const fetchData = useCallback(async () => {
83
- if (!enabled) {
84
- return;
85
- }
86
-
87
- try {
88
- setIsLoading(true);
89
- setError(null);
90
-
91
- const response = await fetch(`${apiUrl}/workspaces`);
92
- if (!response.ok) {
93
- throw new Error(`Failed to fetch workspaces: ${response.statusText}`);
94
- }
95
-
96
- const data = await response.json();
97
- setWorkspaces(
98
- data.workspaces.map((w: Workspace) => ({
99
- ...w,
100
- lastActiveAt: new Date(w.lastActiveAt),
101
- }))
102
- );
103
- setActiveWorkspaceId(data.activeWorkspaceId);
104
-
105
- // Fetch agents for active workspace
106
- if (data.activeWorkspaceId) {
107
- const agentsResponse = await fetch(`${apiUrl}/workspaces/${data.activeWorkspaceId}/agents`);
108
- if (agentsResponse.ok) {
109
- const agentsData = await agentsResponse.json();
110
- setAgents(
111
- agentsData.agents.map((a: OrchestratorAgent) => ({
112
- ...a,
113
- spawnedAt: new Date(a.spawnedAt),
114
- }))
115
- );
116
- }
117
- }
118
- } catch (err) {
119
- setError(err instanceof Error ? err : new Error(String(err)));
120
- } finally {
121
- setIsLoading(false);
122
- }
123
- }, [apiUrl, enabled]);
124
-
125
- // WebSocket connection - only connect if enabled
126
- useEffect(() => {
127
- // Skip connection if orchestrator is not enabled
128
- if (!enabled) {
129
- return;
130
- }
131
-
132
- const connect = () => {
133
- try {
134
- const ws = new WebSocket(wsUrl);
135
-
136
- ws.onopen = () => {
137
- setIsConnected(true);
138
- setError(null);
139
- };
140
-
141
- ws.onmessage = (event) => {
142
- try {
143
- const message = JSON.parse(event.data);
144
-
145
- if (message.type === 'init') {
146
- // Initial state from server
147
- setWorkspaces(
148
- message.data.workspaces.map((w: Workspace) => ({
149
- ...w,
150
- lastActiveAt: new Date(w.lastActiveAt),
151
- }))
152
- );
153
- setActiveWorkspaceId(message.data.activeWorkspaceId);
154
- setAgents(
155
- message.data.agents?.map((a: OrchestratorAgent) => ({
156
- ...a,
157
- spawnedAt: new Date(a.spawnedAt),
158
- })) || []
159
- );
160
- setIsLoading(false);
161
- } else if (message.type === 'event') {
162
- handleEvent(message.data as OrchestratorEvent);
163
- }
164
- } catch (err) {
165
- console.error('Failed to parse WebSocket message:', err);
166
- }
167
- };
168
-
169
- ws.onclose = () => {
170
- setIsConnected(false);
171
- wsRef.current = null;
172
-
173
- // Reconnect after delay
174
- reconnectTimeoutRef.current = setTimeout(connect, 3000);
175
- };
176
-
177
- ws.onerror = (err) => {
178
- console.error('WebSocket error:', err);
179
- ws.close();
180
- };
181
-
182
- wsRef.current = ws;
183
- } catch (err) {
184
- setError(err instanceof Error ? err : new Error(String(err)));
185
- // Retry connection
186
- reconnectTimeoutRef.current = setTimeout(connect, 3000);
187
- }
188
- };
189
-
190
- // Start with HTTP fetch, then upgrade to WebSocket
191
- fetchData().then(connect);
192
-
193
- return () => {
194
- if (reconnectTimeoutRef.current) {
195
- clearTimeout(reconnectTimeoutRef.current);
196
- }
197
- if (wsRef.current) {
198
- wsRef.current.close();
199
- }
200
- };
201
- }, [wsUrl, fetchData, enabled]);
202
-
203
- // Handle real-time events
204
- const handleEvent = useCallback((event: OrchestratorEvent) => {
205
- switch (event.type) {
206
- case 'workspace:added':
207
- setWorkspaces((prev) => [...prev, event.data as Workspace]);
208
- break;
209
-
210
- case 'workspace:removed':
211
- setWorkspaces((prev) => prev.filter((w) => w.id !== event.workspaceId));
212
- break;
213
-
214
- case 'workspace:updated':
215
- setWorkspaces((prev) =>
216
- prev.map((w) =>
217
- w.id === event.workspaceId ? { ...w, ...(event.data as Partial<Workspace>) } : w
218
- )
219
- );
220
- break;
221
-
222
- case 'workspace:switched':
223
- setActiveWorkspaceId((event.data as { currentId: string }).currentId);
224
- break;
225
-
226
- case 'agent:spawned':
227
- setAgents((prev) => [...prev, event.data as OrchestratorAgent]);
228
- break;
229
-
230
- case 'agent:stopped':
231
- case 'agent:crashed':
232
- setAgents((prev) => prev.filter((a) => a.name !== (event.data as { name: string }).name));
233
- break;
234
-
235
- case 'agent:restarted':
236
- setAgents((prev) =>
237
- prev.map((a) =>
238
- a.name === (event.data as { name: string }).name
239
- ? { ...a, status: 'running' as const, restartCount: a.restartCount + 1 }
240
- : a
241
- )
242
- );
243
- break;
244
- }
245
- }, []);
246
-
247
- // Switch workspace
248
- const switchWorkspace = useCallback(
249
- async (workspaceId: string) => {
250
- const response = await fetch(`${apiUrl}/workspaces/${workspaceId}/switch`, {
251
- method: 'POST',
252
- });
253
-
254
- if (!response.ok) {
255
- throw new Error(`Failed to switch workspace: ${response.statusText}`);
256
- }
257
-
258
- // Fetch agents for new workspace
259
- const agentsResponse = await fetch(`${apiUrl}/workspaces/${workspaceId}/agents`);
260
- if (agentsResponse.ok) {
261
- const agentsData = await agentsResponse.json();
262
- setAgents(
263
- agentsData.agents.map((a: OrchestratorAgent) => ({
264
- ...a,
265
- spawnedAt: new Date(a.spawnedAt),
266
- }))
267
- );
268
- }
269
- },
270
- [apiUrl]
271
- );
272
-
273
- // Add workspace
274
- const addWorkspace = useCallback(
275
- async (path: string, name?: string): Promise<Workspace> => {
276
- const response = await fetch(`${apiUrl}/workspaces`, {
277
- method: 'POST',
278
- headers: { 'Content-Type': 'application/json' },
279
- body: JSON.stringify({ path, name }),
280
- });
281
-
282
- if (!response.ok) {
283
- const error = await response.json();
284
- throw new Error(error.error || 'Failed to add workspace');
285
- }
286
-
287
- return response.json();
288
- },
289
- [apiUrl]
290
- );
291
-
292
- // Remove workspace
293
- const removeWorkspace = useCallback(
294
- async (workspaceId: string) => {
295
- const response = await fetch(`${apiUrl}/workspaces/${workspaceId}`, {
296
- method: 'DELETE',
297
- });
298
-
299
- if (!response.ok) {
300
- throw new Error(`Failed to remove workspace: ${response.statusText}`);
301
- }
302
- },
303
- [apiUrl]
304
- );
305
-
306
- // Spawn agent
307
- const spawnAgent = useCallback(
308
- async (name: string, task?: string, provider?: string): Promise<OrchestratorAgent> => {
309
- if (!activeWorkspaceId) {
310
- throw new Error('No active workspace');
311
- }
312
-
313
- const response = await fetch(`${apiUrl}/workspaces/${activeWorkspaceId}/agents`, {
314
- method: 'POST',
315
- headers: { 'Content-Type': 'application/json' },
316
- body: JSON.stringify({ name, task, provider }),
317
- });
318
-
319
- if (!response.ok) {
320
- const error = await response.json();
321
- throw new Error(error.error || 'Failed to spawn agent');
322
- }
323
-
324
- return response.json();
325
- },
326
- [apiUrl, activeWorkspaceId]
327
- );
328
-
329
- // Stop agent
330
- const stopAgent = useCallback(
331
- async (agentName: string) => {
332
- if (!activeWorkspaceId) {
333
- throw new Error('No active workspace');
334
- }
335
-
336
- const response = await fetch(
337
- `${apiUrl}/workspaces/${activeWorkspaceId}/agents/${agentName}`,
338
- {
339
- method: 'DELETE',
340
- }
341
- );
342
-
343
- if (!response.ok) {
344
- throw new Error(`Failed to stop agent: ${response.statusText}`);
345
- }
346
- },
347
- [apiUrl, activeWorkspaceId]
348
- );
349
-
350
- return {
351
- workspaces,
352
- activeWorkspaceId,
353
- agents,
354
- isConnected,
355
- isLoading,
356
- error,
357
- switchWorkspace,
358
- addWorkspace,
359
- removeWorkspace,
360
- spawnAgent,
361
- stopAgent,
362
- refresh: fetchData,
363
- };
364
- }