@polderlabs/bizar 7.0.4 → 8.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (489) hide show
  1. package/.claude/settings.local.json +8 -0
  2. package/bizar-dash/DESIGN.md +729 -969
  3. package/bizar-dash/GLYPH.md +418 -0
  4. package/bizar-dash/PLAN.md +1135 -0
  5. package/bizar-dash/dist/assets/ActivityFeed-BRBtQOHB.js +6 -0
  6. package/bizar-dash/dist/assets/ActivityFeed-BRBtQOHB.js.map +1 -0
  7. package/bizar-dash/dist/assets/ActivityView-CwqhxBfh.js +1 -0
  8. package/bizar-dash/dist/assets/ActivityView-CwqhxBfh.js.map +1 -0
  9. package/bizar-dash/dist/assets/AgentActivity-6MxU-a9F.js +1 -0
  10. package/bizar-dash/dist/assets/AgentActivity-6MxU-a9F.js.map +1 -0
  11. package/bizar-dash/dist/assets/AgentsView-BYrOFdwl.js +8 -0
  12. package/bizar-dash/dist/assets/AgentsView-BYrOFdwl.js.map +1 -0
  13. package/bizar-dash/dist/assets/Badge-Cd61wsBa.js +1 -0
  14. package/bizar-dash/dist/assets/Badge-Cd61wsBa.js.map +1 -0
  15. package/bizar-dash/dist/assets/Card-C_bvqXdQ.js +1 -0
  16. package/bizar-dash/dist/assets/Card-C_bvqXdQ.js.map +1 -0
  17. package/bizar-dash/dist/assets/EmptyState-BWQuKnk9.js +1 -0
  18. package/bizar-dash/dist/assets/EmptyState-BWQuKnk9.js.map +1 -0
  19. package/bizar-dash/dist/assets/GoalsView-Dok0yt9S.js +11 -0
  20. package/bizar-dash/dist/assets/GoalsView-Dok0yt9S.js.map +1 -0
  21. package/bizar-dash/dist/assets/Grid-C62gCPqt.js +1 -0
  22. package/bizar-dash/dist/assets/Grid-C62gCPqt.js.map +1 -0
  23. package/bizar-dash/dist/assets/KanbanCard-CtTKP6ZX.js +21 -0
  24. package/bizar-dash/dist/assets/KanbanCard-CtTKP6ZX.js.map +1 -0
  25. package/bizar-dash/dist/assets/LibrariesView-BcyBQXiY.js +67 -0
  26. package/bizar-dash/dist/assets/LibrariesView-BcyBQXiY.js.map +1 -0
  27. package/bizar-dash/dist/assets/MemoryView-49wR4u-y.js +13 -0
  28. package/bizar-dash/dist/assets/MemoryView-49wR4u-y.js.map +1 -0
  29. package/bizar-dash/dist/assets/OverviewView-BtQ_UWYj.js +1 -0
  30. package/bizar-dash/dist/assets/OverviewView-BtQ_UWYj.js.map +1 -0
  31. package/bizar-dash/dist/assets/ProgressBar-CpvDeq9F.js +1 -0
  32. package/bizar-dash/dist/assets/ProgressBar-CpvDeq9F.js.map +1 -0
  33. package/bizar-dash/dist/assets/SettingsRow-DmIe5OUu.js +30 -0
  34. package/bizar-dash/dist/assets/SettingsRow-DmIe5OUu.js.map +1 -0
  35. package/bizar-dash/dist/assets/SettingsView-D1KmGWbi.js +48 -0
  36. package/bizar-dash/dist/assets/SettingsView-D1KmGWbi.js.map +1 -0
  37. package/bizar-dash/dist/assets/StatTile-BkIP32gG.js +11 -0
  38. package/bizar-dash/dist/assets/StatTile-BkIP32gG.js.map +1 -0
  39. package/bizar-dash/dist/assets/TasksView-Cba3GJ42.js +1 -0
  40. package/bizar-dash/dist/assets/TasksView-Cba3GJ42.js.map +1 -0
  41. package/bizar-dash/dist/assets/ViewHeader-D6c2cw1b.js +6 -0
  42. package/bizar-dash/dist/assets/ViewHeader-D6c2cw1b.js.map +1 -0
  43. package/bizar-dash/dist/assets/brain-DeoXNDE2.js +6 -0
  44. package/bizar-dash/dist/assets/brain-DeoXNDE2.js.map +1 -0
  45. package/bizar-dash/dist/assets/calendar-DRlQkGJc.js +6 -0
  46. package/bizar-dash/dist/assets/calendar-DRlQkGJc.js.map +1 -0
  47. package/bizar-dash/dist/assets/circle-check-DmYQ3vGp.js +6 -0
  48. package/bizar-dash/dist/assets/circle-check-DmYQ3vGp.js.map +1 -0
  49. package/bizar-dash/dist/assets/cmdk-BwN8hcKQ.js +80 -0
  50. package/bizar-dash/dist/assets/cmdk-BwN8hcKQ.js.map +1 -0
  51. package/bizar-dash/dist/assets/dnd-kit-DR2Qzzxk.js +5 -0
  52. package/bizar-dash/dist/assets/dnd-kit-DR2Qzzxk.js.map +1 -0
  53. package/bizar-dash/dist/assets/git-merge-OoqBKQer.js +6 -0
  54. package/bizar-dash/dist/assets/git-merge-OoqBKQer.js.map +1 -0
  55. package/bizar-dash/dist/assets/git-pull-request-CXBQTR2f.js +6 -0
  56. package/bizar-dash/dist/assets/git-pull-request-CXBQTR2f.js.map +1 -0
  57. package/bizar-dash/dist/assets/main-COdgjqbZ.css +1 -0
  58. package/bizar-dash/dist/assets/main-Cw6gybzS.js +109 -0
  59. package/bizar-dash/dist/assets/main-Cw6gybzS.js.map +1 -0
  60. package/bizar-dash/dist/assets/message-square-DUTeIQAR.js +6 -0
  61. package/bizar-dash/dist/assets/message-square-DUTeIQAR.js.map +1 -0
  62. package/bizar-dash/dist/assets/minus-CrStJTZ7.js +6 -0
  63. package/bizar-dash/dist/assets/minus-CrStJTZ7.js.map +1 -0
  64. package/bizar-dash/dist/assets/wrench-BJ1WIC4u.js +6 -0
  65. package/bizar-dash/dist/assets/wrench-BJ1WIC4u.js.map +1 -0
  66. package/bizar-dash/dist/{mobile.html → v8.html} +6 -9
  67. package/bizar-dash/node_modules/.vite/vitest/da39a3ee5e6b4b0d3255bfef95601890afd80709/results.json +1 -1
  68. package/bizar-dash/src/server/server.mjs +1 -57
  69. package/bizar-dash/src/web/node_modules/.vite/vitest/da39a3ee5e6b4b0d3255bfef95601890afd80709/results.json +1 -0
  70. package/bizar-dash/src/web/v8/App.tsx +188 -0
  71. package/bizar-dash/src/web/v8/__tests__/App.test.tsx +102 -0
  72. package/bizar-dash/src/web/v8/__tests__/AppShell.test.tsx +79 -0
  73. package/bizar-dash/src/web/v8/__tests__/PageSkeleton.test.tsx +12 -0
  74. package/bizar-dash/src/web/v8/__tests__/SettingsView.test.tsx +84 -0
  75. package/bizar-dash/src/web/v8/__tests__/Sidebar.test.tsx +95 -0
  76. package/bizar-dash/src/web/v8/__tests__/activity.test.tsx +63 -0
  77. package/bizar-dash/src/web/v8/__tests__/agents.test.tsx +90 -0
  78. package/bizar-dash/src/web/v8/__tests__/controls.test.tsx +135 -0
  79. package/bizar-dash/src/web/v8/__tests__/cx.test.ts +25 -0
  80. package/bizar-dash/src/web/v8/__tests__/data.test.tsx +293 -0
  81. package/bizar-dash/src/web/v8/__tests__/feedback.test.tsx +213 -0
  82. package/bizar-dash/src/web/v8/__tests__/goals.test.tsx +105 -0
  83. package/bizar-dash/src/web/v8/__tests__/kanban.test.tsx +176 -0
  84. package/bizar-dash/src/web/v8/__tests__/libraries.test.tsx +70 -0
  85. package/bizar-dash/src/web/v8/__tests__/memory.test.tsx +60 -0
  86. package/bizar-dash/src/web/v8/__tests__/navigation.test.tsx +137 -0
  87. package/bizar-dash/src/web/v8/__tests__/settings.test.tsx +104 -0
  88. package/bizar-dash/src/web/v8/__tests__/theme.test.tsx +98 -0
  89. package/bizar-dash/src/web/v8/__tests__/views.test.tsx +112 -0
  90. package/bizar-dash/src/web/v8/main.tsx +28 -0
  91. package/bizar-dash/src/web/v8/shell/AppShell.tsx +90 -0
  92. package/bizar-dash/src/web/v8/shell/PageSkeleton.tsx +29 -0
  93. package/bizar-dash/src/web/v8/shell/Sidebar.tsx +361 -0
  94. package/bizar-dash/src/web/v8/shell/StatusBar.tsx +63 -0
  95. package/bizar-dash/src/web/v8/shell/Topbar.tsx +113 -0
  96. package/bizar-dash/src/web/v8/shell/index.ts +15 -0
  97. package/bizar-dash/src/web/v8/ui/activity/ActivityFeed.tsx +137 -0
  98. package/bizar-dash/src/web/v8/ui/agents/AgentActivity.tsx +101 -0
  99. package/bizar-dash/src/web/v8/ui/agents/AgentCard.tsx +158 -0
  100. package/bizar-dash/src/web/v8/ui/controls/Button.tsx +141 -0
  101. package/bizar-dash/src/web/v8/ui/controls/ButtonGroup.tsx +32 -0
  102. package/bizar-dash/src/web/v8/ui/controls/Checkbox.tsx +49 -0
  103. package/bizar-dash/src/web/v8/ui/controls/Field.tsx +78 -0
  104. package/bizar-dash/src/web/v8/ui/controls/Form.tsx +23 -0
  105. package/bizar-dash/src/web/v8/ui/controls/IconButton.tsx +112 -0
  106. package/bizar-dash/src/web/v8/ui/controls/Input.tsx +94 -0
  107. package/bizar-dash/src/web/v8/ui/controls/RadioGroup.tsx +74 -0
  108. package/bizar-dash/src/web/v8/ui/controls/Select.tsx +171 -0
  109. package/bizar-dash/src/web/v8/ui/controls/Slider.tsx +68 -0
  110. package/bizar-dash/src/web/v8/ui/controls/Switch.tsx +56 -0
  111. package/bizar-dash/src/web/v8/ui/controls/Textarea.tsx +64 -0
  112. package/bizar-dash/src/web/v8/ui/controls/Toggle.tsx +36 -0
  113. package/bizar-dash/src/web/v8/ui/controls/ToggleGroup.tsx +85 -0
  114. package/bizar-dash/src/web/v8/ui/data/Accordion.tsx +134 -0
  115. package/bizar-dash/src/web/v8/ui/data/Avatar.tsx +175 -0
  116. package/bizar-dash/src/web/v8/ui/data/Badge.tsx +93 -0
  117. package/bizar-dash/src/web/v8/ui/data/BarList.tsx +101 -0
  118. package/bizar-dash/src/web/v8/ui/data/Card.tsx +140 -0
  119. package/bizar-dash/src/web/v8/ui/data/Chip.tsx +96 -0
  120. package/bizar-dash/src/web/v8/ui/data/Kbd.tsx +42 -0
  121. package/bizar-dash/src/web/v8/ui/data/ProgressBar.tsx +93 -0
  122. package/bizar-dash/src/web/v8/ui/data/Sparkline.tsx +98 -0
  123. package/bizar-dash/src/web/v8/ui/data/StatTile.tsx +150 -0
  124. package/bizar-dash/src/web/v8/ui/data/Table.tsx +170 -0
  125. package/bizar-dash/src/web/v8/ui/data/Timeline.tsx +130 -0
  126. package/bizar-dash/src/web/v8/ui/data/ViewHeader.tsx +122 -0
  127. package/bizar-dash/src/web/v8/ui/feedback/Alert.tsx +95 -0
  128. package/bizar-dash/src/web/v8/ui/feedback/Banner.tsx +39 -0
  129. package/bizar-dash/src/web/v8/ui/feedback/ContextMenu.tsx +143 -0
  130. package/bizar-dash/src/web/v8/ui/feedback/Dialog.tsx +149 -0
  131. package/bizar-dash/src/web/v8/ui/feedback/Drawer.tsx +8 -0
  132. package/bizar-dash/src/web/v8/ui/feedback/DropdownMenu.tsx +231 -0
  133. package/bizar-dash/src/web/v8/ui/feedback/EmptyState.tsx +48 -0
  134. package/bizar-dash/src/web/v8/ui/feedback/Popover.tsx +56 -0
  135. package/bizar-dash/src/web/v8/ui/feedback/Sheet.tsx +103 -0
  136. package/bizar-dash/src/web/v8/ui/feedback/Skeleton.tsx +67 -0
  137. package/bizar-dash/src/web/v8/ui/feedback/Spinner.tsx +30 -0
  138. package/bizar-dash/src/web/v8/ui/feedback/Toast.tsx +66 -0
  139. package/bizar-dash/src/web/v8/ui/feedback/Tooltip.tsx +89 -0
  140. package/bizar-dash/src/web/v8/ui/goals/GoalCard.tsx +176 -0
  141. package/bizar-dash/src/web/v8/ui/goals/KeyResult.tsx +115 -0
  142. package/bizar-dash/src/web/v8/ui/index.ts +322 -0
  143. package/bizar-dash/src/web/v8/ui/kanban/KanbanBoard.tsx +80 -0
  144. package/bizar-dash/src/web/v8/ui/kanban/KanbanCard.tsx +247 -0
  145. package/bizar-dash/src/web/v8/ui/kanban/KanbanColumn.tsx +181 -0
  146. package/bizar-dash/src/web/v8/ui/kanban/KanbanContextMenu.tsx +122 -0
  147. package/bizar-dash/src/web/v8/ui/kanban/KanbanQuickAdd.tsx +141 -0
  148. package/bizar-dash/src/web/v8/ui/libraries/LibraryGrid.tsx +30 -0
  149. package/bizar-dash/src/web/v8/ui/libraries/LibraryItem.tsx +161 -0
  150. package/bizar-dash/src/web/v8/ui/memory/MemoryVault.tsx +144 -0
  151. package/bizar-dash/src/web/v8/ui/navigation/CommandPalette.tsx +224 -0
  152. package/bizar-dash/src/web/v8/ui/navigation/NavLink.tsx +81 -0
  153. package/bizar-dash/src/web/v8/ui/navigation/Pagination.tsx +164 -0
  154. package/bizar-dash/src/web/v8/ui/navigation/Tabs.tsx +128 -0
  155. package/bizar-dash/src/web/v8/ui/navigation/useCommandPaletteHotkey.test.ts +79 -0
  156. package/bizar-dash/src/web/v8/ui/primitives/Box.tsx +144 -0
  157. package/bizar-dash/src/web/v8/ui/primitives/Center.tsx +40 -0
  158. package/bizar-dash/src/web/v8/ui/primitives/Cluster.tsx +67 -0
  159. package/bizar-dash/src/web/v8/ui/primitives/Grid.tsx +104 -0
  160. package/bizar-dash/src/web/v8/ui/primitives/Inline.tsx +77 -0
  161. package/bizar-dash/src/web/v8/ui/primitives/Portal.tsx +33 -0
  162. package/bizar-dash/src/web/v8/ui/primitives/ScrollArea.tsx +62 -0
  163. package/bizar-dash/src/web/v8/ui/primitives/Separator.tsx +42 -0
  164. package/bizar-dash/src/web/v8/ui/primitives/Stack.tsx +73 -0
  165. package/bizar-dash/src/web/v8/ui/primitives/VisuallyHidden.tsx +49 -0
  166. package/bizar-dash/src/web/v8/ui/settings/SettingsNav.tsx +91 -0
  167. package/bizar-dash/src/web/v8/ui/settings/SettingsRow.tsx +88 -0
  168. package/bizar-dash/src/web/v8/ui/settings/SettingsSection.tsx +109 -0
  169. package/bizar-dash/src/web/v8/ui/styles/globals.css +220 -0
  170. package/bizar-dash/src/web/v8/ui/styles/reset.css +57 -0
  171. package/bizar-dash/src/web/v8/ui/styles/tokens.css +217 -0
  172. package/bizar-dash/src/web/v8/ui/theme/DensityProvider.test.tsx +74 -0
  173. package/bizar-dash/src/web/v8/ui/theme/DensityProvider.tsx +66 -0
  174. package/bizar-dash/src/web/v8/ui/theme/ThemeProvider.test.tsx +86 -0
  175. package/bizar-dash/src/web/v8/ui/theme/ThemeProvider.tsx +94 -0
  176. package/bizar-dash/src/web/v8/ui/theme/ThemeToggle.tsx +88 -0
  177. package/bizar-dash/src/web/v8/ui/theme/useDensity.ts +15 -0
  178. package/bizar-dash/src/web/v8/ui/theme/useTheme.ts +16 -0
  179. package/bizar-dash/src/web/v8/ui/utils/cx.ts +19 -0
  180. package/bizar-dash/src/web/v8/views/Activity/ActivityView.tsx +33 -0
  181. package/bizar-dash/src/web/v8/views/Agents/AgentsView.tsx +108 -0
  182. package/bizar-dash/src/web/v8/views/CommandPalette/AppCommandPalette.test.tsx +142 -0
  183. package/bizar-dash/src/web/v8/views/CommandPalette/AppCommandPalette.tsx +144 -0
  184. package/bizar-dash/src/web/v8/views/Goals/GoalsView.tsx +84 -0
  185. package/bizar-dash/src/web/v8/views/Libraries/LibrariesView.tsx +41 -0
  186. package/bizar-dash/src/web/v8/views/Memory/MemoryView.tsx +61 -0
  187. package/bizar-dash/src/web/v8/views/Overview/OverviewView.tsx +92 -0
  188. package/bizar-dash/src/web/v8/views/Router.tsx +96 -0
  189. package/bizar-dash/src/web/v8/views/Settings/SettingsView.tsx +305 -0
  190. package/bizar-dash/src/web/v8/views/Tasks/CommandPalettePlaceholder.tsx +106 -0
  191. package/bizar-dash/src/web/v8/views/Tasks/TasksKanbanPlaceholder.tsx +62 -0
  192. package/bizar-dash/src/web/v8/views/Tasks/TasksView.tsx +74 -0
  193. package/bizar-dash/src/web/v8/vite-env.d.ts +15 -0
  194. package/bizar-dash/src/web/{mobile.html → v8.html} +4 -7
  195. package/bizar-dash/tests/setup.ts +26 -0
  196. package/bizar-dash/vite.config.ts +26 -2
  197. package/bizar-dash/vitest.config.ts +5 -3
  198. package/package.json +36 -3
  199. package/bizar-dash/dist/assets/EnvVarsSection-BfhAz3ax.js +0 -114
  200. package/bizar-dash/dist/assets/EnvVarsSection-BfhAz3ax.js.map +0 -1
  201. package/bizar-dash/dist/assets/MobileChat-DLWdv6tQ.js +0 -1
  202. package/bizar-dash/dist/assets/MobileChat-DLWdv6tQ.js.map +0 -1
  203. package/bizar-dash/dist/assets/MobileSettings-Bxv62uPY.js +0 -1
  204. package/bizar-dash/dist/assets/MobileSettings-Bxv62uPY.js.map +0 -1
  205. package/bizar-dash/dist/assets/Toast-ATSAmbdi.js +0 -26
  206. package/bizar-dash/dist/assets/Toast-ATSAmbdi.js.map +0 -1
  207. package/bizar-dash/dist/assets/__vite-browser-external-BIHI7g3E.js +0 -1
  208. package/bizar-dash/dist/assets/__vite-browser-external-BIHI7g3E.js.map +0 -1
  209. package/bizar-dash/dist/assets/main-CJAtrosO.css +0 -1
  210. package/bizar-dash/dist/assets/main-DKKj9dsq.js +0 -430
  211. package/bizar-dash/dist/assets/main-DKKj9dsq.js.map +0 -1
  212. package/bizar-dash/dist/assets/mobile-C_naUN91.js +0 -1
  213. package/bizar-dash/dist/assets/mobile-C_naUN91.js.map +0 -1
  214. package/bizar-dash/dist/assets/mobile-layout-BWLtwtfQ.css +0 -1
  215. package/bizar-dash/dist/assets/mobile-layout-GZ3bE8L6.js +0 -211
  216. package/bizar-dash/dist/assets/mobile-layout-GZ3bE8L6.js.map +0 -1
  217. package/bizar-dash/dist/assets/useSlashCommands-BOwD7lNb.js +0 -65
  218. package/bizar-dash/dist/assets/useSlashCommands-BOwD7lNb.js.map +0 -1
  219. package/bizar-dash/dist/index.html +0 -43
  220. package/bizar-dash/src/web/App.tsx +0 -915
  221. package/bizar-dash/src/web/MobileApp.tsx +0 -414
  222. package/bizar-dash/src/web/components/ArtifactCreateDialog.tsx +0 -95
  223. package/bizar-dash/src/web/components/ArtifactListDialog.tsx +0 -55
  224. package/bizar-dash/src/web/components/ArtifactViewer.tsx +0 -144
  225. package/bizar-dash/src/web/components/AuditDialog.tsx +0 -79
  226. package/bizar-dash/src/web/components/AutosaveField.tsx +0 -50
  227. package/bizar-dash/src/web/components/BackupRestore.tsx +0 -330
  228. package/bizar-dash/src/web/components/BgStatusBadge.tsx +0 -32
  229. package/bizar-dash/src/web/components/Button.tsx +0 -56
  230. package/bizar-dash/src/web/components/CanvasContextMenu.tsx +0 -68
  231. package/bizar-dash/src/web/components/Card.tsx +0 -40
  232. package/bizar-dash/src/web/components/CollapsibleSection.tsx +0 -72
  233. package/bizar-dash/src/web/components/CommandDialog.tsx +0 -66
  234. package/bizar-dash/src/web/components/DoctorPanel.tsx +0 -160
  235. package/bizar-dash/src/web/components/EmptyState.tsx +0 -30
  236. package/bizar-dash/src/web/components/EnvVarManager.tsx +0 -430
  237. package/bizar-dash/src/web/components/EvalDiff.tsx +0 -157
  238. package/bizar-dash/src/web/components/EvalExportButton.tsx +0 -27
  239. package/bizar-dash/src/web/components/EvalRunCard.tsx +0 -78
  240. package/bizar-dash/src/web/components/FileBrowser.tsx +0 -633
  241. package/bizar-dash/src/web/components/HeadroomSettings.tsx +0 -418
  242. package/bizar-dash/src/web/components/HeadroomStatus.tsx +0 -158
  243. package/bizar-dash/src/web/components/HelpDialog.tsx +0 -55
  244. package/bizar-dash/src/web/components/InviteDialog.tsx +0 -205
  245. package/bizar-dash/src/web/components/KillConfirmDialog.tsx +0 -88
  246. package/bizar-dash/src/web/components/MobileBottomNav.tsx +0 -38
  247. package/bizar-dash/src/web/components/MobileDrawer.tsx +0 -68
  248. package/bizar-dash/src/web/components/MobileHeader.tsx +0 -50
  249. package/bizar-dash/src/web/components/MobileLayout.tsx +0 -63
  250. package/bizar-dash/src/web/components/Modal.tsx +0 -215
  251. package/bizar-dash/src/web/components/Notifications.tsx +0 -242
  252. package/bizar-dash/src/web/components/ScheduleTemplateCard.tsx +0 -72
  253. package/bizar-dash/src/web/components/ScreenshotCapture.tsx +0 -138
  254. package/bizar-dash/src/web/components/ScreenshotOCR.tsx +0 -42
  255. package/bizar-dash/src/web/components/SearchModal.tsx +0 -227
  256. package/bizar-dash/src/web/components/SettingsNav.tsx +0 -117
  257. package/bizar-dash/src/web/components/SettingsSearch.tsx +0 -328
  258. package/bizar-dash/src/web/components/Sidebar.tsx +0 -89
  259. package/bizar-dash/src/web/components/Spinner.tsx +0 -19
  260. package/bizar-dash/src/web/components/StatusBadge.tsx +0 -56
  261. package/bizar-dash/src/web/components/Tag.tsx +0 -41
  262. package/bizar-dash/src/web/components/TailscaleSettings.tsx +0 -161
  263. package/bizar-dash/src/web/components/TaskCard.tsx +0 -69
  264. package/bizar-dash/src/web/components/TaskCreateSheet.tsx +0 -76
  265. package/bizar-dash/src/web/components/Toast.tsx +0 -150
  266. package/bizar-dash/src/web/components/Toggle.tsx +0 -31
  267. package/bizar-dash/src/web/components/Topbar.tsx +0 -455
  268. package/bizar-dash/src/web/components/UsageChart.tsx +0 -250
  269. package/bizar-dash/src/web/components/UsageTable.tsx +0 -90
  270. package/bizar-dash/src/web/components/VirtualList.tsx +0 -53
  271. package/bizar-dash/src/web/components/VisualPlanDialog.tsx +0 -58
  272. package/bizar-dash/src/web/components/VoiceNotesPanel.tsx +0 -211
  273. package/bizar-dash/src/web/components/VoiceRecorder.tsx +0 -105
  274. package/bizar-dash/src/web/components/WorkspaceSelector.tsx +0 -158
  275. package/bizar-dash/src/web/components/agents/CommunicationLog.tsx +0 -126
  276. package/bizar-dash/src/web/components/agents/DependencyGraph.tsx +0 -163
  277. package/bizar-dash/src/web/components/agents/QualityGates.tsx +0 -123
  278. package/bizar-dash/src/web/components/agents/RealTimeEventLog.tsx +0 -127
  279. package/bizar-dash/src/web/components/agents/RoutingDecisions.test.tsx +0 -148
  280. package/bizar-dash/src/web/components/agents/RoutingDecisions.tsx +0 -160
  281. package/bizar-dash/src/web/components/background/AttachButton.tsx +0 -96
  282. package/bizar-dash/src/web/components/background/TmuxAttachCard.tsx +0 -122
  283. package/bizar-dash/src/web/components/chat/AgentChip.tsx +0 -68
  284. package/bizar-dash/src/web/components/chat/AgentNode.tsx +0 -127
  285. package/bizar-dash/src/web/components/chat/AgentTree.tsx +0 -80
  286. package/bizar-dash/src/web/components/chat/ChatBubble.tsx +0 -60
  287. package/bizar-dash/src/web/components/chat/ChatComposer.tsx +0 -72
  288. package/bizar-dash/src/web/components/chat/ChatInfoPanel.tsx +0 -370
  289. package/bizar-dash/src/web/components/chat/ChatRail.tsx +0 -387
  290. package/bizar-dash/src/web/components/chat/ChatThread.tsx +0 -127
  291. package/bizar-dash/src/web/components/chat/ChatTopBar.tsx +0 -50
  292. package/bizar-dash/src/web/components/chat/Composer.tsx +0 -166
  293. package/bizar-dash/src/web/components/chat/ConfirmModal.tsx +0 -54
  294. package/bizar-dash/src/web/components/chat/EmptyState.tsx +0 -21
  295. package/bizar-dash/src/web/components/chat/FirstRunGreeting.tsx +0 -18
  296. package/bizar-dash/src/web/components/chat/FloatingComposer.tsx +0 -38
  297. package/bizar-dash/src/web/components/chat/InfoPanel.tsx +0 -184
  298. package/bizar-dash/src/web/components/chat/JumpToLatest.tsx +0 -58
  299. package/bizar-dash/src/web/components/chat/LoadingSkeleton.tsx +0 -19
  300. package/bizar-dash/src/web/components/chat/MessageBlock.tsx +0 -260
  301. package/bizar-dash/src/web/components/chat/MessageBubble.tsx +0 -60
  302. package/bizar-dash/src/web/components/chat/SessionList.tsx +0 -163
  303. package/bizar-dash/src/web/components/chat/SessionRowMenu.tsx +0 -206
  304. package/bizar-dash/src/web/components/chat/StreamingIndicator.tsx +0 -37
  305. package/bizar-dash/src/web/components/chat/SuggestionCards.tsx +0 -55
  306. package/bizar-dash/src/web/components/chat/WelcomeScreen.tsx +0 -36
  307. package/bizar-dash/src/web/components/chat/_legacy.ts +0 -30
  308. package/bizar-dash/src/web/components/chat/index.ts +0 -31
  309. package/bizar-dash/src/web/components/chat/useAutoGrowTextarea.ts +0 -18
  310. package/bizar-dash/src/web/components/chat/useChat.ts +0 -1190
  311. package/bizar-dash/src/web/components/chat/useSlashCommands.ts +0 -47
  312. package/bizar-dash/src/web/components/goals/GoalInput.tsx +0 -86
  313. package/bizar-dash/src/web/components/goals/PlanVisualization.tsx +0 -111
  314. package/bizar-dash/src/web/components/tasks/BacklogPanel.css +0 -109
  315. package/bizar-dash/src/web/components/tasks/BacklogPanel.tsx +0 -209
  316. package/bizar-dash/src/web/hooks/useAutosave.ts +0 -107
  317. package/bizar-dash/src/web/hooks/useI18n.ts +0 -13
  318. package/bizar-dash/src/web/index.html +0 -37
  319. package/bizar-dash/src/web/lib/api.ts +0 -237
  320. package/bizar-dash/src/web/lib/goapPlanner.ts +0 -614
  321. package/bizar-dash/src/web/lib/i18n.ts +0 -25
  322. package/bizar-dash/src/web/lib/logger.ts +0 -30
  323. package/bizar-dash/src/web/lib/markdown.tsx +0 -59
  324. package/bizar-dash/src/web/lib/search.ts +0 -115
  325. package/bizar-dash/src/web/lib/types.ts +0 -894
  326. package/bizar-dash/src/web/lib/utils.ts +0 -114
  327. package/bizar-dash/src/web/lib/ws.ts +0 -177
  328. package/bizar-dash/src/web/locales/en.json +0 -52
  329. package/bizar-dash/src/web/main.tsx +0 -43
  330. package/bizar-dash/src/web/mobile/MobileApp.tsx +0 -309
  331. package/bizar-dash/src/web/mobile/MobileBottomNav.tsx +0 -38
  332. package/bizar-dash/src/web/mobile/MobileChat.tsx +0 -138
  333. package/bizar-dash/src/web/mobile/MobileDoctor.tsx +0 -80
  334. package/bizar-dash/src/web/mobile/MobileEval.tsx +0 -167
  335. package/bizar-dash/src/web/mobile/MobileMemory.tsx +0 -108
  336. package/bizar-dash/src/web/mobile/MobileOverview.tsx +0 -213
  337. package/bizar-dash/src/web/mobile/MobileSettings.tsx +0 -251
  338. package/bizar-dash/src/web/mobile/MobileTasks.tsx +0 -94
  339. package/bizar-dash/src/web/mobile/MobileTopbar.tsx +0 -115
  340. package/bizar-dash/src/web/mobile/components/MobileBottomSheet.tsx +0 -182
  341. package/bizar-dash/src/web/mobile/components/MobileListItem.tsx +0 -64
  342. package/bizar-dash/src/web/mobile/components/MobileModal.tsx +0 -123
  343. package/bizar-dash/src/web/mobile/views/MobileActivity.tsx +0 -273
  344. package/bizar-dash/src/web/mobile/views/MobileAgents.tsx +0 -374
  345. package/bizar-dash/src/web/mobile/views/MobileArtifactCanvas.tsx +0 -439
  346. package/bizar-dash/src/web/mobile/views/MobileArtifacts.tsx +0 -143
  347. package/bizar-dash/src/web/mobile/views/MobileChat.tsx +0 -257
  348. package/bizar-dash/src/web/mobile/views/MobileConfig.tsx +0 -175
  349. package/bizar-dash/src/web/mobile/views/MobileHistory.tsx +0 -191
  350. package/bizar-dash/src/web/mobile/views/MobileMods.tsx +0 -149
  351. package/bizar-dash/src/web/mobile/views/MobileMore.tsx +0 -121
  352. package/bizar-dash/src/web/mobile/views/MobileNotifications.tsx +0 -137
  353. package/bizar-dash/src/web/mobile/views/MobilePlans.tsx +0 -26
  354. package/bizar-dash/src/web/mobile/views/MobileSchedules.tsx +0 -685
  355. package/bizar-dash/src/web/mobile/views/MobileSearchModal.tsx +0 -172
  356. package/bizar-dash/src/web/mobile/views/MobileSettings.tsx +0 -363
  357. package/bizar-dash/src/web/mobile/views/MobileSkills.tsx +0 -153
  358. package/bizar-dash/src/web/mobile/views/MobileTasks.tsx +0 -564
  359. package/bizar-dash/src/web/mobile/views/QrCodePanel.tsx +0 -69
  360. package/bizar-dash/src/web/mobile.tsx +0 -14
  361. package/bizar-dash/src/web/styles/agents-redesign.css +0 -311
  362. package/bizar-dash/src/web/styles/chat.css +0 -1740
  363. package/bizar-dash/src/web/styles/glyphs.css +0 -960
  364. package/bizar-dash/src/web/styles/main.css +0 -10389
  365. package/bizar-dash/src/web/styles/memory.css +0 -1177
  366. package/bizar-dash/src/web/styles/minimax-usage.css +0 -842
  367. package/bizar-dash/src/web/styles/mobile-chat.css +0 -5
  368. package/bizar-dash/src/web/styles/mobile-layout.css +0 -233
  369. package/bizar-dash/src/web/styles/mobile.css +0 -2181
  370. package/bizar-dash/src/web/styles/settings.css +0 -775
  371. package/bizar-dash/src/web/styles/skills.css +0 -302
  372. package/bizar-dash/src/web/styles/tasks-redesign.css +0 -253
  373. package/bizar-dash/src/web/styles/tasks.css +0 -605
  374. package/bizar-dash/src/web/ui/controls/Button.tsx +0 -77
  375. package/bizar-dash/src/web/ui/controls/Checkbox.tsx +0 -95
  376. package/bizar-dash/src/web/ui/controls/IconButton.tsx +0 -66
  377. package/bizar-dash/src/web/ui/controls/Kbd.tsx +0 -24
  378. package/bizar-dash/src/web/ui/controls/NumberInput.tsx +0 -77
  379. package/bizar-dash/src/web/ui/controls/RadioGroup.tsx +0 -109
  380. package/bizar-dash/src/web/ui/controls/SearchInput.tsx +0 -91
  381. package/bizar-dash/src/web/ui/controls/Select.tsx +0 -92
  382. package/bizar-dash/src/web/ui/controls/Slider.tsx +0 -70
  383. package/bizar-dash/src/web/ui/controls/TextInput.tsx +0 -67
  384. package/bizar-dash/src/web/ui/controls/Textarea.tsx +0 -56
  385. package/bizar-dash/src/web/ui/controls/Toggle.tsx +0 -79
  386. package/bizar-dash/src/web/ui/controls/controls.css +0 -476
  387. package/bizar-dash/src/web/ui/controls/index.ts +0 -35
  388. package/bizar-dash/src/web/ui/data/BarChart.tsx +0 -60
  389. package/bizar-dash/src/web/ui/data/DataTable.tsx +0 -216
  390. package/bizar-dash/src/web/ui/data/EmptyState.tsx +0 -60
  391. package/bizar-dash/src/web/ui/data/ErrorState.tsx +0 -56
  392. package/bizar-dash/src/web/ui/data/KeyValueList.tsx +0 -106
  393. package/bizar-dash/src/web/ui/data/LoadingState.tsx +0 -65
  394. package/bizar-dash/src/web/ui/data/Sparkline.tsx +0 -87
  395. package/bizar-dash/src/web/ui/data/StatTile.tsx +0 -87
  396. package/bizar-dash/src/web/ui/data/data.css +0 -540
  397. package/bizar-dash/src/web/ui/data/index.ts +0 -31
  398. package/bizar-dash/src/web/ui/feedback/Badge.tsx +0 -49
  399. package/bizar-dash/src/web/ui/feedback/Dialog.tsx +0 -209
  400. package/bizar-dash/src/web/ui/feedback/ProgressBar.tsx +0 -69
  401. package/bizar-dash/src/web/ui/feedback/StatusDot.tsx +0 -50
  402. package/bizar-dash/src/web/ui/feedback/Toast.tsx +0 -200
  403. package/bizar-dash/src/web/ui/feedback/Tooltip.tsx +0 -126
  404. package/bizar-dash/src/web/ui/feedback/feedback.css +0 -314
  405. package/bizar-dash/src/web/ui/feedback/index.ts +0 -43
  406. package/bizar-dash/src/web/ui/index.ts +0 -57
  407. package/bizar-dash/src/web/ui/layout/AppShell.tsx +0 -51
  408. package/bizar-dash/src/web/ui/layout/Breadcrumbs.tsx +0 -97
  409. package/bizar-dash/src/web/ui/layout/Panel.tsx +0 -73
  410. package/bizar-dash/src/web/ui/layout/PanelHeader.tsx +0 -39
  411. package/bizar-dash/src/web/ui/layout/Sidebar.tsx +0 -131
  412. package/bizar-dash/src/web/ui/layout/Tabs.tsx +0 -133
  413. package/bizar-dash/src/web/ui/layout/Topbar.tsx +0 -42
  414. package/bizar-dash/src/web/ui/layout/ViewHeader.tsx +0 -48
  415. package/bizar-dash/src/web/ui/layout/index.ts +0 -34
  416. package/bizar-dash/src/web/ui/layout/layout.css +0 -464
  417. package/bizar-dash/src/web/ui/navigation/CommandPalette.tsx +0 -199
  418. package/bizar-dash/src/web/ui/navigation/NavGroup.tsx +0 -95
  419. package/bizar-dash/src/web/ui/navigation/NavLink.tsx +0 -93
  420. package/bizar-dash/src/web/ui/navigation/index.ts +0 -17
  421. package/bizar-dash/src/web/ui/navigation/navigation.css +0 -343
  422. package/bizar-dash/src/web/ui/primitives/Box.tsx +0 -91
  423. package/bizar-dash/src/web/ui/primitives/Grid.tsx +0 -49
  424. package/bizar-dash/src/web/ui/primitives/Inline.tsx +0 -55
  425. package/bizar-dash/src/web/ui/primitives/Separator.tsx +0 -46
  426. package/bizar-dash/src/web/ui/primitives/Stack.tsx +0 -54
  427. package/bizar-dash/src/web/ui/primitives/VisuallyHidden.tsx +0 -26
  428. package/bizar-dash/src/web/ui/primitives/index.ts +0 -23
  429. package/bizar-dash/src/web/ui/primitives/primitives.css +0 -183
  430. package/bizar-dash/src/web/ui/styles/globals.css +0 -86
  431. package/bizar-dash/src/web/ui/styles/reset.css +0 -125
  432. package/bizar-dash/src/web/ui/styles/tokens.css +0 -208
  433. package/bizar-dash/src/web/ui/theme/ThemeProvider.tsx +0 -142
  434. package/bizar-dash/src/web/ui/theme/tokens.ts +0 -131
  435. package/bizar-dash/src/web/ui/theme/useTheme.ts +0 -22
  436. package/bizar-dash/src/web/ui/utils/cx.ts +0 -42
  437. package/bizar-dash/src/web/views/Activity.tsx +0 -1221
  438. package/bizar-dash/src/web/views/Agents.tsx +0 -964
  439. package/bizar-dash/src/web/views/Artifacts.tsx +0 -1494
  440. package/bizar-dash/src/web/views/BackgroundAgents.tsx +0 -822
  441. package/bizar-dash/src/web/views/Chat.tsx +0 -532
  442. package/bizar-dash/src/web/views/Config.tsx +0 -3
  443. package/bizar-dash/src/web/views/Doctor.tsx +0 -317
  444. package/bizar-dash/src/web/views/Eval.tsx +0 -372
  445. package/bizar-dash/src/web/views/EvalReport.tsx +0 -353
  446. package/bizar-dash/src/web/views/GoalPlanner.tsx +0 -158
  447. package/bizar-dash/src/web/views/Harness.tsx +0 -306
  448. package/bizar-dash/src/web/views/History.tsx +0 -353
  449. package/bizar-dash/src/web/views/Memory.tsx +0 -193
  450. package/bizar-dash/src/web/views/MiniMaxUsage.tsx +0 -942
  451. package/bizar-dash/src/web/views/ModView.tsx +0 -207
  452. package/bizar-dash/src/web/views/Mods.tsx +0 -706
  453. package/bizar-dash/src/web/views/Overview.tsx +0 -1343
  454. package/bizar-dash/src/web/views/Providers.tsx +0 -302
  455. package/bizar-dash/src/web/views/Schedules.tsx +0 -902
  456. package/bizar-dash/src/web/views/Settings.tsx +0 -308
  457. package/bizar-dash/src/web/views/Skills.tsx +0 -383
  458. package/bizar-dash/src/web/views/SpawnAgentModal.tsx +0 -221
  459. package/bizar-dash/src/web/views/Tasks.tsx +0 -789
  460. package/bizar-dash/src/web/views/Workspace.tsx +0 -294
  461. package/bizar-dash/src/web/views/glyphs/GlyphRenderer.tsx +0 -844
  462. package/bizar-dash/src/web/views/glyphs/components.tsx +0 -1098
  463. package/bizar-dash/src/web/views/memory/ConfigPanel.tsx +0 -426
  464. package/bizar-dash/src/web/views/memory/FromScreenshotPanel.tsx +0 -23
  465. package/bizar-dash/src/web/views/memory/GitSyncPanel.tsx +0 -220
  466. package/bizar-dash/src/web/views/memory/LightragPanel.tsx +0 -310
  467. package/bizar-dash/src/web/views/memory/MemoryGraphLegend.tsx +0 -29
  468. package/bizar-dash/src/web/views/memory/MemoryGraphPanel.tsx +0 -192
  469. package/bizar-dash/src/web/views/memory/MemoryGraphView.tsx +0 -336
  470. package/bizar-dash/src/web/views/memory/MemoryOverview.tsx +0 -367
  471. package/bizar-dash/src/web/views/memory/MemoryStatusCard.tsx +0 -160
  472. package/bizar-dash/src/web/views/memory/ObsidianPanel.tsx +0 -650
  473. package/bizar-dash/src/web/views/memory/SemanticSearchPanel.tsx +0 -197
  474. package/bizar-dash/src/web/views/memory/VaultFromClipboardPanel.tsx +0 -101
  475. package/bizar-dash/src/web/views/settings/ActivitySection.tsx +0 -205
  476. package/bizar-dash/src/web/views/settings/AgentSection.tsx +0 -305
  477. package/bizar-dash/src/web/views/settings/AuthSection.tsx +0 -159
  478. package/bizar-dash/src/web/views/settings/EnvVarsSection.tsx +0 -15
  479. package/bizar-dash/src/web/views/settings/GeneralSection.tsx +0 -128
  480. package/bizar-dash/src/web/views/settings/HeadroomSection.tsx +0 -39
  481. package/bizar-dash/src/web/views/settings/MemorySection.tsx +0 -154
  482. package/bizar-dash/src/web/views/settings/NetworkSection.tsx +0 -87
  483. package/bizar-dash/src/web/views/settings/NotificationsSection.tsx +0 -34
  484. package/bizar-dash/src/web/views/settings/SystemLlmSection.tsx +0 -81
  485. package/bizar-dash/src/web/views/settings/ThemeSection.tsx +0 -168
  486. package/bizar-dash/src/web/views/settings/UpdatesSection.tsx +0 -256
  487. package/bizar-dash/src/web/views/settings/WorkspacesSection.tsx +0 -189
  488. package/packages/sdk/.harness/agents.json +0 -17
  489. package/packages/sdk/.harness/topology.json +0 -4
