@dungle-scrubs/admin-ui-soft 0.0.0-stage → 0.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 (557) hide show
  1. package/GUIDE.md +110 -0
  2. package/LICENSE +21 -0
  3. package/README.md +36 -2
  4. package/THIRD-PARTY-NOTICES.md +25 -0
  5. package/UPSTREAM-VENDORED-CHANGES.md +317 -0
  6. package/VENDORED-CHANGES.md +60 -0
  7. package/dist/_virtual/_rolldown/runtime.js +13 -0
  8. package/dist/ai/compositions/agent-console/agent-console.d.ts +109 -0
  9. package/dist/ai/compositions/agent-console/agent-console.js +644 -0
  10. package/dist/ai/compositions/attention-feed/attention-feed.d.ts +127 -0
  11. package/dist/ai/compositions/attention-feed/attention-feed.js +626 -0
  12. package/dist/ai/compositions/conversation-browser/conversation-browser.d.ts +126 -0
  13. package/dist/ai/compositions/conversation-browser/conversation-browser.js +364 -0
  14. package/dist/ai/compositions/redaction-marker/redaction-marker.d.ts +42 -0
  15. package/dist/ai/compositions/redaction-marker/redaction-marker.js +202 -0
  16. package/dist/ai/compositions/run-inspector/json-view.js +164 -0
  17. package/dist/ai/compositions/run-inspector/run-inspector.d.ts +66 -0
  18. package/dist/ai/compositions/run-inspector/run-inspector.js +703 -0
  19. package/dist/ai/compositions/run-inspector/run-model.js +155 -0
  20. package/dist/ai/compositions/tool-approval/json-args.js +54 -0
  21. package/dist/ai/compositions/tool-approval/tool-approval.d.ts +57 -0
  22. package/dist/ai/compositions/tool-approval/tool-approval.js +331 -0
  23. package/dist/ai/compositions/tool-call-row/tool-call-row.js +74 -0
  24. package/dist/ai/compositions/transcript-viewer/to-thread-messages.js +65 -0
  25. package/dist/ai/compositions/transcript-viewer/transcript-viewer.d.ts +63 -0
  26. package/dist/ai/compositions/transcript-viewer/transcript-viewer.js +471 -0
  27. package/dist/ai/compositions/usage-meter/usage-format.js +107 -0
  28. package/dist/ai/compositions/usage-meter/usage-meter.d.ts +32 -0
  29. package/dist/ai/compositions/usage-meter/usage-meter.js +258 -0
  30. package/dist/ai/testing/mock-clock.d.ts +31 -0
  31. package/dist/ai/testing/mock-clock.js +66 -0
  32. package/dist/ai/testing/mock-reply.d.ts +70 -0
  33. package/dist/ai/testing/mock-reply.js +100 -0
  34. package/dist/ai/testing/mock-runtime.d.ts +86 -0
  35. package/dist/ai/testing/mock-runtime.js +384 -0
  36. package/dist/ai/types.d.ts +323 -0
  37. package/dist/ai.css +1088 -0
  38. package/dist/ai.d.ts +160 -0
  39. package/dist/ai.js +158 -0
  40. package/dist/components/assistant-ui/elements/activity-graph.d.ts +14 -0
  41. package/dist/components/assistant-ui/elements/activity-graph.js +69 -0
  42. package/dist/components/assistant-ui/elements/agent-card.d.ts +21 -0
  43. package/dist/components/assistant-ui/elements/agent-card.js +75 -0
  44. package/dist/components/assistant-ui/elements/agent-handoff.d.ts +13 -0
  45. package/dist/components/assistant-ui/elements/agent-handoff.js +47 -0
  46. package/dist/components/assistant-ui/elements/agent-plan.d.ts +16 -0
  47. package/dist/components/assistant-ui/elements/agent-plan.js +93 -0
  48. package/dist/components/assistant-ui/elements/agent-status.aui.d.ts +24 -0
  49. package/dist/components/assistant-ui/elements/agent-status.aui.js +161 -0
  50. package/dist/components/assistant-ui/elements/agent-status.d.ts +17 -0
  51. package/dist/components/assistant-ui/elements/agent-status.js +47 -0
  52. package/dist/components/assistant-ui/elements/approval-card.d.ts +31 -0
  53. package/dist/components/assistant-ui/elements/approval-card.js +99 -0
  54. package/dist/components/assistant-ui/elements/artifact-card.d.ts +12 -0
  55. package/dist/components/assistant-ui/elements/artifact-card.js +47 -0
  56. package/dist/components/assistant-ui/elements/assistant-modal.aui.d.ts +7 -0
  57. package/dist/components/assistant-ui/elements/assistant-modal.aui.js +276 -0
  58. package/dist/components/assistant-ui/elements/assistant-sidebar.aui.d.ts +7 -0
  59. package/dist/components/assistant-ui/elements/assistant-sidebar.aui.js +18 -0
  60. package/dist/components/assistant-ui/elements/attachment.aui.d.ts +9 -0
  61. package/dist/components/assistant-ui/elements/attachment.aui.js +143 -0
  62. package/dist/components/assistant-ui/elements/background-inbox.d.ts +18 -0
  63. package/dist/components/assistant-ui/elements/background-inbox.js +65 -0
  64. package/dist/components/assistant-ui/elements/canvas-split.d.ts +25 -0
  65. package/dist/components/assistant-ui/elements/canvas-split.js +106 -0
  66. package/dist/components/assistant-ui/elements/chart.d.ts +19 -0
  67. package/dist/components/assistant-ui/elements/chart.js +105 -0
  68. package/dist/components/assistant-ui/elements/chat-panel.d.ts +15 -0
  69. package/dist/components/assistant-ui/elements/chat-panel.js +82 -0
  70. package/dist/components/assistant-ui/elements/checkpoint-history.d.ts +17 -0
  71. package/dist/components/assistant-ui/elements/checkpoint-history.js +60 -0
  72. package/dist/components/assistant-ui/elements/code-diff.d.ts +18 -0
  73. package/dist/components/assistant-ui/elements/code-diff.js +89 -0
  74. package/dist/components/assistant-ui/elements/code-runner.d.ts +15 -0
  75. package/dist/components/assistant-ui/elements/code-runner.js +108 -0
  76. package/dist/components/assistant-ui/elements/command-palette.d.ts +20 -0
  77. package/dist/components/assistant-ui/elements/command-palette.js +129 -0
  78. package/dist/components/assistant-ui/elements/comparison-card.d.ts +18 -0
  79. package/dist/components/assistant-ui/elements/comparison-card.js +58 -0
  80. package/dist/components/assistant-ui/elements/composer-trigger-popover.aui.d.ts +51 -0
  81. package/dist/components/assistant-ui/elements/composer-trigger-popover.aui.js +104 -0
  82. package/dist/components/assistant-ui/elements/composer.d.ts +91 -0
  83. package/dist/components/assistant-ui/elements/composer.js +416 -0
  84. package/dist/components/assistant-ui/elements/computer-use.d.ts +19 -0
  85. package/dist/components/assistant-ui/elements/computer-use.js +84 -0
  86. package/dist/components/assistant-ui/elements/confidence-marker.d.ts +20 -0
  87. package/dist/components/assistant-ui/elements/confidence-marker.js +58 -0
  88. package/dist/components/assistant-ui/elements/connection-state.d.ts +13 -0
  89. package/dist/components/assistant-ui/elements/connection-state.js +59 -0
  90. package/dist/components/assistant-ui/elements/context-breakdown.d.ts +15 -0
  91. package/dist/components/assistant-ui/elements/context-breakdown.js +91 -0
  92. package/dist/components/assistant-ui/elements/context-display.aui.d.ts +25 -0
  93. package/dist/components/assistant-ui/elements/context-display.aui.js +26 -0
  94. package/dist/components/assistant-ui/elements/context-display.d.ts +43 -0
  95. package/dist/components/assistant-ui/elements/context-display.js +300 -0
  96. package/dist/components/assistant-ui/elements/conversation-map.aui.d.ts +9 -0
  97. package/dist/components/assistant-ui/elements/conversation-map.aui.js +177 -0
  98. package/dist/components/assistant-ui/elements/conversation-map.d.ts +19 -0
  99. package/dist/components/assistant-ui/elements/conversation-map.js +84 -0
  100. package/dist/components/assistant-ui/elements/conversation-search.d.ts +20 -0
  101. package/dist/components/assistant-ui/elements/conversation-search.js +75 -0
  102. package/dist/components/assistant-ui/elements/cost-meter.d.ts +19 -0
  103. package/dist/components/assistant-ui/elements/cost-meter.js +76 -0
  104. package/dist/components/assistant-ui/elements/data-table.d.ts +72 -0
  105. package/dist/components/assistant-ui/elements/data-table.js +368 -0
  106. package/dist/components/assistant-ui/elements/day-separator.d.ts +16 -0
  107. package/dist/components/assistant-ui/elements/day-separator.js +44 -0
  108. package/dist/components/assistant-ui/elements/diagram.d.ts +15 -0
  109. package/dist/components/assistant-ui/elements/diagram.js +65 -0
  110. package/dist/components/assistant-ui/elements/directive-text.aui.d.ts +11 -0
  111. package/dist/components/assistant-ui/elements/directive-text.aui.js +18 -0
  112. package/dist/components/assistant-ui/elements/directive-text.d.ts +32 -0
  113. package/dist/components/assistant-ui/elements/directive-text.js +35 -0
  114. package/dist/components/assistant-ui/elements/document-reference.d.ts +17 -0
  115. package/dist/components/assistant-ui/elements/document-reference.js +62 -0
  116. package/dist/components/assistant-ui/elements/draft-restore.d.ts +12 -0
  117. package/dist/components/assistant-ui/elements/draft-restore.js +43 -0
  118. package/dist/components/assistant-ui/elements/edit-message.d.ts +15 -0
  119. package/dist/components/assistant-ui/elements/edit-message.js +63 -0
  120. package/dist/components/assistant-ui/elements/elicitation-form.d.ts +23 -0
  121. package/dist/components/assistant-ui/elements/elicitation-form.js +112 -0
  122. package/dist/components/assistant-ui/elements/empty-state.d.ts +16 -0
  123. package/dist/components/assistant-ui/elements/empty-state.js +71 -0
  124. package/dist/components/assistant-ui/elements/error-state.d.ts +13 -0
  125. package/dist/components/assistant-ui/elements/error-state.js +52 -0
  126. package/dist/components/assistant-ui/elements/feedback-dialog.d.ts +15 -0
  127. package/dist/components/assistant-ui/elements/feedback-dialog.js +77 -0
  128. package/dist/components/assistant-ui/elements/file-tree.d.ts +20 -0
  129. package/dist/components/assistant-ui/elements/file-tree.js +74 -0
  130. package/dist/components/assistant-ui/elements/file.d.ts +52 -0
  131. package/dist/components/assistant-ui/elements/file.js +222 -0
  132. package/dist/components/assistant-ui/elements/flow-graph.d.ts +23 -0
  133. package/dist/components/assistant-ui/elements/flow-graph.js +72 -0
  134. package/dist/components/assistant-ui/elements/follow-up-suggestions.aui.d.ts +7 -0
  135. package/dist/components/assistant-ui/elements/follow-up-suggestions.aui.js +30 -0
  136. package/dist/components/assistant-ui/elements/generative-ui.d.ts +8 -0
  137. package/dist/components/assistant-ui/elements/generative-ui.js +27 -0
  138. package/dist/components/assistant-ui/elements/geo-map.d.ts +29 -0
  139. package/dist/components/assistant-ui/elements/geo-map.js +190 -0
  140. package/dist/components/assistant-ui/elements/guardrail-notice.d.ts +15 -0
  141. package/dist/components/assistant-ui/elements/guardrail-notice.js +59 -0
  142. package/dist/components/assistant-ui/elements/heat-graph.d.ts +9 -0
  143. package/dist/components/assistant-ui/elements/heat-graph.js +90 -0
  144. package/dist/components/assistant-ui/elements/image-gallery.d.ts +22 -0
  145. package/dist/components/assistant-ui/elements/image-gallery.js +192 -0
  146. package/dist/components/assistant-ui/elements/image-generation.d.ts +11 -0
  147. package/dist/components/assistant-ui/elements/image-generation.js +64 -0
  148. package/dist/components/assistant-ui/elements/image.d.ts +59 -0
  149. package/dist/components/assistant-ui/elements/image.js +416 -0
  150. package/dist/components/assistant-ui/elements/inline-citation.d.ts +23 -0
  151. package/dist/components/assistant-ui/elements/inline-citation.js +90 -0
  152. package/dist/components/assistant-ui/elements/job-progress.d.ts +25 -0
  153. package/dist/components/assistant-ui/elements/job-progress.js +102 -0
  154. package/dist/components/assistant-ui/elements/launcher-bubble.d.ts +15 -0
  155. package/dist/components/assistant-ui/elements/launcher-bubble.js +71 -0
  156. package/dist/components/assistant-ui/elements/link-preview.d.ts +17 -0
  157. package/dist/components/assistant-ui/elements/link-preview.js +77 -0
  158. package/dist/components/assistant-ui/elements/loading-state.d.ts +13 -0
  159. package/dist/components/assistant-ui/elements/loading-state.js +33 -0
  160. package/dist/components/assistant-ui/elements/logos.d.ts +10 -0
  161. package/dist/components/assistant-ui/elements/logos.js +63 -0
  162. package/dist/components/assistant-ui/elements/map-answer.d.ts +19 -0
  163. package/dist/components/assistant-ui/elements/map-answer.js +120 -0
  164. package/dist/components/assistant-ui/elements/markdown-text.d.ts +11 -0
  165. package/dist/components/assistant-ui/elements/markdown-text.js +152 -0
  166. package/dist/components/assistant-ui/elements/math-block.d.ts +25 -0
  167. package/dist/components/assistant-ui/elements/math-block.js +60 -0
  168. package/dist/components/assistant-ui/elements/mcp-config.aui.d.ts +28 -0
  169. package/dist/components/assistant-ui/elements/mcp-config.aui.js +380 -0
  170. package/dist/components/assistant-ui/elements/mcp-server-panel.d.ts +20 -0
  171. package/dist/components/assistant-ui/elements/mcp-server-panel.js +114 -0
  172. package/dist/components/assistant-ui/elements/media-player.d.ts +21 -0
  173. package/dist/components/assistant-ui/elements/media-player.js +302 -0
  174. package/dist/components/assistant-ui/elements/memory-chips.d.ts +16 -0
  175. package/dist/components/assistant-ui/elements/memory-chips.js +44 -0
  176. package/dist/components/assistant-ui/elements/mermaid-diagram.aui.d.ts +14 -0
  177. package/dist/components/assistant-ui/elements/mermaid-diagram.aui.js +43 -0
  178. package/dist/components/assistant-ui/elements/mermaid-diagram.d.ts +20 -0
  179. package/dist/components/assistant-ui/elements/mermaid-diagram.js +258 -0
  180. package/dist/components/assistant-ui/elements/message-actions.d.ts +17 -0
  181. package/dist/components/assistant-ui/elements/message-actions.js +57 -0
  182. package/dist/components/assistant-ui/elements/message-attachment.d.ts +18 -0
  183. package/dist/components/assistant-ui/elements/message-attachment.js +58 -0
  184. package/dist/components/assistant-ui/elements/message-branches.d.ts +12 -0
  185. package/dist/components/assistant-ui/elements/message-branches.js +55 -0
  186. package/dist/components/assistant-ui/elements/message-pair.d.ts +16 -0
  187. package/dist/components/assistant-ui/elements/message-pair.js +63 -0
  188. package/dist/components/assistant-ui/elements/message-queue.d.ts +15 -0
  189. package/dist/components/assistant-ui/elements/message-queue.js +70 -0
  190. package/dist/components/assistant-ui/elements/message-timing.aui.d.ts +30 -0
  191. package/dist/components/assistant-ui/elements/message-timing.aui.js +98 -0
  192. package/dist/components/assistant-ui/elements/message-timing.d.ts +14 -0
  193. package/dist/components/assistant-ui/elements/message-timing.js +26 -0
  194. package/dist/components/assistant-ui/elements/mobile-composer.d.ts +18 -0
  195. package/dist/components/assistant-ui/elements/mobile-composer.js +76 -0
  196. package/dist/components/assistant-ui/elements/model-picker.d.ts +19 -0
  197. package/dist/components/assistant-ui/elements/model-picker.js +68 -0
  198. package/dist/components/assistant-ui/elements/model-selector.aui.d.ts +23 -0
  199. package/dist/components/assistant-ui/elements/model-selector.aui.js +79 -0
  200. package/dist/components/assistant-ui/elements/model-selector.d.ts +130 -0
  201. package/dist/components/assistant-ui/elements/model-selector.js +399 -0
  202. package/dist/components/assistant-ui/elements/number-ticker.d.ts +10 -0
  203. package/dist/components/assistant-ui/elements/number-ticker.js +41 -0
  204. package/dist/components/assistant-ui/elements/onboarding.d.ts +17 -0
  205. package/dist/components/assistant-ui/elements/onboarding.js +69 -0
  206. package/dist/components/assistant-ui/elements/option-list.d.ts +39 -0
  207. package/dist/components/assistant-ui/elements/option-list.js +176 -0
  208. package/dist/components/assistant-ui/elements/permission-grant.d.ts +14 -0
  209. package/dist/components/assistant-ui/elements/permission-grant.js +84 -0
  210. package/dist/components/assistant-ui/elements/prompt-library.d.ts +20 -0
  211. package/dist/components/assistant-ui/elements/prompt-library.js +121 -0
  212. package/dist/components/assistant-ui/elements/question-flow.d.ts +24 -0
  213. package/dist/components/assistant-ui/elements/question-flow.js +180 -0
  214. package/dist/components/assistant-ui/elements/quota-banner.d.ts +14 -0
  215. package/dist/components/assistant-ui/elements/quota-banner.js +68 -0
  216. package/dist/components/assistant-ui/elements/quote-reply.d.ts +20 -0
  217. package/dist/components/assistant-ui/elements/quote-reply.js +66 -0
  218. package/dist/components/assistant-ui/elements/quote.aui.d.ts +61 -0
  219. package/dist/components/assistant-ui/elements/quote.aui.js +170 -0
  220. package/dist/components/assistant-ui/elements/read-aloud.d.ts +16 -0
  221. package/dist/components/assistant-ui/elements/read-aloud.js +66 -0
  222. package/dist/components/assistant-ui/elements/reasoning-effort.d.ts +17 -0
  223. package/dist/components/assistant-ui/elements/reasoning-effort.js +67 -0
  224. package/dist/components/assistant-ui/elements/reasoning-panel.d.ts +20 -0
  225. package/dist/components/assistant-ui/elements/reasoning-panel.js +60 -0
  226. package/dist/components/assistant-ui/elements/reasoning.aui.d.ts +24 -0
  227. package/dist/components/assistant-ui/elements/reasoning.aui.js +70 -0
  228. package/dist/components/assistant-ui/elements/reasoning.d.ts +38 -0
  229. package/dist/components/assistant-ui/elements/reasoning.js +194 -0
  230. package/dist/components/assistant-ui/elements/recommendation-card.d.ts +16 -0
  231. package/dist/components/assistant-ui/elements/recommendation-card.js +65 -0
  232. package/dist/components/assistant-ui/elements/regenerate-menu.d.ts +18 -0
  233. package/dist/components/assistant-ui/elements/regenerate-menu.js +46 -0
  234. package/dist/components/assistant-ui/elements/research-report.d.ts +19 -0
  235. package/dist/components/assistant-ui/elements/research-report.js +63 -0
  236. package/dist/components/assistant-ui/elements/retrieval-chunks.d.ts +19 -0
  237. package/dist/components/assistant-ui/elements/retrieval-chunks.js +86 -0
  238. package/dist/components/assistant-ui/elements/reviewable-diff.d.ts +21 -0
  239. package/dist/components/assistant-ui/elements/reviewable-diff.js +104 -0
  240. package/dist/components/assistant-ui/elements/schedule-card.d.ts +19 -0
  241. package/dist/components/assistant-ui/elements/schedule-card.js +80 -0
  242. package/dist/components/assistant-ui/elements/score-breakdown.d.ts +19 -0
  243. package/dist/components/assistant-ui/elements/score-breakdown.js +107 -0
  244. package/dist/components/assistant-ui/elements/scroll-anchor.d.ts +15 -0
  245. package/dist/components/assistant-ui/elements/scroll-anchor.js +104 -0
  246. package/dist/components/assistant-ui/elements/settings-panel.d.ts +23 -0
  247. package/dist/components/assistant-ui/elements/settings-panel.js +108 -0
  248. package/dist/components/assistant-ui/elements/shared-conversation.d.ts +18 -0
  249. package/dist/components/assistant-ui/elements/shared-conversation.js +56 -0
  250. package/dist/components/assistant-ui/elements/shiki-highlighter.aui.d.ts +29 -0
  251. package/dist/components/assistant-ui/elements/shiki-highlighter.aui.js +31 -0
  252. package/dist/components/assistant-ui/elements/shiki-highlighter.d.ts +26 -0
  253. package/dist/components/assistant-ui/elements/shiki-highlighter.js +49 -0
  254. package/dist/components/assistant-ui/elements/sources.aui.d.ts +24 -0
  255. package/dist/components/assistant-ui/elements/sources.aui.js +121 -0
  256. package/dist/components/assistant-ui/elements/sources.d.ts +21 -0
  257. package/dist/components/assistant-ui/elements/sources.js +109 -0
  258. package/dist/components/assistant-ui/elements/speaker-identity.d.ts +17 -0
  259. package/dist/components/assistant-ui/elements/speaker-identity.js +45 -0
  260. package/dist/components/assistant-ui/elements/spec-sheet.d.ts +17 -0
  261. package/dist/components/assistant-ui/elements/spec-sheet.js +39 -0
  262. package/dist/components/assistant-ui/elements/stopped-run.d.ts +12 -0
  263. package/dist/components/assistant-ui/elements/stopped-run.js +44 -0
  264. package/dist/components/assistant-ui/elements/streaming-text.d.ts +15 -0
  265. package/dist/components/assistant-ui/elements/streaming-text.js +45 -0
  266. package/dist/components/assistant-ui/elements/subagent-list.d.ts +17 -0
  267. package/dist/components/assistant-ui/elements/subagent-list.js +74 -0
  268. package/dist/components/assistant-ui/elements/suggestions.d.ts +14 -0
  269. package/dist/components/assistant-ui/elements/suggestions.js +25 -0
  270. package/dist/components/assistant-ui/elements/surfaces.d.ts +42 -0
  271. package/dist/components/assistant-ui/elements/surfaces.js +87 -0
  272. package/dist/components/assistant-ui/elements/syntax-highlighter.d.ts +7 -0
  273. package/dist/components/assistant-ui/elements/syntax-highlighter.js +41 -0
  274. package/dist/components/assistant-ui/elements/task-card.aui.d.ts +24 -0
  275. package/dist/components/assistant-ui/elements/task-card.aui.js +136 -0
  276. package/dist/components/assistant-ui/elements/task-card.d.ts +22 -0
  277. package/dist/components/assistant-ui/elements/task-card.js +104 -0
  278. package/dist/components/assistant-ui/elements/terminal-block.d.ts +27 -0
  279. package/dist/components/assistant-ui/elements/terminal-block.js +266 -0
  280. package/dist/components/assistant-ui/elements/thinking-indicator.d.ts +10 -0
  281. package/dist/components/assistant-ui/elements/thinking-indicator.js +30 -0
  282. package/dist/components/assistant-ui/elements/thread-list.aui.d.ts +39 -0
  283. package/dist/components/assistant-ui/elements/thread-list.aui.js +331 -0
  284. package/dist/components/assistant-ui/elements/thread-list.d.ts +19 -0
  285. package/dist/components/assistant-ui/elements/thread-list.js +72 -0
  286. package/dist/components/assistant-ui/elements/thread-search.d.ts +20 -0
  287. package/dist/components/assistant-ui/elements/thread-search.js +94 -0
  288. package/dist/components/assistant-ui/elements/thread.aui.d.ts +36 -0
  289. package/dist/components/assistant-ui/elements/thread.aui.js +625 -0
  290. package/dist/components/assistant-ui/elements/threadlist-sidebar.aui.d.ts +19 -0
  291. package/dist/components/assistant-ui/elements/threadlist-sidebar.aui.js +75 -0
  292. package/dist/components/assistant-ui/elements/timeline.d.ts +18 -0
  293. package/dist/components/assistant-ui/elements/timeline.js +40 -0
  294. package/dist/components/assistant-ui/elements/todo-list.d.ts +21 -0
  295. package/dist/components/assistant-ui/elements/todo-list.js +100 -0
  296. package/dist/components/assistant-ui/elements/tool-call.d.ts +17 -0
  297. package/dist/components/assistant-ui/elements/tool-call.js +70 -0
  298. package/dist/components/assistant-ui/elements/tool-error.d.ts +16 -0
  299. package/dist/components/assistant-ui/elements/tool-error.js +62 -0
  300. package/dist/components/assistant-ui/elements/tool-fallback.aui.d.ts +44 -0
  301. package/dist/components/assistant-ui/elements/tool-fallback.aui.js +542 -0
  302. package/dist/components/assistant-ui/elements/tool-group.aui.d.ts +37 -0
  303. package/dist/components/assistant-ui/elements/tool-group.aui.js +104 -0
  304. package/dist/components/assistant-ui/elements/tool-group.d.ts +20 -0
  305. package/dist/components/assistant-ui/elements/tool-group.js +71 -0
  306. package/dist/components/assistant-ui/elements/tool-timeline.d.ts +44 -0
  307. package/dist/components/assistant-ui/elements/tool-timeline.js +109 -0
  308. package/dist/components/assistant-ui/elements/tooltip-icon-button.d.ts +12 -0
  309. package/dist/components/assistant-ui/elements/tooltip-icon-button.js +30 -0
  310. package/dist/components/assistant-ui/elements/trace-waterfall.d.ts +33 -0
  311. package/dist/components/assistant-ui/elements/trace-waterfall.js +102 -0
  312. package/dist/components/assistant-ui/elements/typing-indicator.d.ts +9 -0
  313. package/dist/components/assistant-ui/elements/typing-indicator.js +45 -0
  314. package/dist/components/assistant-ui/elements/voice-conversation.aui.d.ts +11 -0
  315. package/dist/components/assistant-ui/elements/voice-conversation.aui.js +54 -0
  316. package/dist/components/assistant-ui/elements/voice-conversation.d.ts +21 -0
  317. package/dist/components/assistant-ui/elements/voice-conversation.js +110 -0
  318. package/dist/components/assistant-ui/elements/voice.aui.d.ts +22 -0
  319. package/dist/components/assistant-ui/elements/voice.aui.js +100 -0
  320. package/dist/components/assistant-ui/elements/voice.d.ts +15 -0
  321. package/dist/components/assistant-ui/elements/voice.js +400 -0
  322. package/dist/components/assistant-ui/elements/web-preview.d.ts +18 -0
  323. package/dist/components/assistant-ui/elements/web-preview.js +61 -0
  324. package/dist/components/assistant-ui/elements/web-search.d.ts +17 -0
  325. package/dist/components/assistant-ui/elements/web-search.js +54 -0
  326. package/dist/components/assistant-ui/utils/href.d.ts +13 -0
  327. package/dist/components/assistant-ui/utils/href.js +39 -0
  328. package/dist/components/assistant-ui/utils/range.d.ts +22 -0
  329. package/dist/components/assistant-ui/utils/range.js +48 -0
  330. package/dist/components/assistant-ui/utils/task.d.ts +14 -0
  331. package/dist/components/assistant-ui/utils/task.js +75 -0
  332. package/dist/components/icons/github.js +13 -0
  333. package/dist/components/theme-provider.d.ts +16 -0
  334. package/dist/components/theme-provider.js +116 -0
  335. package/dist/components/ui/accordion.d.ts +8 -0
  336. package/dist/components/ui/accordion.js +53 -0
  337. package/dist/components/ui/alert-dialog.d.ts +20 -0
  338. package/dist/components/ui/alert-dialog.js +93 -0
  339. package/dist/components/ui/alert.d.ts +12 -0
  340. package/dist/components/ui/alert.js +42 -0
  341. package/dist/components/ui/aspect-ratio.d.ts +6 -0
  342. package/dist/components/ui/aspect-ratio.js +13 -0
  343. package/dist/components/ui/attachment.d.ts +25 -0
  344. package/dist/components/ui/attachment.js +103 -0
  345. package/dist/components/ui/avatar.d.ts +13 -0
  346. package/dist/components/ui/avatar.js +50 -0
  347. package/dist/components/ui/badge.d.ts +14 -0
  348. package/dist/components/ui/badge.js +30 -0
  349. package/dist/components/ui/breadcrumb.d.ts +12 -0
  350. package/dist/components/ui/breadcrumb.js +71 -0
  351. package/dist/components/ui/bubble.d.ts +18 -0
  352. package/dist/components/ui/bubble.js +72 -0
  353. package/dist/components/ui/button-group.d.ts +12 -0
  354. package/dist/components/ui/button-group.js +41 -0
  355. package/dist/components/ui/button.d.ts +19 -0
  356. package/dist/components/ui/button.js +71 -0
  357. package/dist/components/ui/calendar.d.ts +12 -0
  358. package/dist/components/ui/calendar.js +108 -0
  359. package/dist/components/ui/card.d.ts +13 -0
  360. package/dist/components/ui/card.js +55 -0
  361. package/dist/components/ui/carousel.d.ts +30 -0
  362. package/dist/components/ui/carousel.js +131 -0
  363. package/dist/components/ui/chart.d.ts +46 -0
  364. package/dist/components/ui/chart.js +148 -0
  365. package/dist/components/ui/checkbox.d.ts +5 -0
  366. package/dist/components/ui/checkbox.js +20 -0
  367. package/dist/components/ui/collapsible.d.ts +7 -0
  368. package/dist/components/ui/collapsible.js +23 -0
  369. package/dist/components/ui/combobox.d.ts +26 -0
  370. package/dist/components/ui/combobox.js +161 -0
  371. package/dist/components/ui/command.d.ts +21 -0
  372. package/dist/components/ui/command.js +87 -0
  373. package/dist/components/ui/context-menu.d.ts +31 -0
  374. package/dist/components/ui/context-menu.js +132 -0
  375. package/dist/components/ui/dialog.d.ts +19 -0
  376. package/dist/components/ui/dialog.js +91 -0
  377. package/dist/components/ui/diff-viewer.d.ts +100 -0
  378. package/dist/components/ui/diff-viewer.js +461 -0
  379. package/dist/components/ui/direction.d.ts +2 -0
  380. package/dist/components/ui/direction.js +2 -0
  381. package/dist/components/ui/dot-matrix.d.ts +150 -0
  382. package/dist/components/ui/dot-matrix.js +248 -0
  383. package/dist/components/ui/drawer.d.ts +18 -0
  384. package/dist/components/ui/drawer.js +123 -0
  385. package/dist/components/ui/dropdown-menu.d.ts +31 -0
  386. package/dist/components/ui/dropdown-menu.js +136 -0
  387. package/dist/components/ui/empty.d.ts +13 -0
  388. package/dist/components/ui/empty.js +59 -0
  389. package/dist/components/ui/field.d.ts +26 -0
  390. package/dist/components/ui/field.js +109 -0
  391. package/dist/components/ui/hover-card.d.ts +7 -0
  392. package/dist/components/ui/hover-card.js +36 -0
  393. package/dist/components/ui/input-group.d.ts +20 -0
  394. package/dist/components/ui/input-group.js +77 -0
  395. package/dist/components/ui/input-otp.d.ts +13 -0
  396. package/dist/components/ui/input-otp.js +46 -0
  397. package/dist/components/ui/input.d.ts +5 -0
  398. package/dist/components/ui/input.js +14 -0
  399. package/dist/components/ui/item.d.ts +24 -0
  400. package/dist/components/ui/item.js +120 -0
  401. package/dist/components/ui/kbd.d.ts +5 -0
  402. package/dist/components/ui/kbd.js +19 -0
  403. package/dist/components/ui/label.d.ts +5 -0
  404. package/dist/components/ui/label.js +12 -0
  405. package/dist/components/ui/marker.d.ts +12 -0
  406. package/dist/components/ui/marker.js +42 -0
  407. package/dist/components/ui/menubar.d.ts +31 -0
  408. package/dist/components/ui/menubar.js +135 -0
  409. package/dist/components/ui/message-scroller.d.ts +12 -0
  410. package/dist/components/ui/message-scroller.js +59 -0
  411. package/dist/components/ui/message.d.ts +12 -0
  412. package/dist/components/ui/message.js +48 -0
  413. package/dist/components/ui/native-select.d.ts +10 -0
  414. package/dist/components/ui/native-select.js +37 -0
  415. package/dist/components/ui/navigation-menu.d.ts +13 -0
  416. package/dist/components/ui/navigation-menu.js +82 -0
  417. package/dist/components/ui/number-roll.d.ts +21 -0
  418. package/dist/components/ui/number-roll.js +269 -0
  419. package/dist/components/ui/pagination.d.ts +19 -0
  420. package/dist/components/ui/pagination.js +79 -0
  421. package/dist/components/ui/popover.d.ts +11 -0
  422. package/dist/components/ui/popover.js +54 -0
  423. package/dist/components/ui/progress.d.ts +9 -0
  424. package/dist/components/ui/progress.js +44 -0
  425. package/dist/components/ui/questionnaire.d.ts +21 -0
  426. package/dist/components/ui/questionnaire.js +169 -0
  427. package/dist/components/ui/radio-group.d.ts +7 -0
  428. package/dist/components/ui/radio-group.js +26 -0
  429. package/dist/components/ui/resizable.d.ts +9 -0
  430. package/dist/components/ui/resizable.js +28 -0
  431. package/dist/components/ui/scroll-area.d.ts +6 -0
  432. package/dist/components/ui/scroll-area.js +35 -0
  433. package/dist/components/ui/select.d.ts +17 -0
  434. package/dist/components/ui/select.js +96 -0
  435. package/dist/components/ui/separator.d.ts +5 -0
  436. package/dist/components/ui/separator.js +14 -0
  437. package/dist/components/ui/sheet.d.ts +16 -0
  438. package/dist/components/ui/sheet.js +87 -0
  439. package/dist/components/ui/sidebar.d.ts +65 -0
  440. package/dist/components/ui/sidebar.js +386 -0
  441. package/dist/components/ui/skeleton.d.ts +4 -0
  442. package/dist/components/ui/skeleton.js +12 -0
  443. package/dist/components/ui/slider.d.ts +5 -0
  444. package/dist/components/ui/slider.js +33 -0
  445. package/dist/components/ui/spinner.d.ts +4 -0
  446. package/dist/components/ui/spinner.js +15 -0
  447. package/dist/components/ui/switch.d.ts +7 -0
  448. package/dist/components/ui/switch.js +19 -0
  449. package/dist/components/ui/table.d.ts +12 -0
  450. package/dist/components/ui/table.js +65 -0
  451. package/dist/components/ui/tabs.d.ts +12 -0
  452. package/dist/components/ui/tabs.js +45 -0
  453. package/dist/components/ui/textarea.d.ts +5 -0
  454. package/dist/components/ui/textarea.js +12 -0
  455. package/dist/components/ui/toast.d.ts +18 -0
  456. package/dist/components/ui/toast.js +121 -0
  457. package/dist/components/ui/toggle-group.d.ts +13 -0
  458. package/dist/components/ui/toggle-group.js +51 -0
  459. package/dist/components/ui/toggle.d.ts +10 -0
  460. package/dist/components/ui/toggle.js +35 -0
  461. package/dist/components/ui/tooltip.d.ts +8 -0
  462. package/dist/components/ui/tooltip.js +43 -0
  463. package/dist/compositions/app-rail/app-rail.d.ts +19 -0
  464. package/dist/compositions/app-rail/app-rail.js +58 -0
  465. package/dist/compositions/app-shell/app-shell.d.ts +56 -0
  466. package/dist/compositions/app-shell/app-shell.js +143 -0
  467. package/dist/compositions/app-shell/theme-toggle.d.ts +10 -0
  468. package/dist/compositions/app-shell/theme-toggle.js +65 -0
  469. package/dist/compositions/confirm-action/confirm-action.d.ts +48 -0
  470. package/dist/compositions/confirm-action/confirm-action.js +48 -0
  471. package/dist/compositions/data-table/data-table-state.d.ts +23 -0
  472. package/dist/compositions/data-table/data-table-state.js +46 -0
  473. package/dist/compositions/data-table/data-table.d.ts +185 -0
  474. package/dist/compositions/data-table/data-table.js +615 -0
  475. package/dist/compositions/date-range-picker/date-range-options.d.ts +28 -0
  476. package/dist/compositions/date-range-picker/date-range-options.js +61 -0
  477. package/dist/compositions/date-range-picker/date-range-picker.d.ts +55 -0
  478. package/dist/compositions/date-range-picker/date-range-picker.js +409 -0
  479. package/dist/compositions/decision-queue/decision-queue.d.ts +114 -0
  480. package/dist/compositions/decision-queue/decision-queue.js +478 -0
  481. package/dist/compositions/event-feed/event-feed.d.ts +59 -0
  482. package/dist/compositions/event-feed/event-feed.js +105 -0
  483. package/dist/compositions/feedback.d.ts +20 -0
  484. package/dist/compositions/feedback.js +49 -0
  485. package/dist/compositions/fields.d.ts +64 -0
  486. package/dist/compositions/fields.js +293 -0
  487. package/dist/compositions/form-kit/form-context.d.ts +10 -0
  488. package/dist/compositions/form-kit/form-context.js +12 -0
  489. package/dist/compositions/form-kit/form-fields.d.ts +95 -0
  490. package/dist/compositions/form-kit/form-fields.js +233 -0
  491. package/dist/compositions/form-kit/form-kit.d.ts +128 -0
  492. package/dist/compositions/form-kit/form-kit.js +119 -0
  493. package/dist/compositions/inspector/inspector.d.ts +53 -0
  494. package/dist/compositions/inspector/inspector.js +80 -0
  495. package/dist/compositions/layout.d.ts +36 -0
  496. package/dist/compositions/layout.js +86 -0
  497. package/dist/compositions/state-blocks/state-blocks.d.ts +42 -0
  498. package/dist/compositions/state-blocks/state-blocks.js +81 -0
  499. package/dist/compositions/status-panel/status-panel.d.ts +94 -0
  500. package/dist/compositions/status-panel/status-panel.js +189 -0
  501. package/dist/fonts/InterVariable.woff2 +0 -0
  502. package/dist/fonts/inter.css +15 -0
  503. package/dist/hooks/use-attachment-src.js +35 -0
  504. package/dist/hooks/use-copy-to-clipboard.js +34 -0
  505. package/dist/hooks/use-mobile.d.ts +3 -0
  506. package/dist/hooks/use-mobile.js +18 -0
  507. package/dist/index.d.ts +102 -0
  508. package/dist/index.js +102 -0
  509. package/dist/lib/context-level.js +7 -0
  510. package/dist/lib/elapsed.js +61 -0
  511. package/dist/lib/iso-date.js +30 -0
  512. package/dist/lib/motion-loop.js +41 -0
  513. package/dist/lib/pointer.js +14 -0
  514. package/dist/lib/status-tone.d.ts +7 -0
  515. package/dist/lib/status-tone.js +55 -0
  516. package/dist/lib/triage-keys.js +229 -0
  517. package/dist/lib/utils.js +2 -0
  518. package/dist/motion/alert-toast/alert-toast.d.ts +51 -0
  519. package/dist/motion/alert-toast/alert-toast.js +226 -0
  520. package/dist/motion/branch-menu/branch-menu.d.ts +47 -0
  521. package/dist/motion/branch-menu/branch-menu.js +287 -0
  522. package/dist/motion/check-item/check-item.d.ts +24 -0
  523. package/dist/motion/check-item/check-item.js +110 -0
  524. package/dist/motion/dial/dial.d.ts +39 -0
  525. package/dist/motion/dial/dial.js +290 -0
  526. package/dist/motion/dictation-button/dictation-button.d.ts +45 -0
  527. package/dist/motion/dictation-button/dictation-button.js +232 -0
  528. package/dist/motion/hold-button/hold-button.d.ts +37 -0
  529. package/dist/motion/hold-button/hold-button.js +192 -0
  530. package/dist/motion/masonry-grid/masonry-grid.d.ts +42 -0
  531. package/dist/motion/masonry-grid/masonry-grid.js +145 -0
  532. package/dist/motion/prompt-composer/prompt-composer.d.ts +90 -0
  533. package/dist/motion/prompt-composer/prompt-composer.js +374 -0
  534. package/dist/motion/scrub-select/scrub-select.d.ts +33 -0
  535. package/dist/motion/scrub-select/scrub-select.js +346 -0
  536. package/dist/motion/spotlight-grid/spotlight-grid.d.ts +40 -0
  537. package/dist/motion/spotlight-grid/spotlight-grid.js +171 -0
  538. package/dist/motion/star-rating/star-rating.d.ts +32 -0
  539. package/dist/motion/star-rating/star-rating.js +191 -0
  540. package/dist/motion/status-glyph/status-glyph.d.ts +28 -0
  541. package/dist/motion/status-glyph/status-glyph.js +171 -0
  542. package/dist/motion/stepper/stepper.d.ts +56 -0
  543. package/dist/motion/stepper/stepper.js +211 -0
  544. package/dist/motion/swipe-row/swipe-row.d.ts +52 -0
  545. package/dist/motion/swipe-row/swipe-row.js +208 -0
  546. package/dist/motion/thinking-trace/thinking-trace.d.ts +32 -0
  547. package/dist/motion/thinking-trace/thinking-trace.js +186 -0
  548. package/dist/motion/tool-call-chip/tool-call-chip.d.ts +36 -0
  549. package/dist/motion/tool-call-chip/tool-call-chip.js +135 -0
  550. package/dist/motion/working-indicator/working-indicator.d.ts +38 -0
  551. package/dist/motion/working-indicator/working-indicator.js +171 -0
  552. package/dist/styles.css +828 -0
  553. package/dist/tokens.css +230 -0
  554. package/licenses/Inter-OFL.txt +92 -0
  555. package/licenses/assistant-ui-MIT.txt +21 -0
  556. package/licenses/shadcn-MIT.md +21 -0
  557. package/package.json +133 -4