@@ -1,789 +0,0 @@
1
- /*
2
- * Tasks.tsx — Wave 3 redesigned kanban board (Supabase-style simplicity).
3
- *
4
- * The view groups tasks into 5 columns by API status (queued | doing | done
5
- * | blocked | backlog) and renders each column as a `Panel` from the new
6
- * design system. Task rows are compact (~76px) cards with a left-edge
7
- * priority accent (3px) derived from the priority token. The redesign
8
- * intentionally uses only design-system primitives (Panel, Grid, Stack,
9
- * Inline, Badge, StatusDot, Button, IconButton, SearchInput, Select,
10
- * EmptyState, LoadingState) — no legacy `.task-card` / `.kanban-column`
11
- * classes from main.css.
12
- *
13
- * Hard constraints preserved from the previous implementation:
14
- * - Same export name (`Tasks`) and same `Props` shape so App.tsx keeps
15
- * importing without changes.
16
- * - Same API contracts (`api.get('/tasks')`, `api.patch(.../status)`, etc).
17
- * - Same WS subscriptions (`tasks:change`, `tasks:delete`).
18
- * - Same COLUMNS array — the API status enum is the public contract.
19
- * - BacklogPanel is still imported from `components/tasks/BacklogPanel`
20
- * and receives the same props (out-of-scope for this redesign).
21
- * - Legacy `Modal` is reused for the create/edit dialogs (out-of-scope).
22
- * - 30s tick for relative-time labels.
23
- *
24
- * What changed:
25
- * - Columns are now `Panel`s with a StatusDot + count in the header.
26
- * - Task rows render with `Badge` for status/priority/agent and
27
- * `IconButton` for actions (edit, submit-to-odin, retry, delete).
28
- * - The whole task row is clickable (delegates to the edit modal) —
29
- * action buttons stop propagation so they keep their dedicated path.
30
- * - Toolbar uses `SearchInput` + `Select` (priority) instead of raw
31
- * inputs.
32
- */
33
- import React, { useEffect, useMemo, useState } from 'react';
34
- import {
35
- CheckSquare,
36
- Plus,
37
- Trash2,
38
- RefreshCw,
39
- Tag as TagIcon,
40
- ArchiveRestore,
41
- RotateCw,
42
- Send,
43
- Inbox,
44
- Edit2,
45
- Bot,
46
- } from 'lucide-react';
47
- import { Button } from '../components/Button';
48
- import { Card, CardTitle, CardMeta } from '../components/Card';
49
- import { useModal } from '../components/Modal';
50
- import { useToast } from '../components/Toast';
51
- import { api, enhancePrompt } from '../lib/api';
52
- import { formatRelative } from '../lib/utils';
53
- import type { Settings, Snapshot, Task } from '../lib/types';
54
- import { BacklogPanel } from '../components/tasks/BacklogPanel';
55
- import {
56
- Badge,
57
- cx,
58
- Grid,
59
- IconButton,
60
- Inline,
61
- LoadingState,
62
- Panel,
63
- SearchInput,
64
- Select,
65
- Stack,
66
- StatusDot,
67
- type BadgeVariant,
68
- } from '../ui';
69
-
70
- import '../styles/tasks-redesign.css';
71
-
72
- type Props = {
73
- snapshot: Snapshot;
74
- settings: Settings;
75
- activeTab: string;
76
- setActiveTab: (id: string) => void;
77
- refreshSnapshot: () => Promise<void>;
78
- };
79
-
80
- type StatusKind = 'info' | 'accent' | 'success' | 'warning' | 'error';
81
- type PriorityKind = 'low' | 'normal' | 'high';
82
-
83
- /**
84
- * UI <-> API status mapping. We keep the existing API enum
85
- * (queued | doing | done | blocked | archived | backlog) and only
86
- * rename the labels here so the dashboard, server, and tests stay in
87
- * sync. Switch back if you need to expose the raw API value.
88
- */
89
- const COLUMNS: {
90
- id: Task['status'];
91
- label: string;
92
- kind: StatusKind;
93
- dotVariant: 'info' | 'success' | 'warning' | 'danger';
94
- }[] = [
95
- { id: 'queued', label: 'Todo', kind: 'info', dotVariant: 'info' },
96
- { id: 'doing', label: 'In progress', kind: 'accent', dotVariant: 'info' },
97
- { id: 'done', label: 'Done', kind: 'success', dotVariant: 'success' },
98
- { id: 'blocked', label: 'Failed', kind: 'error', dotVariant: 'danger' },
99
- ];
100
-
101
- const PRIORITIES: readonly PriorityKind[] = ['low', 'normal', 'high'];
102
-
103
- const PRIORITY_OPTIONS = [
104
- { value: '', label: 'All' },
105
- ...PRIORITIES.map((p) => ({ value: p, label: p })),
106
- ];
107
-
108
- const STATUS_BADGE: Record<StatusKind, BadgeVariant> = {
109
- info: 'info',
110
- accent: 'accent',
111
- success: 'success',
112
- warning: 'warning',
113
- error: 'danger',
114
- };
115
-
116
- const PRIORITY_BADGE: Record<PriorityKind, BadgeVariant> = {
117
- high: 'danger',
118
- normal: 'info',
119
- low: 'neutral',
120
- };
121
-
122
- function TasksInner({
123
- snapshot,
124
- refreshSnapshot,
125
- }: Props) {
126
- const toast = useToast();
127
- const modal = useModal();
128
- const [tasks, setTasks] = useState<Task[]>(snapshot.tasks || []);
129
- const [loading, setLoading] = useState(!snapshot.tasks);
130
- const [filter, setFilter] = useState('');
131
- const [priorityFilter, setPriorityFilter] = useState<string>('');
132
- const [showBacklog, setShowBacklog] = useState(false);
133
- const [tick, setTick] = useState(0); // for live timer re-render
134
- const [statusAnnouncement, setStatusAnnouncement] = useState('');
135
-
136
- const reload = async () => {
137
- try {
138
- const data = await api.get<Task[]>('/tasks');
139
- setTasks(Array.isArray(data) ? data : []);
140
- } catch (err) {
141
- toast.error(`Tasks load failed: ${(err as Error).message}`);
142
- } finally {
143
- setLoading(false);
144
- }
145
- };
146
-
147
- useEffect(() => {
148
- if (snapshot.tasks) {
149
- setTasks(snapshot.tasks);
150
- setLoading(false);
151
- }
152
- }, [snapshot.tasks]);
153
-
154
- // Periodic tick keeps relative-time labels fresh without a full reload.
155
- useEffect(() => {
156
- const id = setInterval(() => setTick((t) => t + 1), 30_000);
157
- return () => clearInterval(id);
158
- }, []);
159
-
160
- const filtered = useMemo(() => {
161
- let out = tasks.filter((t) => t.status !== 'backlog');
162
- if (priorityFilter) {
163
- out = out.filter((t) => (t.priority || 'normal') === priorityFilter);
164
- }
165
- if (filter.trim()) {
166
- const q = filter.toLowerCase();
167
- out = out.filter((t) =>
168
- (t.title || '').toLowerCase().includes(q) ||
169
- (t.description || '').toLowerCase().includes(q),
170
- );
171
- }
172
- return out;
173
- }, [tasks, filter, priorityFilter]);
174
-
175
- const sorted = useMemo(() => {
176
- const priorityWeight = { high: 0, normal: 1, low: 2 } as Record<string, number>;
177
- return [...filtered].sort((a, b) => {
178
- const pa = priorityWeight[a.priority] ?? 1;
179
- const pb = priorityWeight[b.priority] ?? 1;
180
- if (pa !== pb) return pa - pb;
181
- return new Date(b.createdAt).getTime() - new Date(a.createdAt).getTime();
182
- });
183
- }, [filtered]);
184
-
185
- const backlogCount = tasks.filter((t) => t.status === 'backlog').length;
186
-
187
- // ─── Actions ─────────────────────────────────────────────────────────────
188
-
189
- const moveTask = async (taskId: string, newStatus: string) => {
190
- const t = tasks.find((x) => x.id === taskId);
191
- if (!t) return;
192
- const prev = t.status;
193
- setTasks((cur) =>
194
- cur.map((x) => (x.id === taskId ? { ...x, status: newStatus } : x)),
195
- );
196
- setStatusAnnouncement(`Task ${t.title} moved to ${newStatus}.`);
197
- try {
198
- await api.patch(`/tasks/${encodeURIComponent(taskId)}/status`, {
199
- status: newStatus,
200
- });
201
- toast.success(`Moved to ${newStatus}.`, 1200);
202
- } catch (err) {
203
- setTasks((cur) =>
204
- cur.map((x) => (x.id === taskId ? { ...x, status: prev } : x)),
205
- );
206
- setStatusAnnouncement(`Failed to move task ${t.title}: ${(err as Error).message}`);
207
- toast.error(`Move failed: ${(err as Error).message}`);
208
- }
209
- };
210
-
211
- const deleteTask = async (taskId: string) => {
212
- if (!confirm('Delete this task?')) return;
213
- try {
214
- await api.del(`/tasks/${encodeURIComponent(taskId)}`);
215
- setTasks((cur) => cur.filter((t) => t.id !== taskId));
216
- toast.success('Task deleted.', 1200);
217
- } catch (err) {
218
- toast.error(`Delete failed: ${(err as Error).message}`);
219
- }
220
- };
221
-
222
- const retryTask = async (taskId: string) => {
223
- try {
224
- // Re-dispatch via the existing /tasks/:id/start endpoint. The
225
- // server returns 202 on accept; failures surface as 502/404.
226
- const r = await api.post<{ ok: boolean; task: Task }>(
227
- `/tasks/${encodeURIComponent(taskId)}/start`,
228
- );
229
- if (r && r.task) {
230
- setTasks((cur) => cur.map((t) => (t.id === taskId ? r.task : t)));
231
- }
232
- toast.success('Retry dispatched.', 1200);
233
- } catch (err) {
234
- toast.error(`Retry failed: ${(err as Error).message}`);
235
- }
236
- };
237
-
238
- const submitToOdin = async (taskId: string) => {
239
- const t = tasks.find((x) => x.id === taskId);
240
- if (!t) return;
241
- try {
242
- // The /tasks/submit endpoint takes a title + description and
243
- // hands the bundle to Odin for delegation. We re-use the task's
244
- // existing fields.
245
- const r = await api.post<{ main: Task; subtasks: Task[] }>('/tasks/submit', {
246
- title: t.title,
247
- description: t.description,
248
- priority: t.priority,
249
- tags: t.tags,
250
- });
251
- const count = (r.subtasks || []).length;
252
- toast.success(
253
- count > 1
254
- ? `Odin split it into ${count} subtasks.`
255
- : 'Sent to Odin.',
256
- 1500,
257
- );
258
- if (r.subtasks && r.subtasks.length > 0) {
259
- setTasks((cur) => [r.main, ...r.subtasks, ...cur.filter((x) => x.id !== t.id)]);
260
- }
261
- await refreshSnapshot();
262
- } catch (err) {
263
- toast.error(`Submit failed: ${(err as Error).message}`);
264
- }
265
- };
266
-
267
- const handleTaskClick = (task: Task) => {
268
- openEditTaskModal(modal, toast, task, setTasks, reload, refreshSnapshot);
269
- };
270
-
271
- return (
272
- <div className="view view-tasks tasks-wave3">
273
- {/* Hidden live region for screen-reader announcements of status changes. */}
274
- <div className="sr-only" role="status" aria-live="polite">
275
- {statusAnnouncement}
276
- </div>
277
- <header className="tasks-wave3__header">
278
- <div>
279
- <h2 className="tasks-wave3__title-row">
280
- <CheckSquare size={18} aria-hidden /> Tasks ({sorted.length})
281
- </h2>
282
- <p className="tasks-wave3__subtitle">
283
- Add a task — title and description is all you need. Odin picks the agent and priority.
284
- </p>
285
- </div>
286
- </header>
287
-
288
- {/* Toolbar: search, priority filter, refresh, backlog toggle, new task */}
289
- <div className="tasks-wave3__toolbar" role="toolbar" aria-label="Task filters">
290
- <div className="tasks-wave3__toolbar-group">
291
- <SearchInput
292
- inputSize="sm"
293
- value={filter}
294
- onChange={((v: unknown) => setFilter(String(v))) as unknown as React.ComponentProps<typeof SearchInput>['onChange']}
295
- placeholder="Search…"
296
- aria-label="Search tasks"
297
- />
298
- </div>
299
-
300
- <div className="tasks-wave3__toolbar-group">
301
- <span className="tasks-wave3__toolbar-label" id="tasks-priority-filter-label">
302
- Priority
303
- </span>
304
- <Select
305
- inputSize="sm"
306
- aria-labelledby="tasks-priority-filter-label"
307
- options={PRIORITY_OPTIONS}
308
- value={priorityFilter}
309
- onChange={(e) => setPriorityFilter((e.target as HTMLSelectElement).value)}
310
- />
311
- </div>
312
-
313
- <div className="tasks-wave3__toolbar-spacer" />
314
-
315
- <div className="tasks-wave3__toolbar-group">
316
- <Button
317
- variant="ghost"
318
- size="sm"
319
- onClick={reload}
320
- title="Refresh"
321
- aria-label="Refresh tasks"
322
- >
323
- <RefreshCw size={14} aria-hidden />
324
- </Button>
325
- {backlogCount > 0 && (
326
- <Button
327
- variant={showBacklog ? 'accent' : 'ghost'}
328
- size="sm"
329
- onClick={() => setShowBacklog((v) => !v)}
330
- title={showBacklog ? 'Hide backlog' : 'Show backlog'}
331
- >
332
- <Inbox size={14} aria-hidden />
333
- Backlog
334
- <span className="tasks-wave3__column-count" aria-label={`${backlogCount} items`}>
335
- {backlogCount}
336
- </span>
337
- </Button>
338
- )}
339
- <Button
340
- variant="primary"
341
- size="sm"
342
- onClick={() => openCreateTaskModal(modal, toast, setTasks, reload, refreshSnapshot)}
343
- >
344
- <Plus size={14} aria-hidden /> New task
345
- </Button>
346
- </div>
347
- </div>
348
-
349
- {showBacklog && backlogCount > 0 && (
350
- <BacklogPanel
351
- agents={snapshot.agents || []}
352
- onRefresh={refreshSnapshot}
353
- />
354
- )}
355
-
356
- {loading ? (
357
- <LoadingState label="Loading tasks…" />
358
- ) : (
359
- <Grid cols={5} gap={3} className="tasks-wave3__kanban">
360
- {COLUMNS.map((col) => {
361
- const columnTasks = sorted.filter((t) => t.status === col.id);
362
- return (
363
- <Panel
364
- key={col.id}
365
- padding={3}
366
- className="tasks-wave3__column"
367
- title={
368
- <span className="tasks-wave3__column-title">
369
- <StatusDot variant={col.dotVariant} size="sm" label={col.label} />
370
- {col.label}
371
- </span>
372
- }
373
- actions={
374
- <span
375
- className="tasks-wave3__column-count"
376
- aria-label={`${columnTasks.length} tasks`}
377
- >
378
- {columnTasks.length}
379
- </span>
380
- }
381
- >
382
- <Stack gap={2} className="tasks-wave3__column-body">
383
- {columnTasks.length === 0 ? (
384
- <div className="tasks-wave3__column-empty">No tasks</div>
385
- ) : (
386
- columnTasks.map((t) => (
387
- <TaskRow
388
- key={t.id}
389
- task={t}
390
- column={col}
391
- onTaskClick={handleTaskClick}
392
- onEdit={() => openEditTaskModal(modal, toast, t, setTasks, reload, refreshSnapshot)}
393
- onDelete={() => deleteTask(t.id)}
394
- onRetry={() => retryTask(t.id)}
395
- onSubmitToOdin={() => submitToOdin(t.id)}
396
- tick={tick}
397
- />
398
- ))
399
- )}
400
- </Stack>
401
- </Panel>
402
- );
403
- })}
404
- </Grid>
405
- )}
406
- </div>
407
- );
408
- }
409
-
410
- // ─── Row ─────────────────────────────────────────────────────────────────
411
-
412
- type RowProps = {
413
- task: Task;
414
- column: (typeof COLUMNS)[number];
415
- onTaskClick: (task: Task) => void;
416
- onEdit: () => void;
417
- onDelete: () => void;
418
- onRetry: () => void;
419
- onSubmitToOdin: () => void;
420
- tick: number;
421
- };
422
-
423
- function TaskRow({
424
- task,
425
- column,
426
- onTaskClick,
427
- onEdit,
428
- onDelete,
429
- onRetry,
430
- onSubmitToOdin,
431
- tick,
432
- }: RowProps) {
433
- const assignedAgent = task.workedBy || task.assignee || null;
434
- const priority: PriorityKind = (PRIORITIES as readonly string[]).includes(task.priority as string)
435
- ? (task.priority as PriorityKind)
436
- : 'normal';
437
- return (
438
- <div
439
- className={cx('tasks-wave3__row')}
440
- data-task-id={task.id}
441
- data-tick={tick}
442
- role="button"
443
- tabIndex={0}
444
- onClick={() => onTaskClick(task)}
445
- onKeyDown={(e) => {
446
- if (e.key === 'Enter' || e.key === ' ') {
447
- e.preventDefault();
448
- onTaskClick(task);
449
- }
450
- }}
451
- >
452
- <div className="tasks-wave3__row-title-row">
453
- <div className="tasks-wave3__row-title" title={task.title}>
454
- {task.title}
455
- </div>
456
- <Badge variant={STATUS_BADGE[column.kind]} size="sm" aria-label={`Status ${column.label}`}>
457
- {column.label}
458
- </Badge>
459
- </div>
460
-
461
- <Inline gap={1} align="center" className="tasks-wave3__row-badges">
462
- <Badge variant={PRIORITY_BADGE[priority]} size="sm">
463
- {priority}
464
- </Badge>
465
- {assignedAgent && (
466
- <Badge variant="neutral" size="sm">
467
- <Bot size={10} aria-hidden /> @{assignedAgent}
468
- </Badge>
469
- )}
470
- {(task.tags || []).slice(0, 2).map((tag) => (
471
- <Badge key={tag} variant="neutral" size="sm">
472
- #{tag}
473
- </Badge>
474
- ))}
475
- </Inline>
476
-
477
- <div className="tasks-wave3__row-footer">
478
- <span className="tasks-wave3__row-time">{formatRelative(task.createdAt)}</span>
479
- <Inline
480
- gap={1}
481
- align="center"
482
- className="tasks-wave3__row-actions"
483
- onClick={(e) => e.stopPropagation()}
484
- >
485
- <IconButton
486
- variant="ghost"
487
- size="sm"
488
- icon={<Edit2 size={12} aria-hidden />}
489
- aria-label="Edit task"
490
- title="Edit"
491
- onClick={onEdit}
492
- />
493
- <IconButton
494
- variant="ghost"
495
- size="sm"
496
- icon={<Send size={12} aria-hidden />}
497
- aria-label="Submit to Odin"
498
- title="Re-delegate to Odin"
499
- onClick={onSubmitToOdin}
500
- />
501
- <IconButton
502
- variant="ghost"
503
- size="sm"
504
- icon={<RotateCw size={12} aria-hidden />}
505
- aria-label="Retry task"
506
- title="Retry"
507
- onClick={onRetry}
508
- />
509
- <IconButton
510
- variant="danger"
511
- size="sm"
512
- icon={<Trash2 size={12} aria-hidden />}
513
- aria-label="Delete task"
514
- title="Delete"
515
- onClick={onDelete}
516
- />
517
- </Inline>
518
- </div>
519
- </div>
520
- );
521
- }
522
-
523
- // ─── Create / Edit modal ───────────────────────────────────────────────────
524
- //
525
- // Simplified: title, description, priority hint, optional tags. NO
526
- // agent dropdown. The store will default `assignee` and `workedBy` to
527
- // null; the orchestrator sets them when it picks the task up.
528
-
529
- function openCreateTaskModal(
530
- modal: ReturnType<typeof useModal>,
531
- toast: ReturnType<typeof useToast>,
532
- setTasks: (updater: (cur: Task[]) => Task[]) => void,
533
- reload: () => Promise<void>,
534
- refreshSnapshot: () => Promise<void>,
535
- ) {
536
- let titleEl: HTMLInputElement | null = null;
537
- let descEl: HTMLTextAreaElement | null = null;
538
- let tagsEl: HTMLInputElement | null = null;
539
- let priorityEl: HTMLSelectElement | null = null;
540
-
541
- const submit = async (e?: React.SyntheticEvent) => {
542
- if (e && typeof e.preventDefault === 'function') e.preventDefault();
543
- const title = (titleEl?.value || '').trim();
544
- const description = (descEl?.value || '').trim();
545
- if (!title) {
546
- toast.warning('Title is required.');
547
- titleEl?.focus();
548
- return;
549
- }
550
- const priority = (priorityEl?.value || 'normal') as PriorityKind;
551
- const tags = (tagsEl?.value || '')
552
- .split(',')
553
- .map((s) => s.trim())
554
- .filter(Boolean);
555
-
556
- try {
557
- const created = await api.post<Task>('/tasks', {
558
- title,
559
- description,
560
- priority,
561
- tags,
562
- // No assignee / agent — Odin decides.
563
- });
564
- modal.close();
565
- // Synthetic mousedown is intentional: it signals any open outside-
566
- // click listeners (e.g. WorkspaceSelector, Notifications popover)
567
- // that another surface has just stolen focus, so they collapse
568
- // before the toast overlays the layout. The event carries no
569
- // coordinates by design — those listeners only check the dispatch.
570
- if (typeof window !== 'undefined') {
571
- window.dispatchEvent(new MouseEvent('mousedown'));
572
- }
573
- setTasks((cur) => [created, ...cur]);
574
- toast.success('Task created.', 1200);
575
- await refreshSnapshot();
576
- } catch (err) {
577
- toast.error(`Create failed: ${(err as Error).message}`);
578
- }
579
- };
580
-
581
- const onTitleKeyDown = (e: React.KeyboardEvent<HTMLInputElement>) => {
582
- if (e.key === 'Enter' && !e.shiftKey) {
583
- e.preventDefault();
584
- submit(e);
585
- }
586
- };
587
-
588
- modal.open({
589
- title: 'New task',
590
- width: 520,
591
- children: (
592
- <div className="task-form">
593
- <label className="field-label" htmlFor="task-title">Title *</label>
594
- <input
595
- ref={(el) => { titleEl = el; }}
596
- id="task-title"
597
- className="input"
598
- type="text"
599
- maxLength={200}
600
- placeholder="What needs to be done?"
601
- autoFocus
602
- onKeyDown={onTitleKeyDown}
603
- />
604
- <label className="field-label" htmlFor="task-desc">Description</label>
605
- <div style={{ display: 'flex', gap: 6, alignItems: 'flex-start' }}>
606
- <textarea
607
- ref={(el) => { descEl = el; }}
608
- id="task-desc"
609
- className="textarea"
610
- rows={4}
611
- placeholder="Add any context Odin might need (markdown ok)…"
612
- style={{ flex: 1 }}
613
- />
614
- <button
615
- type="button"
616
- className="btn btn-ghost btn-icon"
617
- title="Enhance with AI"
618
- onClick={async () => {
619
- if (!descEl?.value?.trim()) return;
620
- const enhanced = await enhancePrompt(descEl.value);
621
- if (enhanced !== descEl.value) descEl.value = enhanced;
622
- }}
623
- >
624
-
625
- </button>
626
- </div>
627
- <div className="task-form-row">
628
- <label htmlFor="task-priority" className="task-form-field">
629
- Priority hint
630
- <select
631
- ref={(el) => { priorityEl = el; }}
632
- id="task-priority"
633
- className="select"
634
- defaultValue="normal"
635
- >
636
- {PRIORITIES.map((p) => (
637
- <option key={p} value={p}>{p}</option>
638
- ))}
639
- </select>
640
- </label>
641
- <label htmlFor="task-tags" className="task-form-field" style={{ flex: 2 }}>
642
- Tags <span className="field-hint">(comma-separated)</span>
643
- <input
644
- ref={(el) => { tagsEl = el; }}
645
- id="task-tags"
646
- className="input"
647
- type="text"
648
- placeholder="bug, frontend, urgent"
649
- />
650
- </label>
651
- </div>
652
- <p className="muted text-sm" style={{ marginTop: 8 }}>
653
- The agent and final priority are decided by Odin after you submit.
654
- </p>
655
- </div>
656
- ),
657
- footer: (
658
- <div className="modal-footer-actions">
659
- <Button variant="ghost" onClick={() => modal.close()}>Cancel</Button>
660
- <Button variant="primary" type="button" onClick={(e) => submit(e)}>
661
- <Plus size={14} /> Create task
662
- </Button>
663
- </div>
664
- ),
665
- });
666
- }
667
-
668
- function openEditTaskModal(
669
- modal: ReturnType<typeof useModal>,
670
- toast: ReturnType<typeof useToast>,
671
- task: Task,
672
- setTasks: (updater: (cur: Task[]) => Task[]) => void,
673
- reload: () => Promise<void>,
674
- refreshSnapshot: () => Promise<void>,
675
- ) {
676
- let titleEl: HTMLInputElement | null = null;
677
- let descEl: HTMLTextAreaElement | null = null;
678
- let tagsEl: HTMLInputElement | null = null;
679
- let priorityEl: HTMLSelectElement | null = null;
680
-
681
- const submit = async () => {
682
- const title = (titleEl?.value || '').trim();
683
- const description = (descEl?.value || '').trim();
684
- if (!title) {
685
- toast.warning('Title is required.');
686
- titleEl?.focus();
687
- return;
688
- }
689
- const priority = (priorityEl?.value || 'normal') as PriorityKind;
690
- const tags = (tagsEl?.value || '')
691
- .split(',')
692
- .map((s) => s.trim())
693
- .filter(Boolean);
694
-
695
- try {
696
- const updated = await api.put<Task>(`/tasks/${encodeURIComponent(task.id)}`, {
697
- title,
698
- description,
699
- priority,
700
- tags,
701
- });
702
- modal.close();
703
- // Synthetic mousedown is intentional: it signals any open outside-
704
- // click listeners (e.g. WorkspaceSelector, Notifications popover)
705
- // that another surface has just stolen focus, so they collapse
706
- // before the toast overlays the layout. The event carries no
707
- // coordinates by design — those listeners only check the dispatch.
708
- if (typeof window !== 'undefined') {
709
- window.dispatchEvent(new MouseEvent('mousedown'));
710
- }
711
- setTasks((cur) => cur.map((x) => (x.id === task.id ? updated : x)));
712
- toast.success('Task updated.', 1200);
713
- await refreshSnapshot();
714
- } catch (err) {
715
- toast.error(`Save failed: ${(err as Error).message}`);
716
- }
717
- };
718
-
719
- modal.open({
720
- title: 'Edit task',
721
- width: 520,
722
- children: (
723
- <div className="task-form">
724
- <label className="field-label" htmlFor="edit-task-title">Title *</label>
725
- <input
726
- ref={(el) => { titleEl = el; }}
727
- id="edit-task-title"
728
- className="input"
729
- type="text"
730
- maxLength={200}
731
- defaultValue={task.title}
732
- autoFocus
733
- />
734
- <label className="field-label" htmlFor="edit-task-desc">Description</label>
735
- <textarea
736
- ref={(el) => { descEl = el; }}
737
- id="edit-task-desc"
738
- className="textarea"
739
- rows={4}
740
- defaultValue={task.description || ''}
741
- />
742
- <div className="task-form-row">
743
- <label htmlFor="edit-task-priority" className="task-form-field">
744
- Priority hint
745
- <select
746
- ref={(el) => { priorityEl = el; }}
747
- id="edit-task-priority"
748
- className="select"
749
- defaultValue={task.priority || 'normal'}
750
- >
751
- {PRIORITIES.map((p) => (
752
- <option key={p} value={p}>{p}</option>
753
- ))}
754
- </select>
755
- </label>
756
- <label htmlFor="edit-task-tags" className="task-form-field" style={{ flex: 2 }}>
757
- Tags
758
- <input
759
- ref={(el) => { tagsEl = el; }}
760
- id="edit-task-tags"
761
- className="input"
762
- type="text"
763
- defaultValue={(task.tags || []).join(', ')}
764
- placeholder="comma-separated"
765
- />
766
- </label>
767
- </div>
768
- <Card>
769
- <CardTitle><TagIcon size={12} /> Status</CardTitle>
770
- <CardMeta>
771
- Current: <strong>{task.status}</strong>
772
- {task.workedBy && <> · Worked by @{task.workedBy}</>}
773
- {task.assignee && !task.workedBy && <> · Assigned @{task.assignee}</>}
774
- </CardMeta>
775
- </Card>
776
- </div>
777
- ),
778
- footer: (
779
- <div className="modal-footer-actions">
780
- <Button variant="ghost" onClick={() => modal.close()}>Cancel</Button>
781
- <Button variant="primary" onClick={submit}>
782
- <ArchiveRestore size={14} /> Save
783
- </Button>
784
- </div>
785
- ),
786
- });
787
- }
788
-
789
- export const Tasks = React.memo(TasksInner);