@@ -0,0 +1,317 @@
1
+ # Inherited source changes
2
+
3
+ This is the admin-ui source provenance snapshot at ac114fc. Soft theme adaptations are recorded in VENDORED-CHANGES.md and supersede theme-specific descriptions below.
4
+
5
+ # Vendored component changes
6
+
7
+ Two vendored trees live in this package. `src/components/ui/` holds upstream
8
+ shadcn components (base-mira, Base UI). `src/components/assistant-ui/` holds
9
+ the assistant-ui registry items (see ASSISTANT-UI.md). Both are kept vanilla
10
+ except for the deliberate deviations below, each fixing a clear defect or a
11
+ decision RFC-02 records. When you pull upstream changes (`shadcn add --diff`,
12
+ re-running the registry install), re-apply or drop each one on purpose.
13
+
14
+ ## src/components/ui (shadcn)
15
+
16
+ These are the only deliberate deviations, each fixing a clear defect found in
17
+ the Storybook visual QA pass (2026-10-03).
18
+
19
+ | File | Change | Why |
20
+ |---|---|---|
21
+ | `src/components/ui/menubar.tsx` | MenubarTrigger className: added focus-visible:bg-muted (between hover:bg-muted and aria-expanded:bg-muted) | The trigger uses outline-hidden and styles only hover and expanded, so keyboard focus was invisible. The new class matches the hover fill, so hover and focus read as one state family. |
22
+ | `src/components/ui/accordion.tsx` | AccordionTrigger className: added `focus-visible:border-ring focus-visible:ring-2 focus-visible:ring-ring/30 focus-visible:ring-inset`. | Keyboard focus was invisible (no focus-visible style at all). The ring is inset because the Accordion root's overflow-hidden clipped an outer ring on the top and sides. |
23
+ | `src/components/ui/slider.tsx` | SliderPrimitive.Thumb className: replaced `focus-visible:ring-2` with `has-focus-visible:ring-3 has-focus-visible:ring-ring/50`; hover and active stay at ring-2 ring-ring/30. | Base UI focuses the hidden <input type=range> inside the thumb, so :focus-visible never matched the thumb div and keyboard focus was invisible. The /30 ring was also too faint to serve as the only focus indicator. |
24
+ | `src/components/ui/calendar.tsx` | CalendarDayButton: removed 'group-data-[focused=true]/day:relative group-data-[focused=true]/day:z-10 group-data-[focused=true]/day:border-ring group-data-[focused=true]/day:ring-[3px] group-data-[focused=true]/day:ring-ring/50'. Button's own focus-visible ring (2px, ring/30) is now the day focus indicator. | Defect: react-day-picker's focused modifier stays on a clicked or programmatically focused day while real focus is elsewhere. That gave two focus indicators at once, a heavy ring crowding neighbouring days, and a square ring on range-middle days. |
25
+ | `src/components/ui/popover.tsx` | PopoverContent adds 'collisionAvoidance' to its Pick of Positioner props and passes it to PopoverPrimitive.Positioner. When omitted it is undefined, which keeps Base UI's default. | Positioner props were not forwarded, so a composition could not stop the popover from moving beside a mid-page trigger, where it looked detached. DateRangePicker needs fallbackAxisSide 'none'. |
26
+ | `src/components/ui/attachment.tsx` | Added `has-[[data-slot=attachment-action]:focus-visible]:ring-0` to the Attachment root classes in attachmentVariants, after the existing `focus-within:ring-1 focus-within:ring-ring/30`. | Focus-ring collision. When an AttachmentAction had keyboard focus, the card's focus-within ring and the button's own ring stacked into two rings. This showed in every Attachment story with an action and in Message WithAttachment. The card ring still shows when focus is elsewhere inside the card, such as AttachmentTrigger, which is outline-none and relies on it. |
27
+ | `src/components/ui/skeleton.tsx` | Skeleton fill: replaced bg-muted with bg-foreground/10. | In light mode the fill was about #F5F5F5 on white (#FAFAFA at the pulse trough, about 1.04:1), so loading views read as blank. The translucent foreground tint shows on any surface, peaking around #E6E6E6 in light. In dark it stays about the same as bg-muted. One class, so all skeletons stay consistent. |
28
+ | `src/components/ui/checkbox.tsx` | Root className: replaced border-input with border-muted-foreground/40, and added dark:border-input before dark:bg-input/30. | An unchecked checkbox outline was a near-white hairline on white (about 1.2:1); row checkboxes in DataTable looked missing. It now samples at #C5C5C5 in light. Dark is unchanged. The checked, invalid and focus border classes still win, being more specific. A darker light --input token was tried first and dropped: it also darkens the bg-input/20 fill and dropped placeholder contrast to 4.48:1, which failed the a11y gate. |
29
+ | `src/components/ui/radio-group.tsx` | RadioGroupItem className: 'border-input' changed to 'border-muted-foreground/40', and 'group-has-[:focus-visible]/field-label:not-data-checked:border-input' changed to '...:border-muted-foreground/40'. | Unchecked radios were nearly invisible in light mode (0.922 hairline on white, about 1.26:1). The token alternative (raising --input) darkened every field fill and failed the a11y color-contrast gate (placeholder at 4.48:1). |
30
+ | `src/components/ui/checkbox.tsx` | Checkbox className: the same swap, 'border-input' to 'border-muted-foreground/40' in both the base class and the field-label focus reset. | Same near-invisible unchecked outline as the radio. Changed together so the two choice controls stay consistent. |
31
+ | `src/components/ui/menubar.tsx` | MenubarTrigger className: added 'focus-visible:ring-2 focus-visible:ring-ring/50 focus-visible:ring-inset' after the round-1 'focus-visible:bg-muted'. | Keyboard focus was still too faint (bg-muted fill only). The ring is inset so it does not collide with the menubar's own border. |
32
+ | `src/components/ui/button.tsx` | Sizes sm, default and lg: a Kbd that is the button's last child gets a trimmed right padding (`has-[>[data-slot=kbd]:last-child]:pr-[3px]` for sm and default, `pr-[5px]` for lg; the 1px border makes up the rest), and in sm the Kbd shrinks to `h-4 min-w-4`. | A key chip sat 2px from the top and bottom edges but 9px from the right (owner feedback). The inset is now even on all sides: 4px in sm and default, 6px in lg. |
33
+ | `src/components/ui/tooltip.tsx` | TooltipContent's Arrow gets `data-slot="tooltip-arrow"`. | The assistant-ui registry hides the arrow on popover-styled tooltips with `[&_[data-slot=tooltip-arrow]]:hidden` (context-display, message-timing.aui), the slot upstream shadcn's arrow carries. Without it a dark diamond sat on top of the light breakdown card. |
34
+ | `src/components/ui/diff-viewer.tsx` | Text colors raised for the a11y gate: the file-mode badge and the old-name/arrow spans `text-muted-foreground/70`, `/60`, `/50` to `text-muted-foreground`; the line numbers `text-muted-foreground/40` to `text-foreground/65`; the stats `text-green-600`/`text-red-600` to `text-green-700`/`text-red-700` (dark variants unchanged). | Registry `registry:ui` item (installed in unit a1). Measured in light: line numbers 1.69:1, and still 4.27:1 as plain muted-foreground on the deleted-line tint; additions count 3.05:1. All now pass 4.5:1 on the plain, added and deleted row backgrounds. |
35
+
36
+ Theme-token deviations (WCAG AA contrast, chart palette) are commented inline in `src/styles/globals.css`.
37
+
38
+ ## src/components/assistant-ui (assistant-ui registry)
39
+
40
+ Installed 2026-10-03 (RFC-02 Design 2, unit a1); see ASSISTANT-UI.md for the
41
+ item lists and the re-install procedure. Edits beyond Biome formatting:
42
+
43
+ | File | Change | Why |
44
+ |---|---|---|
45
+ | `elements/geo-map.tsx` | Removed the DEFAULT_TILE_URL constant; a tile layer is added only when the app passes `tileUrl`. Attribution still defaults to the OpenStreetMap string for layers the app does pass. Replaced the registry's tile-pane grayscale filters (they styled its default OpenStreetMap tiles) with an important re-apply of the field surface background when no tile layer exists. | RFC-02 network rule (hub#45): with no tileUrl the component fetched OpenStreetMap tiles, network I/O to a third party the app never chose. With no layer, leaflet.css's unlayered `background:#ddd` on .leaflet-container would otherwise paint over the field surface (Tailwind utilities sit in a cascade layer and lose to unlayered rules), which broke dark mode. |
46
+ | `elements/sources.aui.tsx` | Removed the defaultFaviconUrl resolver (DuckDuckGo icons service); with no `faviconUrl` prop the SourceIcon fallback renders a lucide Globe icon instead of fetching a favicon. A resolver that errors still falls back to the domain initial, as before. | RFC-02 network rule (hub#45): the default resolver fetched `https://icons.duckduckgo.com/ip3/<domain>.ico` for every source badge. |
47
+ | `src/styles/globals.css` | `@theme inline`: `--color-aui-warning` and `--color-aui-success` referenced `var(----aui-warning)` / `var(----aui-success)` (registry emission bug, quadruple dash, resolves to nothing). Now `var(--aui-warning)` / `var(--aui-success)`, the names the registry items define in `:root` and redefine in `.dark`. | Both color utilities resolved to no value in light and dark; the variables exist under the double-dash names. |
48
+ | `elements/map-answer.tsx` | Inline `biome-ignore lint/correctness/useJsxKeyInIterable` on the `content` element. | False positive: the element is rendered only inside the keyed button/span branches below it, never as a direct iterable child. Keeping the rule on elsewhere catches real missing keys in syncs. |
49
+ | `elements/voice.tsx` | Inline `biome-ignore lint/correctness/useHookAtTopLevel` on `gl.useProgram(program)`. | False positive: a WebGL context method after early returns, not a React hook. |
50
+ | `elements/syntax-highlighter.tsx` | Uses the synchronous `PrismLight` (and `makePrismLightSyntaxHighlighter`) instead of `PrismAsyncLight`; the same languages are registered up front. | Owner report: on a first load, code blocks stayed plain until a refresh. The async build loads its engine after the first render, and its re-render never repainted the code (a remount did). The sync build highlights on mount, with no flash of plain text. |
51
+ | `elements/mcp-config.aui.tsx` | The server row's status is a dot plus plain text instead of a filled Badge (connected chart-2, error destructive, a spinner while connecting or authorizing); 2px gap under the server name. | Owner feedback: the pill's own padding indented the status text from the server name, so the row looked misaligned. |
52
+ | `elements/mcp-config.aui.tsx` | `useAuiState` imported from `@assistant-ui/react` (its re-export) instead of `@assistant-ui/store`, and `@assistant-ui/store` removed from `dependencies`. | RFC-02 Design 2: the components must read the same React context as the consumer's `@assistant-ui/react`. The re-exported function is identical, but a directly pinned store can split: if a later `@assistant-ui/react` inside the peer range needs a newer store, the package manager cannot dedupe, the consumer gets two store copies, and `AuiMcpConfig` reads a context its own copy never provided (throws at render). Going through the peer keeps one copy. |
53
+ | `elements/markdown-text.tsx` | The markdown `a` renderer sets `rel="noopener noreferrer"` after the prop spread, so it cannot be overridden. | RFC-02 Security Considerations: links rendered from assistant markdown MUST open with `rel="noopener noreferrer"`. The registry emission set no `rel`. |
54
+ | `elements/agent-status.aui.tsx` | TaskTray rows: meta and elapsed text `text-foreground/35` and `/30` to `text-muted-foreground`; the tray's PopoverContent gets `aria-label="Tasks"`. | Contrast 2.35:1 and 2.02:1 in light (a11y gate). The popover is a dialog with no name (axe aria-dialog-name). Unit a2. |
55
+ | `elements/agent-status.tsx` | Elapsed time `text-foreground/30` to `text-muted-foreground`. | 2.02:1 in light. Unit a2. |
56
+ | `elements/task-card.tsx`, `elements/task-card.aui.tsx` | Task meta, elapsed time and the transcript role label: `text-foreground/35` and `/30` to `text-muted-foreground`. | 2.35:1 and 2.02:1 in light. Icons keep their faint colors (not text). Unit a2. |
57
+ | `elements/voice-conversation.tsx` | The hint line and the "you" label `text-foreground/35`/`/30` to `text-muted-foreground`; the "ai" label `text-blue-500/70 dark:text-blue-400/70` to `text-blue-600 dark:text-blue-400`; the user's transcript text `text-foreground/50` to `text-muted-foreground`. | 2.35, 2.02, 2.48 and 3.69:1 in light. Unit a2. |
58
+ | `elements/quote.aui.tsx` | QuoteBlockText `text-muted-foreground/80` to `text-muted-foreground`. ComposerQuotePreviewDismiss's default look now styles QuoteDismiss itself (aria-label, classes, the X icon) instead of nesting a `<button>` inside it. | 3.4:1 in light. QuoteDismiss renders a `<button>`, so the default rendered a button inside a button (axe nested-interactive, React hydration warning). Unit a2. |
59
+ | `elements/assistant-modal.aui.tsx` | Removed AssistantModalButton's own `sr-only` label span. | TooltipIconButton already renders the tooltip text as an `sr-only` span, so the launcher's accessible name read "Open Assistant Open Assistant". Unit a2. |
60
+ | `elements/model-selector.tsx` | ModelSelectorTrigger gets `aria-label="Model"` (overridable); ModelSelectorContent gets `aria-label="Models"`. | The trigger is a `role="combobox"` button, which takes no name from its content (axe button-name); the popup is an unnamed dialog (aria-dialog-name). The selected model still reads as the combobox's value. Unit a2. |
61
+ | `elements/follow-up-suggestions.aui.tsx` | A space text node before the label span replaces its `ms-1`. | The accessible name ran title and label together ("Purgethe Linear code"). Same spacing on screen. Unit a2. |
62
+ | `elements/markdown-text.tsx` | The markdown `pre` gets `tabIndex={0}` (with a Biome suppression). | A code block that overflows sideways was a scrollable region keyboard users could not scroll (axe scrollable-region-focusable, WCAG 2.1.1). Also covers the Prism highlighter, which renders into this `pre`. Unit a2. |
63
+ | `elements/shiki-highlighter.tsx` | Container gets `dark:scheme-dark`. | The highlighter emits `light-dark()` token colors, which follow `color-scheme`; nothing set it in dark, so dark mode showed the light theme's colors (near-invisible text on the dark block). Scoped to the highlighter. Unit a2. |
64
+ | `elements/heat-graph.tsx` | Cell colors: the empty level is `color-mix(in oklab, var(--foreground) 8%, var(--background))` and the blue steps mix `#2563eb` toward it (were fixed `#ebedf0`...`#2563eb`); labels `text-gray-500` to `text-muted-foreground`; the first month label is hidden when the primitive's next month label sits within two columns of it (CSS on the label siblings, read from the primitive's own labels). | The fixed light-gray empty cells glared in dark mode. The first partial month's label collided with the next month's one column later ("SepOct"), as GitHub's graph avoids. Unit a2. |
65
+ | `elements/context-display.aui.tsx` | Dropped the `@assistant-ui/ai-sdk` import: no `useThreadTokenUsage` fallback and no thread-state read. `usage` is now a required prop on ContextDisplay Root and the presets (Ring, Bar, Text); the presets are the base components themselves re-bound with the narrowed prop type, not wrappers, so props pass straight through; an app that wants the counter to reset on thread switch passes `resetKey` itself. | RFC-02 Design 3 (hub#57, unit a1b): `@assistant-ui/ai-sdk` was the one dependency forcing the `ai` package on every consumer. UsageMeter owns the Usage record and hands it in, so nothing here reads thread state at render. |
66
+ | `elements/geo-map.tsx` | Removed the top-level `import "leaflet/dist/leaflet.css"`. | RFC-02 Design 2 (unit a1b): the CSS moved to the shipped `ai.css` so the dist chunks stay free of CSS imports, which is what lets a consumer tree-shake `./ai`. |
67
+ | `elements/markdown-text.tsx` | Removed the top-level `import "@assistant-ui/react-markdown/styles/dot.css"`. | Same as geo-map: the CSS rides in `ai.css` instead of the JS graph. |
68
+ | `elements/approval-card.tsx` | Two optional slots: `actions` replaces the default request buttons while `state` is "request", and `children` renders between the details and the actions. Subtitle, detail labels and the receipt line `text-foreground/45`, `/40` and `/55` to `text-muted-foreground`. Detail rows get `items-baseline`. | RFC-02 Design 4: ToolApproval builds on this card but needs its own controls (deny with a reason, edit with a diff, HoldButton for dangerous tools, pending and error in place), which the fixed three buttons could not carry; without either slot the card renders as before. Contrast 3.15:1 (subtitle) and lower in light (a11y gate). The 11px mono labels sat higher than their 12px values. Unit a4b. |
69
+ | `elements/cost-meter.tsx` | `sessionCost` is optional (the session figure is hidden without it); a new optional `scopeLabel` replaces the hard-coded "this run" (default unchanged). With no `lines`, the share bar and the line list are not rendered. Meta text `text-foreground/30`, `/35` and `/25` to `text-muted-foreground`; the line cost `text-foreground/55` to `/70`. | RFC-02 Design 4 (unit a4a): UsageMeter builds on CostMeter for one run or a whole thread from one `Usage` record, which has no session total and may cover a thread. A record with a cost but no token counts has no lines, and an empty bar track read as a zero share. Contrast in light: 4.41:1 for the line cost (axe), and about 2:1 for the faint meta text. |
70
+ | `elements/context-breakdown.tsx` | Token counts, the totals and the Headroom row `text-foreground/35` and `/25` to `text-muted-foreground`; the over-85% totals `text-amber-600` to `text-amber-700` (dark unchanged). | Contrast in light (a11y gate), unit a4a. amber-600 measures about 3.2:1 on white. |
71
+ | `elements/guardrail-notice.tsx` | An optional `children` slot renders under the explanation. The policy label `text-foreground/30` to `text-muted-foreground`, and it truncates at half the row (`max-w-1/2 min-w-0 truncate`) instead of `shrink-0`; "try instead" `/30` to `text-muted-foreground`. | RFC-02 Design 4 (unit a4a): RedactionMarker's expandable withheld-field list lives inside the notice, which had no slot for it. A long policy name (`tether-session-summary`) squeezed the title to "3 fields withh...". Contrast in light (a11y gate). |
72
+ | `elements/mcp-server-panel.tsx` | faint text to muted-foreground (contrast policy); the Authorize pill text `text-amber-700` to `text-amber-800`. | Contrast (a11y gate); 4.48:1 on its amber tint. Unit a2c. |
73
+ | `elements/message-pair.tsx` | faint text to muted-foreground (contrast policy); the newest-word tint `text-blue-500` to `text-blue-600` (dark unchanged). | Contrast (a11y gate); 3.76:1 in light. Unit a2c. |
74
+ | `elements/message-queue.tsx` | faint text to muted-foreground (contrast policy). | Text under 4.5:1 in light and/or dark (a11y gate). Unit a2c. |
75
+ | `elements/message-timing.tsx` | faint text to muted-foreground (contrast policy); the streaming value tint `text-blue-500` to `text-blue-600` (dark unchanged). | Contrast (a11y gate); 3.76:1 in light. Unit a2c. |
76
+ | `elements/mobile-composer.tsx` | faint text to muted-foreground (contrast policy). | Text under 4.5:1 in light and/or dark (a11y gate). Unit a2c. |
77
+ | `elements/model-picker.tsx` | faint text to muted-foreground (contrast policy); the capability chips, context and price use `text-foreground/65` instead of muted-foreground. | Contrast (a11y gate); muted-foreground measured 4.06:1 and 4.4:1 on the selected row's stacked tints; /65 measures over 5:1 there. Unit a2c. |
78
+ | `elements/number-ticker.tsx` | faint text to muted-foreground (contrast policy). | Text under 4.5:1 in light and/or dark (a11y gate). Unit a2c. |
79
+ | `elements/onboarding.tsx` | faint text to muted-foreground (contrast policy). | Text under 4.5:1 in light and/or dark (a11y gate). Unit a2c. |
80
+ | `elements/option-list.tsx` | faint text to muted-foreground (contrast policy); the option description uses `text-foreground/65` (muted-foreground measured 4.4:1 on the selected row tint); the unchecked checkbox border `border-foreground/15` to `border-muted-foreground/40`. | Contrast (a11y gate); the unchecked box was a near-invisible hairline in light, same fix as `ui/checkbox.tsx` above. Unit a2c. |
81
+ | `elements/permission-grant.tsx` | faint text to muted-foreground (contrast policy). | Text under 4.5:1 in light and/or dark (a11y gate). Unit a2c. |
82
+ | `elements/prompt-library.tsx` | faint text to muted-foreground (contrast policy); with an empty query the empty list reads "No saved prompts yet" instead of `Nothing matches “”`. | Contrast (a11y gate); the empty-library message quoted an empty search. Unit a2c. |
83
+ | `elements/question-flow.tsx` | faint text to muted-foreground (contrast policy); the step progressbar gets `aria-label="Progress"`. | Contrast (a11y gate); axe aria-progressbar-name. Unit a2c. |
84
+ | `elements/quota-banner.tsx` | faint text to muted-foreground (contrast policy). | Text under 4.5:1 in light and/or dark (a11y gate). Unit a2c. |
85
+ | `elements/quote-reply.tsx` | faint text to muted-foreground (contrast policy). | Text under 4.5:1 in light and/or dark (a11y gate). Unit a2c. |
86
+ | `elements/read-aloud.tsx` | faint text to muted-foreground (contrast policy). | Text under 4.5:1 in light and/or dark (a11y gate). Unit a2c. |
87
+ | `elements/reasoning-effort.tsx` | faint text to muted-foreground (contrast policy); the read-only segment spans get `text-center`. | Contrast (a11y gate); read-only labels sat at the left of their segments (buttons center by default, spans do not). Unit a2c. |
88
+ | `elements/reasoning-panel.tsx` | faint text to muted-foreground (contrast policy). | Text under 4.5:1 in light and/or dark (a11y gate). Unit a2c. |
89
+ | `elements/recommendation-card.tsx` | faint text to muted-foreground (contrast policy). | Text under 4.5:1 in light and/or dark (a11y gate). Unit a2c. |
90
+ | `elements/regenerate-menu.tsx` | faint text to muted-foreground (contrast policy). | Text under 4.5:1 in light and/or dark (a11y gate). Unit a2c. |
91
+ | `elements/research-report.tsx` | faint text to muted-foreground (contrast policy). | Text under 4.5:1 in light and/or dark (a11y gate). Unit a2c. |
92
+ | `elements/retrieval-chunks.tsx` | faint text to muted-foreground (contrast policy); scores of 0.80 and above `text-emerald-600` to `text-emerald-700` (dark unchanged). | Contrast (a11y gate); 3.65:1 in light. Unit a2c. |
93
+ | `elements/reviewable-diff.tsx` | faint text to muted-foreground (contrast policy); a discarded hunk drops its `opacity-40` and shows its changed lines muted and struck through instead of tinted; the kept label `text-emerald-600` to `text-emerald-700`. | Contrast (a11y gate); the 40% fade put every discarded line at 1.7 to 2.7:1; kept label 3.65:1. Unit a2c. |
94
+ | `elements/schedule-card.tsx` | faint text to muted-foreground (contrast policy); the paused next-run field drops `opacity-45`, and its value reads muted-foreground when paused. | Contrast (a11y gate); the fade put "paused" at 2.32:1. Unit a2c. |
95
+ | `elements/score-breakdown.tsx` | faint text to muted-foreground (contrast policy). | Text under 4.5:1 in light and/or dark (a11y gate). Unit a2c. |
96
+ | `elements/scroll-anchor.tsx` | faint text to muted-foreground (contrast policy). | Text under 4.5:1 in light and/or dark (a11y gate). Unit a2c. |
97
+ | `elements/settings-panel.tsx` | faint text to muted-foreground (contrast policy); the read-only model segment spans get `text-center`. | Contrast (a11y gate); same left-aligned read-only segments as reasoning-effort. Unit a2c. |
98
+ | `elements/shared-conversation.tsx` | faint text to muted-foreground (contrast policy). | Text under 4.5:1 in light and/or dark (a11y gate). Unit a2c. |
99
+ | `elements/sources.tsx` | faint text to muted-foreground (contrast policy). | Text under 4.5:1 in light and/or dark (a11y gate). Unit a2c. |
100
+ | `elements/speaker-identity.tsx` | faint text to muted-foreground (contrast policy). | Text under 4.5:1 in light and/or dark (a11y gate). Unit a2c. |
101
+ | `elements/spec-sheet.tsx` | faint text to muted-foreground (contrast policy). | Text under 4.5:1 in light and/or dark (a11y gate). Unit a2c. |
102
+ | `elements/stopped-run.tsx` | faint text to muted-foreground (contrast policy). | Text under 4.5:1 in light and/or dark (a11y gate). Unit a2c. |
103
+ | `elements/streaming-text.tsx` | faint text to muted-foreground (contrast policy); the newest-word tint `text-blue-500` to `text-blue-600` (dark unchanged). | Contrast (a11y gate); 3.76:1 in light. Unit a2c. |
104
+ | `elements/subagent-list.tsx` | faint text to muted-foreground (contrast policy). | Text under 4.5:1 in light and/or dark (a11y gate). Unit a2c. |
105
+ | `elements/suggestions.tsx` | The selected pill adds `dark:bg-foreground`. | `paper`'s `dark:bg-popover` outranked `bg-foreground`, so a picked suggestion was near-black text on near-black (1.1:1) in dark. Unit a2c. |
106
+ | `elements/surfaces.tsx` | faint text to muted-foreground (contrast policy); this is the shared `ghostButton` token (`text-foreground/45`), so every element's ghost buttons with text change with it. | Contrast (a11y gate). Unit a2c. |
107
+ | `elements/terminal-block.tsx` | faint text to muted-foreground (contrast policy); ink variant faint text `text-background/NN dark:text-foreground/NN` (35 to 55) to `/60` (muted-foreground is for light surfaces and fails on ink); ANSI 32 (paper) `text-emerald-600` to `text-emerald-700`; a dim ANSI segment takes the muted color instead of `opacity-60`. | Contrast (a11y gate); 2.37:1 dim text, 3.24:1 ink meta, 3.65:1 green. Other bright ANSI paper colors (33, 36, 9x) still measure under 4.5:1; no story uses them yet. Unit a2c. |
108
+ | `elements/thinking-indicator.tsx` | faint text to muted-foreground (contrast policy). | Text under 4.5:1 in light and/or dark (a11y gate). Unit a2c. |
109
+ | `elements/thread-list.tsx` | faint text to muted-foreground (contrast policy). | Text under 4.5:1 in light and/or dark (a11y gate). Unit a2c. |
110
+ | `elements/thread-search.tsx` | faint text to muted-foreground (contrast policy). | Text under 4.5:1 in light and/or dark (a11y gate). Unit a2c. |
111
+ | `elements/timeline.tsx` | faint text to muted-foreground (contrast policy). | Text under 4.5:1 in light and/or dark (a11y gate). Unit a2c. |
112
+ | `elements/todo-list.tsx` | faint text to muted-foreground (contrast policy); the pending box border `border-foreground/15` to `border-muted-foreground/40`. | Contrast (a11y gate); near-invisible hairline in light, same as option-list. Unit a2c. |
113
+ | `elements/tool-call.tsx` | faint text to muted-foreground (contrast policy). | Text under 4.5:1 in light and/or dark (a11y gate). Unit a2c. |
114
+ | `elements/tool-error.tsx` | faint text to muted-foreground (contrast policy). | Text under 4.5:1 in light and/or dark (a11y gate). Unit a2c. |
115
+ | `elements/tool-group.tsx` | faint text to muted-foreground (contrast policy). | Text under 4.5:1 in light and/or dark (a11y gate). Unit a2c. |
116
+ | `elements/tool-timeline.tsx` | faint text to muted-foreground (contrast policy); the file stat counts `text-emerald-600`/`text-red-600` to `-700` (dark unchanged). Additive, opt-in selection: `selectedId`, `onSelectedIdChange` and `listLabel` props make the step list a single-select listbox (options, `aria-activedescendant`, click, Up/Down/Home/End); `TimelineStep` gains optional `id` (the row key, defaulting to the chip as before) and `label` (the option's name), and `icon` widens to any component taking a className. When selectable, rows truncate the verb and the chip, and the file stats render after the listbox. Without `onSelectedIdChange` the markup is unchanged. | Contrast (a11y gate); 3.2:1 and 4.18:1 on the chip tint. Unit a2c. Selection: RunInspector (RFC-02 Design 4) builds its timeline view on this element, and hub#61 needs a step to be selectable with a click and the arrow keys; the element had no way to select a row. The icon widening lets the row carry a StatusGlyph. Keying rows by chip also collided when two steps share a tool. Unit a5b. |
117
+ | `elements/trace-waterfall.tsx` | faint text to muted-foreground (contrast policy). Additive, opt-in selection: `selectedId`, `onSelectedIdChange` and `listLabel` props make the spans a single-select listbox (options, `aria-activedescendant`, click, Up/Down/Home/End), with the selected row filled and its name and duration darkened; `TraceSpan` gains an optional `label` (the option's name; the bar's `role="img"` is hidden inside an option). Without `onSelectedIdChange` the markup is unchanged. | Text under 4.5:1 in light and/or dark (a11y gate). Unit a2c. Selection: RunInspector (RFC-02 Design 4) builds its waterfall view on this element, and hub#61 needs a step to be selectable with a click and the arrow keys. The selected duration darkens because muted text measured 4.4:1 on the selected fill. Unit a5b. |
118
+ | `elements/web-preview.tsx` | faint text to muted-foreground (contrast policy). | Text under 4.5:1 in light and/or dark (a11y gate). Unit a2c. |
119
+ | `elements/web-search.tsx` | faint text to muted-foreground (contrast policy). | Text under 4.5:1 in light and/or dark (a11y gate). Unit a2c. |
120
+ | `elements/activity-graph.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
121
+ | `elements/agent-card.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
122
+ | `elements/agent-handoff.tsx` | faint text to muted-foreground (contrast policy); the settled `opacity-45` on the from-chip removed. | The opacity took the chip text to 1.79:1. Settled still reads from the arrow and the to-chip losing its blue. Unit a2b. |
123
+ | `elements/agent-plan.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
124
+ | `elements/approval-card.tsx` | faint text to muted-foreground (contrast policy); the Deny and Always-allow text buttons add `text-muted-foreground` over ghostButton's `text-foreground/45`. | ghostButton text measured 3.15:1 (light) and 4.35:1 (dark). surfaces.tsx is untouched, so icon-only ghost buttons keep their look. Unit a2b. |
125
+ | `elements/artifact-card.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
126
+ | `elements/background-inbox.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
127
+ | `elements/canvas-split.tsx` | faint text to muted-foreground (contrast policy); the "saved" mark `text-emerald-600` to `text-emerald-700`. | emerald-600 measured 3.65:1 on white. Unit a2b. |
128
+ | `elements/chart.tsx` | faint text to muted-foreground (contrast policy); the good-news delta `text-emerald-600` to `text-emerald-700`. | 3.65:1 on white. Unit a2b. |
129
+ | `elements/chat-panel.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
130
+ | `elements/checkpoint-history.tsx` | faint text to muted-foreground (contrast policy); checkpoints after the current one are dimmed with `text-muted-foreground` instead of `opacity-40`; "1 files" reads "1 file". | The opacity took their text to 2.71:1 and 1.72:1. The hollow dot still marks them as undone. Pluralization defect. Unit a2b. |
131
+ | `elements/code-diff.tsx` | faint text to muted-foreground (contrast policy); the additions count `text-emerald-600` to `text-emerald-700`; the horizontal scroll region gets `tabIndex={0}` (Biome suppression). | 3.65:1 on white. A long line made an unfocusable scroll region (axe scrollable-region-focusable, WCAG 2.1.1). Unit a2b. |
132
+ | `elements/code-runner.tsx` | faint text to muted-foreground (contrast policy); the code `pre` and the output scroll region get `tabIndex={0}` (Biome suppressions). | Snippets wider than the card made unfocusable scroll regions (axe scrollable-region-focusable). Unit a2b. |
133
+ | `elements/command-palette.tsx` | faint text to muted-foreground (contrast policy) (including the input placeholder); the listbox is `hidden` when nothing matches. | With no match the empty, bordered listbox drew a blank band and a second divider above "No command matches". Unit a2b. |
134
+ | `elements/comparison-card.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
135
+ | `elements/composer.tsx` | faint text to muted-foreground (contrast policy); a rejected attachment's meta `text-red-600/80` to `text-red-700` (dark `text-red-400`); the context panel's warning percent `text-red-500` to `text-red-600`. | 3.85:1 and 3.8:1 in light. Unit a2b. |
136
+ | `elements/computer-use.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
137
+ | `elements/confidence-marker.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
138
+ | `elements/confidence-marker.tsx` | The space after each claim moves out of its button (each claim renders as a keyed Fragment of the button and a `" "`). | A button is laid out as an inline-block, which drops its own trailing space, so consecutive claims ran together ("Friday.Legal will"). Unit a5a (AttentionFeed). |
139
+ | `elements/connection-state.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
140
+ | `elements/context-breakdown.tsx` | faint text to muted-foreground (contrast policy); the over-85% total `text-amber-600` to `text-amber-700`. | 3.19:1 on white. Unit a2b. |
141
+ | `elements/conversation-map.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
142
+ | `elements/conversation-search.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
143
+ | `elements/cost-meter.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
144
+ | `elements/data-table.tsx` | faint text to muted-foreground (contrast policy); the good-news delta `text-emerald-600` to `text-emerald-700`; the warning badge text `text-amber-700` to `text-amber-800` (dark unchanged). | 3.65:1 on white; the badge measured 4.38:1 on the narrow layout's card. Unit a2b. |
145
+ | `elements/day-separator.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
146
+ | `elements/diagram.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
147
+ | `elements/document-reference.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
148
+ | `elements/draft-restore.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
149
+ | `elements/edit-message.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
150
+ | `elements/elicitation-form.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
151
+ | `elements/empty-state.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
152
+ | `elements/error-state.tsx` | faint text to muted-foreground (contrast policy: the Retrying label); title and Retry `text-red-600` to `text-red-700`; the detail `text-red-600/60 dark:text-red-400/60` to `text-red-800/80 dark:text-red-300/80`. | On the red tint: 4.37:1 (title, Retry), 2.89:1 light and 3.07:1 dark (detail). Unit a2b. |
153
+ | `elements/feedback-dialog.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
154
+ | `elements/file-tree.tsx` | faint text to muted-foreground (contrast policy); the additions counts `text-emerald-600` to `text-emerald-700`; "1 files changed" reads "1 file changed". | 3.65:1 on white. Pluralization defect. Unit a2b. |
155
+ | `elements/geo-map.tsx` | faint text to muted-foreground (contrast policy); on the selected place row the description and coordinates darken to `text-foreground/70` (`group-aria-[current=true]:`). | muted-foreground measured 4.4:1 on the selected row fill. Unit a2b. |
156
+ | `elements/guardrail-notice.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
157
+ | `elements/image-gallery.tsx` | The "+N" overflow overlay `bg-foreground/65 text-background` to `bg-black/60 text-white`. | In dark mode the overlay turned into a white wash with dark text over the last tile. A scrim reads the same in both themes. Unit a2b. |
158
+ | `elements/image-generation.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
159
+ | `elements/inline-citation.tsx` | faint text to muted-foreground (contrast policy) (the citation chip number and the source card). | Story a11y gate (color-contrast). `cursor-default` on the chip stays; the global pointer rule overrides it. Unit a2b. |
160
+ | `elements/job-progress.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
161
+ | `elements/launcher-bubble.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
162
+ | `elements/link-preview.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
163
+ | `elements/map-answer.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
164
+ | `elements/math-block.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
165
+ | `elements/media-player.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
166
+ | `elements/memory-chips.tsx` | faint text to muted-foreground (contrast policy); a chip without a forget button pads its end `pr-2.5` instead of `pr-1`. | pr-1 leaves room for the forget button; read-only chips sat tight against their right edge. Unit a2b. |
167
+ | `elements/mermaid-diagram.tsx` | The streaming skeleton gets `role="status"`. | It carried `aria-label` on a plain div (axe aria-prohibited-attr). Unit a2b. |
168
+ | `elements/message-attachment.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
169
+ | `elements/message-branches.tsx` | faint text to muted-foreground (contrast policy). | Story a11y gate (color-contrast), unit a2b. |
170
+ | `elements/approval-card.tsx` | The details list is one grid (`grid-cols-[minmax(min-content,1fr)_minmax(0,2fr)]`) whose rows are subgrids (`col-span-2 grid-cols-subgrid`), replacing a separate `minmax(0,1fr)` grid per row. | Visual QA (hub#62): in a narrow card (ToolApproval in a thread at 390px) the label column fell below its longest word, so `olderThanHours` broke mid-word ("olderThanHou / rs"). The label column is now never narrower than its longest label, and the value column still lines up across rows. |
171
+ | `elements/context-display.tsx` | `ContextDisplayTrigger` passes `closeOnClick={false}` to its Tooltip trigger. | Visual QA (hub#62): the breakdown opened on hover and focus, but pressing the button (its only purpose) closed it, so a click or Enter showed nothing. |
172
+ | `elements/context-display.tsx` | The usage colors read from admin-ui's shared `contextLevel` (`src/lib/context-level.ts`: warning from 65%, critical from 90%) instead of their own thresholds (critical above 85%). | Visual QA round 2 (hub#62): UsageMeter showed one reading red in the ring and amber in the expanded ContextBreakdown (87% of the window). One helper now colors both. |
173
+ | `elements/context-display.tsx` | ContextDisplayRoot holds the tooltip's open state, and ContextDisplayTrigger opens it on press (`onClick`, merged with any caller's) with `closeOnClick={false}`. Hover, focus, Escape, leaving and an outside press behave as before. | Visual QA round 2 (hub#62): a click on the ring shut the breakdown that hover or focus had just opened, and on a touch screen a tap never opened it, so the breakdown was unreachable on a phone. |
174
+ | `elements/context-breakdown.tsx` | The used/limit total colors by the shared `contextLevel`: amber (`text-amber-700`, dark `text-amber-400`) from 65%, red (`text-red-700`, dark `text-red-400`) from 90%, instead of amber above 85% only. The Headroom dot gets a `border-foreground/30` outline over its `bg-foreground/[0.06]` fill. | Visual QA round 2 (hub#62): the same reading disagreed with ContextDisplay's ring (see above). The Headroom dot, a translucent fill only, was invisible on the dark panel. |
175
+ | `elements/tool-timeline.tsx` | Selection mode only (admin-ui's own addition): the listbox is a size container with `p-1` and a 1px inset focus ring (`ring-1 ring-ring/70`) instead of `p-0.5` and a 2px ring. Below 24rem a row wraps its label and puts the chip on a second line under it; from 24rem the row is one line as before, the label truncating and the chip capped at 45% of the list (`45cqw`). | Visual QA round 2 (hub#62): the 2px ring hugged the rows, so the selected row's fill ran into it, and it was heavier than the inspector's other focus states. On a phone, RunInspector's labels and chips truncated to stubs ("Unsubscribed from De...", "classify_messag..."). |
176
+ | `elements/trace-waterfall.tsx` | An optional `formatDuration` prop formats the total and each span's duration (without it, bare milliseconds as before). Selection mode only: the name and bar columns split 3:2 with a 3.5rem duration column (instead of 7.5rem, the rest and 2.5rem), each name carries its full text as `title`, and the listbox gets `p-1` with a 1px inset focus ring, as in ToolTimeline. | Visual QA round 2 (hub#62): RunInspector's waterfall truncated most step names at 7.5rem, printed "12300ms" and unitless row values beside the timeline's "12.3 s", and its focus ring touched the selected row's fill. |
177
+
178
+ ## Visual QA fix round 2 (hub#62, unit q4, 2026-10-04)
179
+
180
+ Edits made during the second visual QA pass, in addition to the table above.
181
+
182
+ | File | Change | Why |
183
+ |---|---|---|
184
+ | `elements/tool-group.aui.tsx` | ToolGroupTrigger: added `rounded-md outline-none focus-visible:ring-[3px] focus-visible:ring-ring/50`; the outline/muted variants stretch the trigger over the whole header row (`-my-3 min-h-9`, ring inset), the ghost variant gains `px-1 -mx-1`. | After a click the trigger showed the browser's default square outline, a ~12px rectangle drawn through the 36px header (heavy white in dark). The icon also touched the ring's left edge in ghost. |
185
+ | `elements/syntax-highlighter.tsx` | Registered the `json` Prism language; the coldark themes are passed through `withoutPreBackground`, which drops `pre[class*="language-"]`'s background. | The theme's `#e2eaf2` / `#111b27` fills were off the neutral palette and mismatched the code header, the plain markdown pre and the Shiki blocks; without them the markdown pre's own `bg-muted/30` shows, as in every other code block. `json` is the MarkdownText story's demo language. |
186
+ | `elements/follow-up-suggestions.aui.tsx` | The suggestions row wraps (`flex-wrap gap-2`, centered) instead of side-scrolling under a fade mask; the RTL scroll/fade machinery is gone. `AuiIf` also hides the row while the thread's last message is from the user. | A chip cut mid-word at the scroll edge read as a truncated label (same in Thread, ThreadlistSidebar, AssistantSidebar); on narrow panes the scroll was undiscoverable. After sending a suggestion, the row re-offered what was just chosen. |
187
+ | `elements/threadlist-sidebar.aui.tsx` | Added optional `header` and `footer` ReactNode props; both default to the registry demo content (assistant-ui branding, GitHub links), and `footer` can be dropped by passing a falsy value. | An app had no way to replace the demo branding; the props keep the vanilla item unchanged until they are used. |
188
+ | `elements/reasoning.tsx` | ReasoningTrigger: `rounded-md outline-none focus-visible:ring-[3px] focus-visible:ring-ring/50`. ReasoningContent no longer renders the always-on top fade; ReasoningText renders it itself as a sticky overlay that only appears while the text is scrolled down. | The native square focus outline after a click, and the static top fade washed out the first line of an open panel. |
189
+ | `elements/task-card.tsx` | The header button gets `rounded-md outline-none focus-visible:ring-2 focus-visible:ring-ring/50 focus-visible:ring-inset`. | Keyboard focus showed the native outline, clipped by the card's `overflow-hidden` (no top or sides in dark). |
190
+ | `elements/thread.aui.tsx` | ThreadScrollToBottom: `dark:border-border dark:bg-background dark:hover:bg-accent` replaced with `border-border bg-background shadow-sm hover:bg-accent` (both themes). The composer shell dims when the thread is disabled (`data-disabled` + `opacity-50 cursor-not-allowed`; the input placeholder fades further). The viewport gets a top `mask-image` fade (transparent to black over 1.5rem). | The scroll button was transparent in light mode, so the arrow glyph collided with the message text under it; the Disabled thread showed no disabled composer; a thread opens scrolled to its end, and the first bubble read as sliced rather than scrolled past. |
191
+ | `elements/attachment.aui.tsx` | ComposerAddAttachment: removed `dark:border-muted-foreground/15`. | The + button had a visible border only in dark mode; the two themes disagreed. |
192
+ | `elements/sources.aui.tsx` | Document sources render with the same `sourceVariants()` chip as URL sources (was a `secondary` Badge); both chip kinds get `me-1.5 mt-2` (round 1 used `ms-1.5`). | The document chip was a filled, smaller, bolder badge next to outlined chips (two components in one row), and adjacent chips' borders touched. A leading margin indented the row 6px from the text column, and the row sat flush under the text. |
193
+ | `elements/thread-list.aui.tsx` | The search input hides the native cancel button: `[&::-webkit-search-cancel-button]:hidden`. | Chromium drew its blue OS X cancel glyph in both themes; off-token next to the neutral inputs. |
194
+ | `elements/tool-fallback.aui.tsx` | ToolFallbackTrigger: `rounded-md ps-1 -ms-1 outline-none focus-visible:ring-[3px] focus-visible:ring-ring/50`; new `denied` prop renders "Denied tool" with the x-circle icon. ToolFallbackImpl passes it when the approval settled refused. | The native square outline after a click (icon touching its edge), and a denied gated call still read "Used tool" with a check. |
195
+ | `elements/directive-text.tsx` | The mention chip adds `border-border bg-background border`. | `--secondary` equals `--muted`, so secondary chips were invisible inside the muted user bubble in both themes. |
196
+ | `elements/model-selector.tsx` | ModelSelectorItem reserves the icon slot (`size-3.5` placeholder) for models without an icon. | Models without a logo started their text 22px left of the others; the rows misaligned. |
197
+ | `elements/mcp-config.aui.tsx` | The AuthSelect (a native `<select>`) is styled like the form's inputs (`appearance-none`, border/input tokens, focus ring) with a lucide chevron overlay. | Chromium painted the bare select black in dark mode with the OS chevron, visibly a different element beside the shadcn inputs. |
198
+ | `elements/context-display.tsx` | The ring's track `stroke-muted` to `stroke-muted-foreground/30`; the bar's reading gains `font-mono`. | At 0% the track was nearly invisible on white, and the reading mixed mono (ring, text) and sans (bar) across variants. |
199
+ | `elements/heat-graph.tsx` | The empty level is `var(--aui-heat-empty)`, defined in `src/styles/ai.css`: a faint foreground tint in light, `var(--muted)` in dark (was a fixed 8% foreground mix in both). | In dark the 8% tint was barely a step above the background, so empty cells and the lowest bucket read as holes. |
200
+ | `elements/conversation-map.tsx` | Inactive ticks `bg-foreground/15` to `bg-muted-foreground/40`. | The inactive ticks were nearly invisible on white. |
201
+ | `src/styles/ai.css` | `.shimmer:not(.shimmer-bg) { --shimmer-color: var(--foreground); }` and the `--aui-heat-empty` token above. | The tw-shimmer overlay band defaults to white, which erased the glyphs it swept in light mode ("Ru ng tool" mid-sweep). The band now sweeps toward the foreground color, dark on light and light on dark. |
202
+
203
+ The same round changed only stories or test fixtures elsewhere (MarkdownText and
204
+ ModelSelector story setups, the image chart fixture, the heat-graph sparse
205
+ fixture, the conversation-map and file story frames), which carry no vendored
206
+ component change.
207
+
208
+ ## Visual QA pass (2026-10-04, unit q5, hub#62)
209
+
210
+ Element fixes from the AI/Elements review. Story-only fixes (demo data, lead-in
211
+ copy, `max-w-none` frame fills) are not vendored changes and are not listed.
212
+
213
+ | File | Change | Why |
214
+ |---|---|---|
215
+ | `src/styles/globals.css` | After the tw-shimmer import: `.shimmer:where(:not(.shimmer-bg)) { --shimmer-color: var(--foreground); }`. | tw-shimmer's light-mode sweep peaks at currentColor at 20% alpha, so shimmering labels (LoadingState, tool-fallback, attachment) faded to near-invisible mid-sweep on light surfaces; dark already swept brighter. The sweep never runs toward the background now. |
216
+ | `elements/conversation-map.tsx` | Additive `onPreviewChange?: (open: boolean) => void`, passed to `PreviewCard.Root` as `onOpenChange`. | The story's hint text sat in the preview card's slot and was sliced by the open card. Apps need the open state to clear the slot; additive and unused by default. |
217
+ | `elements/composer.tsx` | `ComposerContext` root drops `relative` (the breakdown popover then anchors to the composer, opening above the whole bar instead of over the input); the idle ring track `stroke-foreground/10` to `/25`. | The popover overlapped the composer's input text and read as detached from the ring. The /10 track made the idle gauge read as a spinner. |
218
+ | `elements/code-runner.tsx` | The code panel renders through the library's Prism `SyntaxHighlighter` (`CodePre` strips the theme's tinted background, padding and font, keeps the light/dark className); a `PRISM_LANGUAGE` map sends `typescript`/`javascript` to the registered Prism keys. | Owner rule "code must highlight on first load": the runner's source was monochrome while every other code surface highlighted. The sync Prism build paints on mount. |
219
+ | `elements/mcp-server-panel.tsx` | Authorize renders as a shadcn `Button variant="outline" size="xs"` instead of the amber pill; the tools count pluralizes. | The amber pill matched the status-badge look (and read as one); the native focus outline was the only keyboard cue. Pluralization defect ("1 tools"). |
220
+ | `elements/document-reference.tsx` | Passage rows: with `onJump` they get `focus-visible:ring-[3px] ring-ring/50 ring-inset`; without it the active-page fill no longer applies. | The UA default focus ring was a thick grey/white box. Read-only kept the interactive "selected" fill, so the story name lied. |
221
+ | `elements/guardrail-notice.tsx` | "try instead" alternatives render as ghost rows with a leading chevron and the standard inset focus ring; without `onPick` they stay plain muted text. | The alternatives read as static text while being buttons; the default focus ring overhung the text column. |
222
+ | `elements/error-state.tsx` | Focus returns to Retry when `retrying` ends with the error back; Retry gets the standard focus-visible ring. | The Retrying status renders without the button, so keyboard focus fell to the body and the end state showed no focus at all. |
223
+ | `elements/background-inbox.tsx` | Row buttons get the inset 3px focus ring; an empty `runs` renders a "Nothing running" status line. | The UA default ring was heavy (bright white in dark). The empty story showed only the header. |
224
+ | `elements/media-player.tsx` | `VideoPlayer` renders the same custom control strip as `AudioPlayer` (play/pause, seek slider, time) with `playsInline` and no `controls`; error state and single caption row match the audio player's. | Chrome's default controls bar plus its buffering spinner over the poster matched nothing else in the library and looked broken; the duration was duplicated in the caption. |
225
+ | `elements/elicitation-form.tsx` | The header status is a dot plus text and follows the state (needs input / sent / declined, amber / emerald / neutral); a settled form renders its values as plain text instead of filled inputs, chips and switches. | After Accept/Decline the card still read "needs input" and looked actionable (owner taste: status under a title is a dot plus text). |
226
+ | `elements/code-diff.tsx` | The diff body soft-wraps (`break-words whitespace-pre-wrap`) with the gutter as a fixed leading column; the horizontal scroll region and its tabIndex are gone. | Long lines were hard-clipped at the card edge with no scrollbar or fade, hiding the actual change. Wrapping shows all content. |
227
+ | `elements/map-answer.tsx` | Pins and list rows carry their route order (numbered discs); the list rows use the inset 3px focus ring. | "Stops, in order" was unreadable from the map. The UA default outline was clipped by the card's rounded corners and mismatched the muted fill used for click-selection. |
228
+ | `elements/launcher-bubble.tsx` | The unread badge gets `border border-border`. | The badge is half outside the ink circle; its outer half had no edge against a matching page background and read as a bite out of the bubble. |
229
+ | `elements/image-gallery.tsx` | Tiles: `focus-visible:ring-[3px] ring-ring/50 ring-offset-2 ring-offset-background` replaces the 1px /30 ring. | Focus returned from the lightbox was a faint 1px outline, near-invisible in dark. |
230
+ | `elements/directive-text.tsx` | The chip adds `border-border` (over the Badge's transparent border). | The secondary fill (0.97) is near-white on white, so chips barely read in light and their padding read as stray gaps before punctuation. |
231
+ | `elements/context-breakdown.tsx` | The Headroom legend dot renders as an outlined ring (`border-muted-foreground/50`, transparent fill). | It used the track colour and disappeared in both themes. |
232
+ | `elements/file-tree.tsx` | Additions and deletions render in two fixed `w-7 text-end` slots (the empty slot keeps its width). | Add-only rows right-aligned into the deletions column, so the stats drifted down the tree. |
233
+ | `elements/computer-use.tsx` | The click trail renders as outlined rings at 0.14-0.42 opacity (was filled dots at 0.18-0.54). | Filled blue dots sat on the mock UI's labels and read as glitches; rings read as markers. |
234
+ | `elements/checkpoint-history.tsx` | The checkpoint label wraps (`break-words`, `leading-snug`) instead of truncating. | Labels cut off while the row's hidden hover-restore button held ~80px of invisible width. |
235
+ | `elements/context-display.tsx` | The Bar reading `text-[10px]` to `text-xs`; the track `bg-muted` to `bg-muted-foreground/20`. | The reading was 9-10px and the light-mode track invisible. |
236
+ | `elements/image-generation.tsx` | The size label gets a `bg-black/60` scrim pill (was naked `text-white/70`); the caption wraps to two lines (`line-clamp-2`) under the regenerate icon. | White/70 over the pale peach gradient was unreadable; the caption truncated at one line beside free space. |
237
+ | `elements/conversation-search.tsx` | The match counter and the minimap render only with a query; no matches reads `0/0`. | An empty query already showed "0" (identical to no-matches) plus an orphan empty minimap track. |
238
+ | `elements/math-block.tsx` | `Frac` renders at `text-[1em]` (was `0.85em`). | A display fraction at 85% made the numeric line visibly smaller than the symbolic one (the `\\dfrac` fix). |
239
+ | `elements/confidence-marker.tsx` | The basis slot is content-sized (`min-h-0`, was a reserved `h-9`). | Unhovered cards carried a tall empty strip under the claims. |
240
+ | `elements/diagram.tsx` | The full-screen button renders only with `onExpand` (was a disabled ghost). | A permanently disabled button reads as a broken control, not an absent feature. |
241
+ | `elements/command-palette.tsx` | Without `onRun`: the input is `readOnly` (aria-readonly) and muted, rows render muted with no active fill. | The read-only story was pixel-identical to Default. |
242
+ | `elements/option-list.tsx` | The display-only branch (no `onConfirm`) renders its rows in muted foreground. | Same: read-only rows looked pickable. |
243
+ | `elements/feedback-dialog.tsx` | Without `onToggleReason` only the chosen reason chips render; the note renders as plain text when there is no `onNoteChange` (an empty note renders nothing). | The read-only card showed togglable-looking chips and an empty "Anything else?" textarea. |
244
+ | `elements/cost-meter.tsx` | A line's token reading omits a zero side ("21.4k in" instead of "21.4k in · 0.0k out"). | "0.0k out" is noise. |
245
+ | `elements/shiki-highlighter.tsx` | `highlightLines` now maps to react-shiki's built-in `highlightLineNumbers` option (the custom `.highlighted` transformer is gone); streaming no longer forces plain code, it highlights as it arrives (throttled by `delay`). | The custom transformer added a class with no CSS anywhere, so highlighted lines were invisible. Owner feedback: code must highlight on first load. Unit q6 (visual QA, hub#62). |
246
+ | `elements/shiki-highlighter.aui.tsx` | Docstring only: streaming description updated to match the new behavior. | Keeps vendored docs truthful. Unit q6. |
247
+ | `elements/terminal-block.tsx` | Running cursor `bg-blue-500/70 dark:bg-blue-400/70` to `bg-current` with token text colors; the Show all/Show less button gains `-ml-2`; the output reserve `min-h-[8.5rem]` to `min-h-[6.5rem]`. | Off-token cursor colors inconsistent between themes; the toggle label did not align with the output column; the old reserve left a large empty band under short output. Unit q6. |
248
+ | `elements/reviewable-diff.tsx` | Discarded-hunk `line-through` moved from the row to an inner span around the code text, with leading whitespace outside it. | The strike crossed the gutter gap and the indentation, reading as a dash prefix. Unit q6. |
249
+ | `elements/message-pair.tsx` | Fresh-word blue tint removed (the opacity fade stays); caret `bg-foreground`; a streaming reply with zero words renders three visible-at-rest pulsing dots (`role="status"`, motion-reduce safe). | Off-token blue on fresh tokens; a waiting reply rendered as an empty card. Unit q6. |
250
+ | `elements/streaming-text.tsx` | Same de-blue and caret change as message-pair, plus the same visible waiting dots for the zero-words state. | Same defects; the two elements stay visually consistent. Unit q6. |
251
+ | `elements/message-branches.tsx` | The prev/counter/next pager renders only when there is more than one version (hideWhenSingleBranch); the counter gets `px-1`. | An enabled-looking "1 / 1" pager is noise; the chevron focus ring had no clearance from the counter. Unit q6. |
252
+ | `elements/message-timing.tsx` | Live streaming values `text-blue-600 dark:text-blue-400` to `text-foreground`. | Hard-coded blue off-token. Unit q6. |
253
+ | `elements/message-attachment.tsx` | All attachment kinds share one surface (the field muted fill, `px-3 py-2`, `rounded-2xl`); the trailing ImageIcon is gone; rows get `focus-visible:outline-hidden` + `ring-2 ring-ring/50`. | Image rows styled differently from file rows in one stack; the UA default focus outline was off-family. Unit q6. |
254
+ | `elements/thinking-indicator.tsx` | ShimmerLabel gains `shimmer-color-foreground`. | tw-shimmer's light sweep fades text to 20% alpha, erasing letters on light surfaces. Unit q6. |
255
+ | `elements/tool-call.tsx` | Same `shimmer-color-foreground` on the running label. | Same shimmer defect. Unit q6. |
256
+ | `elements/tool-group.tsx` | The trigger button gets `rounded-t-2xl outline-none focus-visible:ring-2 focus-visible:ring-inset focus-visible:ring-ring/50`. | The UA focus outline was clipped by the card's overflow to a stray bottom line. Unit q6. |
257
+ | `elements/tool-error.tsx` | Retry disables (and dims to `opacity-30`) once `attempt >= maxAttempts`; Retry gains `min-w-24`. | A spent retry budget must read as spent; the Skip button shifted when the label grew to "Retrying". Unit q6. |
258
+ | `elements/tool-timeline.tsx` | `shimmer-color-foreground` on the streaming label; the listbox padding `p-0.5` to `p-1`. | Same shimmer defect on the Working label; the selected row fill ran into the inset focus ring. Unit q6. |
259
+ | `elements/trace-waterfall.tsx` | Running bars `bg-blue-500 dark:bg-blue-400` to `bg-chart-2`; the listbox gets `p-1` and an inset focus ring. | Raw blue matched no theme token; padding ends the selected-fill/ring collision. Unit q6. |
260
+ | `elements/reasoning.tsx` | Trigger gets `rounded-md px-1.5 -mx-1.5 outline-none focus-visible:ring-[3px] focus-visible:ring-ring/50`; the top/bottom fade masks render only when the text is scrolled away from that edge (data-scroll-top/bottom from a scroll + resize observer); light-mode shimmer sweep to foreground on the trigger label. | Raw UA focus rectangle; masks dimmed the first line of an unscrolled panel; the light shimmer erased letters. Unit q6. |
261
+ | `elements/surfaces.tsx` | `floating` gains `shadow-sm dark:bg-foreground/[0.10] dark:border-white/10 dark:shadow-none`; `field` and `fieldInteractive` drop to `dark:bg-foreground/[0.03]`; ShimmerLabel sweeps to foreground in light (`[--shimmer-color:var(--color-foreground)]`, dark keeps the util default). | paper and floating rendered the same block in dark (invisible shadow); the light-mode shimmer highlight vanished over white. Shared tokens, so every consumer changes with them. Unit q6. |
262
+ | `elements/score-breakdown.tsx` | A pending header (skeleton score chip, dot plus "Grading k of n", aria-busy) renders while fewer than all criteria are graded; the verdict is a coloured dot plus text in every state (pill removed). | An in-progress state read as a final pass; pills-for-status is the pattern the owner retired. Unit q6. |
263
+ | `elements/reasoning-effort.tsx` | Segment items get `outline-none focus-visible:ring-[3px] focus-visible:ring-inset focus-visible:ring-ring/50`. | The raw UA outline touched the track edges; ring family fix. Unit q6. |
264
+ | `elements/research-report.tsx` | Spinner and done checks to `text-muted-foreground`. | Hard-coded blue spinner; checks nearly invisible on white. Unit q6. |
265
+ | `elements/mobile-composer.tsx` | The single-line input is an auto-growing textarea (`rows=1`, `field-sizing:content`, `max-h-28`); the quick-action row gets a right-edge mask fade; the footer keeps the home indicator in every state, with the send hint above it while the keyboard is open. | A typed draft clipped at the send button with no wrap; the chip row hard-cut mid-word; the footer jumped between states. Unit q6. |
266
+ | `elements/thread-search.tsx` | Row buttons `outline-none` + `focus-visible:bg-foreground/[0.05]`; the pin icon moved to the trailing side; the group label "pinned" to "Pinned". | The UA focus outline drew a heavy ring over the active fill; the pin glyph indented the title against its own subtitle. Unit q6. |
267
+ | `elements/thread-list.tsx` | Empty state: the group header hides and a centred "No conversations yet" renders; static-actions mode hides the timestamp; action icons use the shared ghostButton surface with `gap-1`; row buttons get the focus fill. | An orphan "Today" header over nothing read as broken; static actions squeezed every title; icon buttons had no focus-visible style so the UA ring appeared. Unit q6. |
268
+ | `elements/task-card.tsx` | Header button `outline-none` + `focus-visible:bg-foreground/[0.05]`; the chevron slot is reserved with an invisible spacer on non-expandable cards; chevron `text-foreground/25` to `text-muted-foreground`. | UA focus outline clipped by overflow-hidden into a box; ragged meta column across stacked cards; the chevron barely signalled expandability. Unit q6. |
269
+ | `elements/retrieval-chunks.tsx` | Skeleton chunk cards render while searching (after the real ones); the min-height reserve applies only while searching or when passages exist. | Static "Retrieving" text over a 130px void; the empty state held reserved height. Unit q6. |
270
+ | `elements/onboarding.tsx` | Inactive step dots `bg-foreground/15` to `bg-muted-foreground/40`; the active dash `bg-foreground/60` to `bg-foreground`. | The indicator read as a single dash in light and stayed faint in dark. Unit q6. |
271
+ | `elements/todo-list.tsx` | The header count gains "- N skipped" when cancelled items exist. | The count said 2/6 while seven rows rendered, with nothing explaining the cancelled row. Unit q6. |
272
+ | `elements/option-list.tsx` | A shared OptionMarker (radio circle for single-select, tick box for multiple) renders at the start of every row, display-only rows included; the footer reads "N selected - up to M". | Options rendered as bare text with no control affordance; the footer count was ambiguous. Unit q6 (high finding). |
273
+ | `elements/question-flow.tsx` | The overview (display-only) branch passes `selectionMode` down to OptionList. | Without it every overview question showed single-select markers. Unit q6. |
274
+ | `elements/scroll-anchor.tsx` | `max-w-[85%]` applies to user bubbles only. | Assistant replies wrapped at about 60% of the card width, leaving a blank right column. Unit q6. |
275
+ | `elements/model-selector.tsx` | ModelSelectorItem always renders the fixed-width icon slot (empty spacer when the model has no icon). | Rows without an icon started their text further left, ragged list edge. Unit q6. |
276
+ | `elements/quote-reply.tsx` | The h-9 toolbar slot unmounts with the toolbar; the highlight span renders only for a non-empty selection. | The hidden toolbar reserved a 60px gap above the quote block. Unit q6. |
277
+ | `elements/settings-panel.tsx` | The read-only switch gets `opacity-50 cursor-not-allowed`; the unchecked thumb gains `dark:bg-foreground`. | Locked switches were pixel-identical to unlocked ones; the dark unchecked thumb was near-invisible. Unit q6. |
278
+ | `elements/schedule-card.tsx` | Unchecked switch thumb `dark:bg-foreground`; an empty history renders a muted "No runs yet" line. | The dark paused state hid the thumb; an empty "recent runs" heading read as a rendering failure. Unit q6. |
279
+ | `elements/model-picker.tsx` | Rows get `outline-none focus-visible:ring-1 focus-visible:ring-foreground/20`. | Keyboard focus drew the UA 2px ring over the selected fill, the heavy-ring pattern the owner dislikes. Unit q6. |
280
+ | `elements/prompt-library.tsx` | Variable count pluralises: `n === 1 ? "var" : "vars"`. | "1 vars". Unit q6. |
281
+ | `elements/permission-grant.tsx` | Settled and pending outcomes render as a coloured dot plus mono text instead of a grey pill. | Owner preference: dot plus text for status; denied and granted were indistinguishable greys. Unit q6. |
282
+ | `elements/read-aloud.tsx` | Progress fill `bg-foreground/80`, current-word highlight `bg-foreground/[0.08]`; the speed button gets `min-w-13` centered. | Off-token blue; the track width jumped between speed labels. Unit q6. |
283
+ | `elements/quota-banner.tsx` | `left === 0` switches the title and bar to the destructive token. | The exhausted state must read as more severe than near-limit. Unit q6. |
284
+
285
+ ## Visual QA round 2 (2026-10-04, unit r1, hub#62)
286
+
287
+ | File | Change | Why |
288
+ |---|---|---|
289
+ | `elements/confidence-marker.tsx` | Optional `labels` prop overrides the per-confidence label before the basis (defaults unchanged). | AttentionFeed reads "sourced", parallel to "inferred" and "unverified"; "from a source" read as placeholder copy on the admin cards. |
290
+ | `elements/thread.aui.tsx` | ThreadScrollToBottom also hides (`invisible`) while the last message's content ends above the viewport footer, measured on scroll and resize. | Under `turnAnchor="top"` the viewport can still scroll through the message group's `mb-14` margin and the top-anchor reserve, both blank, so the jump button showed with nothing below and crowded the action bar. |
291
+ | `elements/thread.aui.tsx` | The user message root gets `-mt-6 pt-6`; the content wrapper's top padding `pt-4` becomes `pt-6`. | The viewport's 1.5rem top fade (logged above) covered a turn pinned to the top and the first message at rest, so the user bubble read as sliced at the pane's edge. Layout is otherwise unchanged. |
292
+ ## Visual QA round 2, AI elements and primitives (2026-10-04, unit r3, hub#62)
293
+
294
+ Row focus follows the focus policy: keyboard focus on a list or menu row is the
295
+ row's hover fill plus a 1px inset ring (`ring-1 ring-inset ring-ring/40`), never
296
+ a 3px ring on a filled row. Story-only fixes (play waits, pointer-style clicks,
297
+ frame heights, demo data) are not vendored changes and are not listed.
298
+
299
+ | File | Change | Why |
300
+ |---|---|---|
301
+ | `elements/map-answer.tsx` | List rows: the 3px inset ring becomes the row focus treatment (hover fill `bg-foreground/[0.02]` plus `ring-1 ring-inset ring-ring/40`); the last row rounds its bottom corners to the card's inner radius. | A hard ring on the selected row, clipped by the card's rounded corners, clashed with the fill-only selection elsewhere. |
302
+ | `elements/reasoning-effort.tsx` | Segments: `focus-visible:ring-[3px] ring-ring/50` to `ring-1 ring-inset ring-ring/40`, and a focused segment takes the hover text color. | The thick ring filled the High segment out to the track edges. |
303
+ | `elements/document-reference.tsx` | Passage rows: the row focus treatment (hover fill plus 1px inset ring) instead of the 3px ring. | The thick ring over the grey fill outweighed the card's other states. |
304
+ | `elements/guardrail-notice.tsx` | "try instead" rows drop `-mx-1` (they sit inside the text column) and use the row focus treatment with `bg-accent`; read-only rows drop `-mx-1` too. | The 3px ring was heavy and overhung the column's left edge. |
305
+ | `elements/background-inbox.tsx` | Rows: the row focus treatment instead of the 3px inset ring. | A heavy ring next to subtle hover fills. |
306
+ | `elements/checkpoint-history.tsx` | The Restore button floats over the row's end (`absolute`, paper fill, `ring-1 ring-border/60`, 3px focus-visible ring) instead of holding an invisible flex column; the row is `relative`. | The hidden button reserved ~80px of every row, so a label wrapped mid-date with space to spare. |
307
+ | `elements/composer.tsx` | The context button shows its percentage (mono, tabular) before the ring, `h-8 px-2 gap-1.5`; the warning color `text-red-500` to `text-red-600` (dark unchanged). | A small arc on a faint track read as a loading spinner. red-600 keeps the new reading above 4.5:1. |
308
+ | `elements/cost-meter.tsx` | Share bar segments `bg-blue-500`/`bg-blue-500/55` (dark `blue-400`) to `bg-foreground/80` and `/45` (the third stays `/25`), the composer context bar's ramp. | Hard-coded saturated blue in the neutral theme. |
309
+ | `elements/memory-chips.tsx` | New and updated chips: `bg-foreground/[0.07]` (dark `/[0.1]`) with `text-foreground` and a leading `bg-foreground/70` dot, instead of the raw blue tint. | Off-token blue. |
310
+ | `elements/terminal-block.tsx` | The "output truncated" note reads "… output truncated", sits at the end of the output above the toggle, and shows only when every line is displayed (expanded, or not collapsible). | Under "Show less" it read as if lines were still hidden. |
311
+ | `elements/onboarding.tsx` | Step dots `h-1 w-1 bg-muted-foreground/40` to `h-1.5 w-1.5 bg-muted-foreground/60`; the active dash `h-1.5`. | The dots were still lost beside the dash. |
312
+ | `elements/launcher-bubble.tsx` | Unread badge: `bg-background text-foreground border border-border` to `bg-foreground text-background ring-2 ring-background`. | A canvas-colored disc half outside the bubble read as a bite; the ink disc cut out by a page-colored ring holds its shape on any background. |
313
+ | `elements/computer-use.tsx` | Trail rings center on the step's point (`-translate-x-1/2 -translate-y-1/2`); the cursor shifts `-mt-[3px] -ml-[3px]` so its tip lands on the point. | Rings and cursor were placed by their top-left corners, away from the click point. |
314
+ | `elements/code-diff.tsx` | Line text is tokenized with the synchronous `PrismLight` (yaml, tsx, json, python registered; language from the file extension; unknown extensions stay plain) with class output, colored from the coldark palette by Tailwind classes on the root; the add/remove row tint stays. | The diff had no syntax highlighting (owner: code must highlight on first load). |
315
+ | `elements/image.tsx` | The zoomed image gets `bg-background rounded-lg shadow-lg ring-1 ring-foreground/10`. | A transparent image (the chart) floated on the black overlay with no panel: dark text vanished, the dimmed page showed through it. |
316
+ | `elements/terminal-block.tsx` | The truncation note reads "… the rest of the output was not kept" instead of "… output truncated". | Under every shown line, "output truncated" read as a contradiction of the expanded output. Unit r4. |
317
+ | `elements/tool-group.tsx` | Row check and cross icons `strokeWidth={2.75}` (default 2). | At 12px the default stroke draws 1px lines whose antialiased tint read grey on some rows of a fully done group. Unit r4. |
@@ -0,0 +1,60 @@
1
+ # Vendored changes
2
+
3
+ ## Component source
4
+
5
+ `src/components/ui/` derives from shadcn/ui's Base UI `base-mira` registry, copied through Hub's `admin-ui` scaffold. The components remain local copies. This package has no runtime dependency on Hub's other kits or the upstream React components.
6
+
7
+ The shadcn MIT attribution remains in `licenses/shadcn-MIT.md`. Base UI stays an installed dependency at version `1.8.0`. Source and asset licenses are recorded separately in `THIRD-PARTY-NOTICES.md`.
8
+
9
+ ## Changes to the Mira components
10
+
11
+ - `Button` adds primary, secondary, tertiary, and critical variants; small, default, and large sizes; and loading behavior with `aria-busy` and disabled interaction. Copied compositions can still use the original variant and size aliases. Slot attributes select the soft theme control, font, radius, and shadow rules. Buttons are 30px rounded rectangles (8px corners) in 13px Inter at weight 540. Primary is a flat indigo fill with a hairline top highlight; critical is the same treatment in red; secondary is a white surface with a hairline ring; outline, tertiary and link stay transparent. Keyboard focus is a 2px indigo outline at 2px offset. Explicit size aliases and caller height utilities remain supported.
12
+ - `Badge` preserves the core `useRender`/`mergeProps` polymorphic contract, variants, and `badgeVariants` helper. Additive neutral, info, success, warning, caution, and critical tones use paired theme tokens. Explicit tone determines color; destructive defaults to critical and other variants to neutral. Outline and link retain their own treatments.
13
+ - `CardTitle` and `DialogTitle` use the shared Inter typography instead of a separate heading font.
14
+ - `Checkbox` uses the package's input border token for unchecked controls. Indeterminate selection receives a token-based fill.
15
+ - `Calendar` removes persistent rings based on DayPicker's focused-day modifier. Actual keyboard focus retains the shared `:focus-visible` treatment and DayPicker's focus behavior.
16
+ - `PopoverContent` forwards `collisionAvoidance` to the Base UI Positioner instead of the Popup, following the existing Hub fix.
17
+ - `Tooltip` marks its arrow with `data-slot="tooltip-arrow"`. Its popup remains Base UI's visual-only tooltip. The trigger provides its accessible name.
18
+ - The copied files retain some inherited client directives. The kit targets client-rendered React apps, with `rsc: false` in `components.json`.
19
+
20
+ The independent `src/styles/globals.css` overrides Mira utility styles through component slots. It supplies compact controls, flat primary buttons, hairline-ringed cards, field focus and invalid states, table spacing, and reduced-motion overrides. Each reduced-motion `!important` has a narrow lint suppression because it must override component utilities.
21
+
22
+ ## Local compositions and stories
23
+
24
+ The package adds `Page`, `Section`, `Stack`, `Grid`, and `Link`; standalone labelled field wrappers; `Banner` and `Modal`; and public `Menu` and `Divider` aliases.
25
+
26
+ Field wrappers link labels, hints, and errors to controls. Disabled labels carry their own disabled marker. `MoneyField` preserves decimal strings, and `DatePicker` formats calendar dates without UTC conversion. The canonical TanStack `DataTable` sorts numeric values, retains selection across pages, limits select-all to the visible page, and clamps the page after data changes. Its original state helpers, server mode, filters, search, virtualization, row actions, and loading/error behavior are copied in full. Invoice examples use this table; the earlier simple implementation and its private sorting helpers are removed. Labelled semantic sections keep horizontally scrollable tables keyboard accessible, with narrow `tabIndex` lint suppressions.
27
+
28
+ Stories cover component variants, theme tokens, density, and composed invoice list and detail interactions. Overlay interactions wait for visible content and settled dismissal before the accessibility scan. Toast interactions hover the toast before querying its accessible Close button, as Base UI hides Close from accessibility APIs while the viewport is collapsed. The tooltip story uses keyboard navigation, checks the rendered popup's exact text and visibility, and verifies Escape dismissal.
29
+
30
+ The isolated `.storybook-soft/` configuration imports soft globals and ai.css in one CSS entry. Both light and dark Vitest projects retain the accessibility error gate and shared cursor check.
31
+
32
+ ## Package delivery
33
+
34
+ The package is published to npm with public access through the Hub release workflow. `dist/index.js` and `dist/ai.js`, with their declarations, expose the full root and AI contracts. Both entries build together unbundled so shared contexts occur once. `dist/styles.css` is uncompiled Tailwind 4 source with explicit scanning directives for built JavaScript, alongside `tokens.css` and the Inter font.
35
+
36
+ Consumer setup and local Storybook commands are documented in [the package guide](GUIDE.md).
37
+
38
+ ## Full root and AI parity
39
+
40
+ The port copies all root UI, icon, composition, motion, hook, and helper modules and all assistant-ui and AI composition modules from Hub admin-ui at ac114fc. Stories, tests, clocks, local media, and synthetic fixtures accompany them. Existing soft theme controls remain local and provide the same imported modules to copied compositions. No runtime import points to another Hub UI kit.
41
+
42
+ Canonical form-kit names are context-bound. The original soft wrappers are now StandaloneTextField, StandaloneSelectField, StandaloneCheckboxField, and StandaloneSwitchField, with corresponding prop types. Canonical EmptyState uses description. The vertical Stack no-wrap phone fix remains in place.
43
+
44
+ Root CSS scans UI, icons, compositions, lib, and motion, excluding diff-viewer; ai.css scans assistant-ui, diff-viewer, hooks, and ai. CSS imports stay out of emitted JavaScript. The copied bundle tests verify context sharing and tree-shaking. Runtime dependencies, exact dev versions, and required/optional peer placement mirror core, excluding its Geist font dependency.
45
+
46
+ Soft theme aliases now cover font-heading, semantic info/success/warning, chart colors, sidebar, larger radii, and shadows. The sidebar uses the nav token in both themes. Status-tone helpers use semantic colors. Indeterminate progress, breadcrumb focus, shimmer, and open/closed data variants retain core behavior. Neutral Banner borders use the semantic border alias in dark mode.
47
+
48
+ Classic data-aui button, field, and card rules in ai.css consume the same tokens as the root components: 30px controls with 8px corners and 12px cards with a hairline ring. Shared element surfaces use card, popover, muted, border, and shadow aliases. Specialized syntax and data visualization palettes remain where they encode content.
49
+
50
+ The expanded story suite exposed additional compatibility fixes. Button forwards caller slot attributes and aria-busy, preserves render-target children, and allows composition sizing utilities to override its defaults. The canonical table clamps a client page when a local row update removes it; server mode retains query ownership. InputGroup textareas retain automatic height instead of inheriting the single-line input height. DecisionQueue draws its keyboard cursor without a color transition. Popup exits settle before focus restoration rather than hiding a still-modal tree. Swipe actions retain paired theme fill/text colors, and registry secondary text uses semantic aliases instead of low-opacity foreground tints.
51
+
52
+ Inherited upstream accessibility, network-default removals, and interaction fixes are recorded in UPSTREAM-VENDORED-CHANGES.md. That file is a provenance snapshot, not a description of the final soft theme.
53
+
54
+ ## Original token set
55
+
56
+ `src/styles/tokens.css` is written for this package: a cool slate neutral ramp, an indigo accent, status tones (neutral, info, success, warning, caution, critical) as fill, ink, tint and border, a 4px space scale, a 12/13/15/18/22px type scale, radii, slate-tinted shadows and two densities. `.dark` redefines the palette and shadows. `globals.css` maps shadcn's semantic variables (`--background`, `--primary` and the rest) onto these tokens and holds the component treatments.
57
+
58
+ `src/styles/fonts/` holds the unmodified `InterVariable.woff2` from the official Inter 4.1 release; `inter.css` records its source URL and checksums.
59
+
60
+ `src/package-content.test.ts` fails when the package source, styles or documentation name a certain third-party design system or its CDN, so material from it cannot return unnoticed.
@@ -0,0 +1,13 @@
1
+ //#region \0rolldown/runtime.js
2
+ var __defProp = Object.defineProperty;
3
+ var __exportAll = (all, no_symbols) => {
4
+ let target = {};
5
+ for (var name in all) __defProp(target, name, {
6
+ get: all[name],
7
+ enumerable: true
8
+ });
9
+ if (!no_symbols) __defProp(target, Symbol.toStringTag, { value: "Module" });
10
+ return target;
11
+ };
12
+ //#endregion
13
+ export { __exportAll };
@@ -0,0 +1,109 @@
1
+ import { DictationButtonProps } from "../../../motion/dictation-button/dictation-button.js";
2
+ import { PromptComposerCommand, PromptComposerOption, PromptComposerSendDetail, PromptComposerSource } from "../../../motion/prompt-composer/prompt-composer.js";
3
+ import { ScrubSelectOption } from "../../../motion/scrub-select/scrub-select.js";
4
+ import { JsonObject, Usage } from "../../types.js";
5
+ import * as React from "react";
6
+ //#region src/ai/compositions/agent-console/agent-console.d.ts
7
+ /** What the agent is doing: at rest, running, or waiting on the owner. */
8
+ export type AgentConsoleStatus = "idle" | "working" | "blocked";
9
+ /** One tool in the agent's scope, or a scope that nests more tools. */
10
+ export interface AgentConsoleTool {
11
+ /** The tool's name as the model calls it (`archive_message`), or the scope's id. */
12
+ id: string;
13
+ /** Display name. Defaults to `id`. */
14
+ label?: string;
15
+ /** Needs a press-and-hold to approve (ToolApproval's dangerous mode). */
16
+ dangerous?: boolean;
17
+ /** Nested tools make this a scope that expands and collapses. */
18
+ children?: readonly AgentConsoleTool[];
19
+ }
20
+ /** An owner decision on a gated tool call, reported to the app. */
21
+ export type AgentConsoleToolDecision = {
22
+ kind: "approve";
23
+ toolCallId: string;
24
+ toolName: string;
25
+ amendedArgs?: JsonObject;
26
+ } | {
27
+ kind: "deny";
28
+ toolCallId: string;
29
+ toolName: string;
30
+ reason?: string;
31
+ } | {
32
+ kind: "always-allow";
33
+ toolCallId: string;
34
+ toolName: string;
35
+ };
36
+ export interface AgentConsoleProps {
37
+ /** The agent's display name, such as "Email agent". */
38
+ name: string;
39
+ /**
40
+ * The agent's status. When omitted it follows the runtime: working while a
41
+ * run streams, blocked while a tool call waits for approval, else idle.
42
+ */
43
+ status?: AgentConsoleStatus;
44
+ /** A few words on the status, such as "Waiting for your approval". */
45
+ statusDetail?: string;
46
+ /** Usage for the thread, shown as a compact UsageMeter in the header. */
47
+ usage?: Usage;
48
+ /** The agent's scoped tools, nested by scope, listed from the header. */
49
+ tools?: readonly AgentConsoleTool[];
50
+ /** The owner chose a tool in the tool list. */
51
+ onToolSelect?: (toolId: string) => void;
52
+ /**
53
+ * Every decision on a gated tool call. The console also answers the
54
+ * runtime (approve or deny, with the reason); this reports what the
55
+ * runtime cannot carry: edited arguments and "always allow". With it, the
56
+ * approval card offers editing the arguments and Always allow.
57
+ */
58
+ onToolDecision?: (decision: AgentConsoleToolDecision) => void;
59
+ /** Model choices for the composer's model picker (a ScrubSelect). */
60
+ models?: readonly ScrubSelectOption[];
61
+ /** The selected model (controlled). */
62
+ model?: string;
63
+ /** The model selected at first (uncontrolled). Defaults to the first option. */
64
+ defaultModel?: string;
65
+ onModelChange?: (model: string) => void;
66
+ /** Reasoning-effort choices for the composer. */
67
+ efforts?: readonly PromptComposerOption[];
68
+ effort?: string;
69
+ defaultEffort?: string;
70
+ onEffortChange?: (effort: string) => void;
71
+ /** What `@` offers in the composer. */
72
+ sources?: readonly PromptComposerSource[];
73
+ /** What `/` offers in the composer. */
74
+ commands?: readonly PromptComposerCommand[];
75
+ /** Shows the composer's attach button; the app opens its own picker. */
76
+ onAttach?: () => void;
77
+ /**
78
+ * Shows a DictationButton in the composer. The app owns the speech
79
+ * handling: it passes the level and acts on start, stop and cancel.
80
+ */
81
+ dictation?: Omit<DictationButtonProps, "disabled" | "className">;
82
+ /** Called after each message the owner sends, with the composer's details. */
83
+ onSend?: (text: string, detail: PromptComposerSendDetail) => void;
84
+ /** Shows a star rating under each finished assistant message. */
85
+ onRate?: (messageId: string, rating: number | null) => void;
86
+ /** The ratings the app recorded, by message id. */
87
+ ratings?: Readonly<Record<string, number | null>>;
88
+ /** The composer's placeholder. Defaults to "Message <name>". */
89
+ placeholder?: string;
90
+ className?: string;
91
+ }
92
+ /**
93
+ * A chat with one agent, on the app's assistant-ui runtime. The header shows
94
+ * the agent's name, model and status, a compact UsageMeter and its scoped
95
+ * tool list (a BranchMenu in a popover). The thread streams the agent's
96
+ * reasoning as a ThinkingTrace, each tool call as a ToolCallChip that
97
+ * expands to its arguments and result (tool-fallback), and a gated call as a
98
+ * ToolApproval card. A WorkingIndicator runs while the agent works, and with
99
+ * `onRate` each finished answer gets a StarRating. The composer is a
100
+ * PromptComposer with a ScrubSelect model picker and a DictationButton.
101
+ *
102
+ * AgentConsole renders inside the app's `AssistantRuntimeProvider` and never
103
+ * creates a runtime: messages, streaming, approvals and cancelling all go
104
+ * through it. A run error shows in place, under its message, and the
105
+ * conversation stays on screen. Below 35rem the header collapses into a
106
+ * details popover, and the composer stays pinned to the bottom.
107
+ */
108
+ export declare function AgentConsole(props: AgentConsoleProps): React.JSX.Element;
109
+ //#endregion