@copilotkit/vue 2.0.0-rc.1 → 2.0.0-rc.10

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 (317) hide show
  1. package/PARITY.md +13 -12
  2. package/README.md +1 -2
  3. package/dist/components/copilot-provider/CopilotKit.vue.d.ts +3 -1
  4. package/dist/components/copilot-provider/CopilotKit.vue.d.ts.map +1 -1
  5. package/dist/hooks/use-copilot-action.d.ts.map +1 -1
  6. package/dist/hooks/use-frontend-tool.d.ts +1 -1
  7. package/dist/hooks/use-frontend-tool.d.ts.map +1 -1
  8. package/dist/hooks/zod-parameters.d.ts +14 -0
  9. package/dist/hooks/zod-parameters.d.ts.map +1 -0
  10. package/dist/index.cjs +1 -76
  11. package/dist/index.cjs.map +1 -1
  12. package/dist/index.mjs +384 -14275
  13. package/dist/index.mjs.map +1 -1
  14. package/dist/use-render-activity-message-CTR_ziWV.js +18097 -0
  15. package/dist/use-render-activity-message-CTR_ziWV.js.map +1 -0
  16. package/dist/use-render-activity-message-Dky9_GRG.cjs +92 -0
  17. package/dist/use-render-activity-message-Dky9_GRG.cjs.map +1 -0
  18. package/dist/v2/components/A2UIMessageRenderer.d.ts +7 -0
  19. package/dist/v2/components/A2UIMessageRenderer.d.ts.map +1 -1
  20. package/dist/v2/components/A2UISurfaceActivityRenderer.vue.d.ts.map +1 -1
  21. package/dist/v2/components/LicenseWarningBanner.vue.d.ts.map +1 -1
  22. package/dist/v2/components/OpenGenerativeUIRenderer.d.ts +13 -45
  23. package/dist/v2/components/OpenGenerativeUIRenderer.d.ts.map +1 -1
  24. package/dist/v2/components/a2ui/A2UIBuiltInToolCallRenderer.d.ts +11 -2
  25. package/dist/v2/components/a2ui/A2UIBuiltInToolCallRenderer.d.ts.map +1 -1
  26. package/dist/v2/components/a2ui/A2UICatalogContext.d.ts +1 -1
  27. package/dist/v2/components/a2ui/A2UICatalogContext.d.ts.map +1 -1
  28. package/dist/v2/components/a2ui/A2UIRecoveryStates.d.ts +144 -0
  29. package/dist/v2/components/a2ui/A2UIRecoveryStates.d.ts.map +1 -0
  30. package/dist/v2/components/a2ui.d.ts +3 -7
  31. package/dist/v2/components/a2ui.d.ts.map +1 -1
  32. package/dist/v2/components/chat/CopilotChat.vue.d.ts +1 -0
  33. package/dist/v2/components/chat/CopilotChat.vue.d.ts.map +1 -1
  34. package/dist/v2/components/chat/CopilotChatAssistantMessage.vue.d.ts +3 -1
  35. package/dist/v2/components/chat/CopilotChatAssistantMessage.vue.d.ts.map +1 -1
  36. package/dist/v2/components/chat/CopilotChatAssistantToolbarButton.vue.d.ts +16 -0
  37. package/dist/v2/components/chat/CopilotChatAssistantToolbarButton.vue.d.ts.map +1 -0
  38. package/dist/v2/components/chat/CopilotChatAttachmentQueue.vue.d.ts.map +1 -1
  39. package/dist/v2/components/chat/CopilotChatAttachmentRenderer.vue.d.ts.map +1 -1
  40. package/dist/v2/components/chat/CopilotChatAudioRecorder.vue.d.ts.map +1 -1
  41. package/dist/v2/components/chat/CopilotChatFeedbackCommentPopover.vue.d.ts +22 -0
  42. package/dist/v2/components/chat/CopilotChatFeedbackCommentPopover.vue.d.ts.map +1 -0
  43. package/dist/v2/components/chat/CopilotChatInput.vue.d.ts +21 -232
  44. package/dist/v2/components/chat/CopilotChatInput.vue.d.ts.map +1 -1
  45. package/dist/v2/components/chat/CopilotChatInspectorButton.vue.d.ts +12 -0
  46. package/dist/v2/components/chat/CopilotChatInspectorButton.vue.d.ts.map +1 -0
  47. package/dist/v2/components/chat/CopilotChatLightbox.vue.d.ts +22 -0
  48. package/dist/v2/components/chat/CopilotChatLightbox.vue.d.ts.map +1 -0
  49. package/dist/v2/components/chat/CopilotChatMessageView.vue.d.ts +20 -0
  50. package/dist/v2/components/chat/CopilotChatMessageView.vue.d.ts.map +1 -1
  51. package/dist/v2/components/chat/CopilotChatReasoningMessage.vue.d.ts.map +1 -1
  52. package/dist/v2/components/chat/CopilotChatSuggestionPill.vue.d.ts.map +1 -1
  53. package/dist/v2/components/chat/CopilotChatSuggestionView.vue.d.ts.map +1 -1
  54. package/dist/v2/components/chat/CopilotChatToggleButton.vue.d.ts.map +1 -1
  55. package/dist/v2/components/chat/CopilotChatToolCallGroup.vue.d.ts +32 -0
  56. package/dist/v2/components/chat/CopilotChatToolCallGroup.vue.d.ts.map +1 -0
  57. package/dist/v2/components/chat/CopilotChatToolCallItem.vue.d.ts.map +1 -1
  58. package/dist/v2/components/chat/CopilotChatToolCallsView.vue.d.ts +11 -1
  59. package/dist/v2/components/chat/CopilotChatToolCallsView.vue.d.ts.map +1 -1
  60. package/dist/v2/components/chat/CopilotChatUserMessage.vue.d.ts.map +1 -1
  61. package/dist/v2/components/chat/CopilotChatView.vue.d.ts +1 -0
  62. package/dist/v2/components/chat/CopilotChatView.vue.d.ts.map +1 -1
  63. package/dist/v2/components/chat/CopilotChatWorkSummary.vue.d.ts +5 -0
  64. package/dist/v2/components/chat/CopilotChatWorkSummary.vue.d.ts.map +1 -0
  65. package/dist/v2/components/chat/CopilotModalHeader.vue.d.ts.map +1 -1
  66. package/dist/v2/components/chat/CopilotModalHeaderCloseButton.d.ts.map +1 -1
  67. package/dist/v2/components/chat/CopilotModalHeaderTitle.d.ts.map +1 -1
  68. package/dist/v2/components/chat/CopilotPopup.vue.d.ts +1 -0
  69. package/dist/v2/components/chat/CopilotPopup.vue.d.ts.map +1 -1
  70. package/dist/v2/components/chat/CopilotPopupView.vue.d.ts +1 -0
  71. package/dist/v2/components/chat/CopilotPopupView.vue.d.ts.map +1 -1
  72. package/dist/v2/components/chat/CopilotPopupViewInternal.vue.d.ts +1 -0
  73. package/dist/v2/components/chat/CopilotPopupViewInternal.vue.d.ts.map +1 -1
  74. package/dist/v2/components/chat/CopilotPopupWelcomeScreen.vue.d.ts.map +1 -1
  75. package/dist/v2/components/chat/CopilotSidebar.vue.d.ts +2 -0
  76. package/dist/v2/components/chat/CopilotSidebar.vue.d.ts.map +1 -1
  77. package/dist/v2/components/chat/CopilotSidebarView.vue.d.ts +2 -0
  78. package/dist/v2/components/chat/CopilotSidebarView.vue.d.ts.map +1 -1
  79. package/dist/v2/components/chat/CopilotSidebarViewInternal.vue.d.ts +2 -0
  80. package/dist/v2/components/chat/CopilotSidebarViewInternal.vue.d.ts.map +1 -1
  81. package/dist/v2/components/chat/CopilotSidebarWelcomeScreen.vue.d.ts.map +1 -1
  82. package/dist/v2/components/chat/StreamingMarkdownDefault.vue.d.ts.map +1 -1
  83. package/dist/v2/components/chat/copilotChatToolCallItemRender.d.ts +0 -1
  84. package/dist/v2/components/chat/copilotChatToolCallItemRender.d.ts.map +1 -1
  85. package/dist/v2/components/chat/index.d.ts +17 -1
  86. package/dist/v2/components/chat/index.d.ts.map +1 -1
  87. package/dist/v2/components/chat/inspector-shortcuts.d.ts +12 -0
  88. package/dist/v2/components/chat/inspector-shortcuts.d.ts.map +1 -0
  89. package/dist/v2/components/chat/message-feedback.d.ts +89 -0
  90. package/dist/v2/components/chat/message-feedback.d.ts.map +1 -0
  91. package/dist/v2/components/chat/tool-call-capture.d.ts +39 -0
  92. package/dist/v2/components/chat/tool-call-capture.d.ts.map +1 -0
  93. package/dist/v2/components/chat/tool-call-display-context.d.ts +22 -0
  94. package/dist/v2/components/chat/tool-call-display-context.d.ts.map +1 -0
  95. package/dist/v2/components/chat/tool-call-group-parts.d.ts +131 -0
  96. package/dist/v2/components/chat/tool-call-group-parts.d.ts.map +1 -0
  97. package/dist/v2/components/chat/turn-work.d.ts +33 -0
  98. package/dist/v2/components/chat/turn-work.d.ts.map +1 -0
  99. package/dist/v2/components/chat/types.d.ts +104 -5
  100. package/dist/v2/components/chat/types.d.ts.map +1 -1
  101. package/dist/v2/components/chat/use-chat-labels.d.ts +8 -0
  102. package/dist/v2/components/chat/use-chat-labels.d.ts.map +1 -0
  103. package/dist/v2/components/chat/use-lightbox.d.ts +18 -0
  104. package/dist/v2/components/chat/use-lightbox.d.ts.map +1 -0
  105. package/dist/v2/components/icons/index.d.ts +968 -1
  106. package/dist/v2/components/icons/index.d.ts.map +1 -1
  107. package/dist/v2/components/ui/CopilotDropdownMenuContent.vue.d.ts +55 -0
  108. package/dist/v2/components/ui/CopilotDropdownMenuContent.vue.d.ts.map +1 -0
  109. package/dist/v2/components/ui/CopilotPopover.vue.d.ts +40 -0
  110. package/dist/v2/components/ui/CopilotPopover.vue.d.ts.map +1 -0
  111. package/dist/v2/components/ui/CopilotTooltip.vue.d.ts +37 -0
  112. package/dist/v2/components/ui/CopilotTooltip.vue.d.ts.map +1 -0
  113. package/dist/v2/components/ui/dropdown-menu.d.ts +14 -0
  114. package/dist/v2/components/ui/dropdown-menu.d.ts.map +1 -0
  115. package/dist/v2/components/ui/floating.d.ts +84 -0
  116. package/dist/v2/components/ui/floating.d.ts.map +1 -0
  117. package/dist/v2/components/ui/presence.d.ts +9 -0
  118. package/dist/v2/components/ui/presence.d.ts.map +1 -0
  119. package/dist/v2/components/ui/use-id.d.ts +9 -0
  120. package/dist/v2/components/ui/use-id.d.ts.map +1 -0
  121. package/dist/v2/hooks/use-default-render-tool.d.ts +6 -0
  122. package/dist/v2/hooks/use-default-render-tool.d.ts.map +1 -1
  123. package/dist/v2/hooks/use-frontend-tool.d.ts +5 -0
  124. package/dist/v2/hooks/use-frontend-tool.d.ts.map +1 -1
  125. package/dist/v2/hooks/use-render-activity-message.d.ts +13 -9
  126. package/dist/v2/hooks/use-render-activity-message.d.ts.map +1 -1
  127. package/dist/v2/hooks/use-render-custom-messages.d.ts +5 -7
  128. package/dist/v2/hooks/use-render-custom-messages.d.ts.map +1 -1
  129. package/dist/v2/hooks/use-render-tool.d.ts +4 -0
  130. package/dist/v2/hooks/use-render-tool.d.ts.map +1 -1
  131. package/dist/v2/index.cjs +1 -1
  132. package/dist/v2/index.d.cts +3 -0
  133. package/dist/v2/index.d.mts +3 -0
  134. package/dist/v2/index.d.ts +3 -0
  135. package/dist/v2/index.d.ts.map +1 -1
  136. package/dist/v2/index.mjs +197 -197
  137. package/dist/v2/index.mjs.map +1 -1
  138. package/dist/v2/lib/message-feedback.d.ts +33 -0
  139. package/dist/v2/lib/message-feedback.d.ts.map +1 -0
  140. package/dist/v2/lib/processPartialHtml.d.ts +1 -2
  141. package/dist/v2/lib/processPartialHtml.d.ts.map +1 -1
  142. package/dist/v2/lib/vue-core.d.ts +0 -1
  143. package/dist/v2/lib/vue-core.d.ts.map +1 -1
  144. package/dist/v2/providers/CopilotChatConfigurationProvider.vue.d.ts.map +1 -1
  145. package/dist/v2/providers/CopilotKitProvider.types.d.ts +56 -6
  146. package/dist/v2/providers/CopilotKitProvider.types.d.ts.map +1 -1
  147. package/dist/v2/providers/CopilotKitProvider.vue.d.ts +6 -2
  148. package/dist/v2/providers/CopilotKitProvider.vue.d.ts.map +1 -1
  149. package/dist/v2/providers/index.d.ts +1 -1
  150. package/dist/v2/providers/index.d.ts.map +1 -1
  151. package/dist/v2/providers/keys.d.ts +8 -0
  152. package/dist/v2/providers/keys.d.ts.map +1 -1
  153. package/dist/v2/providers/types.d.ts +3 -37
  154. package/dist/v2/providers/types.d.ts.map +1 -1
  155. package/dist/v2/styles/CopilotKitStyles.d.ts +18 -0
  156. package/dist/v2/styles/CopilotKitStyles.d.ts.map +1 -0
  157. package/dist/v2/types/defineToolCallRenderer.d.ts +2 -0
  158. package/dist/v2/types/defineToolCallRenderer.d.ts.map +1 -1
  159. package/dist/v2/types/human-in-the-loop.d.ts +8 -29
  160. package/dist/v2/types/human-in-the-loop.d.ts.map +1 -1
  161. package/dist/v2/types/interrupt.d.ts +1 -22
  162. package/dist/v2/types/interrupt.d.ts.map +1 -1
  163. package/dist/v2/types/vue-activity-message-renderer.d.ts +16 -15
  164. package/dist/v2/types/vue-activity-message-renderer.d.ts.map +1 -1
  165. package/dist/v2/types/vue-custom-message-renderer.d.ts +7 -16
  166. package/dist/v2/types/vue-custom-message-renderer.d.ts.map +1 -1
  167. package/dist/v2/types/vue-tool-call-renderer.d.ts +16 -28
  168. package/dist/v2/types/vue-tool-call-renderer.d.ts.map +1 -1
  169. package/package.json +14 -27
  170. package/src/__tests__/build-entries.test.ts +27 -0
  171. package/src/components/copilot-provider/CopilotKit.vue +4 -1
  172. package/src/hooks/__tests__/zod-parameters.test.ts +520 -0
  173. package/src/hooks/use-copilot-action.ts +2 -1
  174. package/src/hooks/use-frontend-tool.ts +3 -6
  175. package/src/hooks/zod-parameters.ts +162 -0
  176. package/src/v2/__tests__/exports.test.ts +4 -2
  177. package/src/v2/components/A2UIMessageRenderer.ts +56 -68
  178. package/src/v2/components/A2UISurfaceActivityRenderer.vue +11 -23
  179. package/src/v2/components/LicenseWarningBanner.vue +31 -15
  180. package/src/v2/components/OpenGenerativeUIRenderer.ts +51 -373
  181. package/src/v2/components/__tests__/A2UIBasicCatalogColors.test.ts +8 -9
  182. package/src/v2/components/__tests__/A2UICatalogContext.test.ts +1 -1
  183. package/src/v2/components/__tests__/A2UIMessageRenderer.test.ts +63 -36
  184. package/src/v2/components/__tests__/LicenseWarningBanner.test.ts +20 -0
  185. package/src/v2/components/__tests__/OpenGenerativeUIRenderer.test.ts +55 -6
  186. package/src/v2/components/a2ui/A2UIBuiltInToolCallRenderer.ts +15 -258
  187. package/src/v2/components/a2ui/A2UICatalogContext.ts +10 -102
  188. package/src/v2/components/a2ui/A2UIRecoveryStates.ts +444 -0
  189. package/src/v2/components/a2ui/__tests__/A2UIRecoveryStates.test.ts +175 -0
  190. package/src/v2/components/a2ui.ts +1 -1
  191. package/src/v2/components/chat/CopilotChat.vue +26 -40
  192. package/src/v2/components/chat/CopilotChatAssistantMessage.vue +267 -67
  193. package/src/v2/components/chat/CopilotChatAssistantToolbarButton.vue +46 -0
  194. package/src/v2/components/chat/CopilotChatAttachmentQueue.vue +150 -173
  195. package/src/v2/components/chat/CopilotChatAttachmentRenderer.vue +77 -20
  196. package/src/v2/components/chat/CopilotChatAudioRecorder.vue +2 -2
  197. package/src/v2/components/chat/CopilotChatFeedbackCommentPopover.vue +240 -0
  198. package/src/v2/components/chat/CopilotChatInput.vue +250 -191
  199. package/src/v2/components/chat/CopilotChatInspectorButton.vue +331 -0
  200. package/src/v2/components/chat/CopilotChatLightbox.vue +105 -0
  201. package/src/v2/components/chat/CopilotChatMessageView.vue +262 -87
  202. package/src/v2/components/chat/CopilotChatReasoningMessage.vue +52 -35
  203. package/src/v2/components/chat/CopilotChatSuggestionPill.vue +5 -14
  204. package/src/v2/components/chat/CopilotChatSuggestionView.vue +1 -4
  205. package/src/v2/components/chat/CopilotChatToggleButton.vue +3 -9
  206. package/src/v2/components/chat/CopilotChatToggleButtonCloseIcon.ts +1 -1
  207. package/src/v2/components/chat/CopilotChatToggleButtonOpenIcon.ts +1 -1
  208. package/src/v2/components/chat/CopilotChatToolCallGroup.vue +353 -0
  209. package/src/v2/components/chat/CopilotChatToolCallItem.vue +24 -14
  210. package/src/v2/components/chat/CopilotChatToolCallsView.vue +194 -21
  211. package/src/v2/components/chat/CopilotChatUserMessage.vue +105 -42
  212. package/src/v2/components/chat/CopilotChatView.vue +37 -42
  213. package/src/v2/components/chat/CopilotChatWorkSummary.vue +111 -0
  214. package/src/v2/components/chat/CopilotModalHeader.vue +10 -8
  215. package/src/v2/components/chat/CopilotModalHeaderCloseButton.ts +7 -6
  216. package/src/v2/components/chat/CopilotModalHeaderTitle.ts +1 -4
  217. package/src/v2/components/chat/CopilotPopup.vue +3 -0
  218. package/src/v2/components/chat/CopilotPopupView.vue +1 -0
  219. package/src/v2/components/chat/CopilotPopupViewInternal.vue +9 -19
  220. package/src/v2/components/chat/CopilotPopupWelcomeScreen.vue +5 -8
  221. package/src/v2/components/chat/CopilotSidebar.vue +5 -0
  222. package/src/v2/components/chat/CopilotSidebarView.vue +2 -0
  223. package/src/v2/components/chat/CopilotSidebarViewInternal.vue +24 -17
  224. package/src/v2/components/chat/CopilotSidebarWelcomeScreen.vue +7 -10
  225. package/src/v2/components/chat/StreamingMarkdownDefault.vue +3 -5
  226. package/src/v2/components/chat/__tests__/CopilotChat.labels.test.ts +19 -4
  227. package/src/v2/components/chat/__tests__/CopilotChatActivityRendering.e2e.test.ts +26 -9
  228. package/src/v2/components/chat/__tests__/CopilotChatAssistantMessage.inspector.test.ts +269 -0
  229. package/src/v2/components/chat/__tests__/CopilotChatAssistantMessage.learningFeedback.test.ts +760 -0
  230. package/src/v2/components/chat/__tests__/CopilotChatAssistantMessage.slots.e2e.test.ts +3 -5
  231. package/src/v2/components/chat/__tests__/CopilotChatAssistantMessage.test.ts +2 -2
  232. package/src/v2/components/chat/__tests__/CopilotChatInput.addMenu.test.ts +328 -0
  233. package/src/v2/components/chat/__tests__/CopilotChatInput.slots.e2e.test.ts +6 -3
  234. package/src/v2/components/chat/__tests__/CopilotChatInput.test.ts +55 -14
  235. package/src/v2/components/chat/__tests__/CopilotChatLightbox.test.ts +160 -0
  236. package/src/v2/components/chat/__tests__/CopilotChatMessageView.test.ts +247 -403
  237. package/src/v2/components/chat/__tests__/CopilotChatMessageView.toolCallDisplay.test.ts +637 -0
  238. package/src/v2/components/chat/__tests__/CopilotChatSuggestionPill.test.ts +1 -1
  239. package/src/v2/components/chat/__tests__/CopilotChatSuggestionView.slots.e2e.test.ts +3 -1
  240. package/src/v2/components/chat/__tests__/CopilotChatToolCallsView.learning.test.ts +75 -0
  241. package/src/v2/components/chat/__tests__/CopilotChatUserMessage.attachments.test.ts +143 -0
  242. package/src/v2/components/chat/__tests__/CopilotChatView.inputOverlay.test.ts +5 -4
  243. package/src/v2/components/chat/__tests__/CopilotChatView.rootWidth.test.ts +7 -33
  244. package/src/v2/components/chat/__tests__/CopilotModalHeader.slots.e2e.test.ts +1 -1
  245. package/src/v2/components/chat/__tests__/CopilotPopupView.slots.e2e.test.ts +3 -3
  246. package/src/v2/components/chat/__tests__/CopilotSidebarView.position.test.ts +126 -0
  247. package/src/v2/components/chat/__tests__/messageFeedbackDefaults.test.ts +33 -0
  248. package/src/v2/components/chat/__tests__/modalChatDisplayProps.test.ts +44 -0
  249. package/src/v2/components/chat/copilotChatToolCallItemRender.ts +3 -19
  250. package/src/v2/components/chat/index.ts +2 -1
  251. package/src/v2/components/chat/inspector-shortcuts.ts +34 -0
  252. package/src/v2/components/chat/message-feedback.ts +291 -0
  253. package/src/v2/components/chat/tool-call-capture.ts +55 -0
  254. package/src/v2/components/chat/tool-call-display-context.ts +28 -0
  255. package/src/v2/components/chat/tool-call-group-parts.ts +251 -0
  256. package/src/v2/components/chat/turn-work.ts +52 -0
  257. package/src/v2/components/chat/types.ts +114 -4
  258. package/src/v2/components/chat/use-chat-labels.ts +16 -0
  259. package/src/v2/components/chat/use-lightbox.ts +64 -0
  260. package/src/v2/components/icons/__tests__/icons.test.ts +72 -68
  261. package/src/v2/components/icons/index.ts +109 -23
  262. package/src/v2/components/ui/CopilotDropdownMenuContent.vue +465 -0
  263. package/src/v2/components/ui/CopilotPopover.vue +138 -0
  264. package/src/v2/components/ui/CopilotTooltip.vue +237 -0
  265. package/src/v2/components/ui/__tests__/CopilotTooltip.test.ts +168 -0
  266. package/src/v2/components/ui/dropdown-menu.ts +15 -0
  267. package/src/v2/components/ui/floating.ts +321 -0
  268. package/src/v2/components/ui/presence.ts +54 -0
  269. package/src/v2/components/ui/use-id.ts +16 -0
  270. package/src/v2/hooks/__tests__/use-frontend-tool.e2e.test.ts +62 -1
  271. package/src/v2/hooks/__tests__/use-render-activity-message.test.ts +105 -0
  272. package/src/v2/hooks/__tests__/use-render-tool.test.ts +3 -6
  273. package/src/v2/hooks/__tests__/zod-regression.test.ts +5 -4
  274. package/src/v2/hooks/use-default-render-tool.ts +123 -62
  275. package/src/v2/hooks/use-frontend-tool.ts +10 -10
  276. package/src/v2/hooks/use-render-activity-message.ts +27 -48
  277. package/src/v2/hooks/use-render-custom-messages.ts +14 -35
  278. package/src/v2/hooks/use-render-tool.ts +8 -0
  279. package/src/v2/index.ts +3 -0
  280. package/src/v2/lib/__tests__/message-feedback.test.ts +152 -0
  281. package/src/v2/lib/message-feedback.ts +120 -0
  282. package/src/v2/lib/processPartialHtml.ts +6 -21
  283. package/src/v2/lib/vue-core.ts +3 -5
  284. package/src/v2/providers/CopilotChatConfigurationProvider.vue +29 -2
  285. package/src/v2/providers/CopilotKitProvider.types.ts +57 -5
  286. package/src/v2/providers/CopilotKitProvider.vue +177 -114
  287. package/src/v2/providers/__tests__/CopilotChatConfigurationProvider.openThread.test.ts +69 -0
  288. package/src/v2/providers/__tests__/CopilotKitProvider.a2ui.test.ts +1 -1
  289. package/src/v2/providers/__tests__/CopilotKitProvider.headersAtSendTime.test.ts +3 -3
  290. package/src/v2/providers/__tests__/CopilotKitProvider.learning.test.ts +536 -0
  291. package/src/v2/providers/__tests__/CopilotKitProvider.test.ts +17 -33
  292. package/src/v2/providers/index.ts +4 -1
  293. package/src/v2/providers/keys.ts +12 -0
  294. package/src/v2/providers/types.ts +3 -38
  295. package/src/v2/styles/CopilotKitStyles.ts +95 -0
  296. package/src/v2/styles/__tests__/CopilotKitStyles.client.test.ts +149 -0
  297. package/src/v2/styles/__tests__/CopilotKitStyles.ssr.test.ts +71 -0
  298. package/src/v2/types/__tests__/defineToolCallRenderer.test.ts +28 -33
  299. package/src/v2/types/defineToolCallRenderer.ts +9 -4
  300. package/src/v2/types/human-in-the-loop.ts +8 -32
  301. package/src/v2/types/interrupt.ts +7 -31
  302. package/src/v2/types/vue-activity-message-renderer.ts +24 -15
  303. package/src/v2/types/vue-custom-message-renderer.ts +12 -16
  304. package/src/v2/types/vue-tool-call-renderer.ts +23 -31
  305. package/vite.config.ts +5 -5
  306. package/dist/styles.css +0 -2
  307. package/dist/v2/components/chat/BasicMarkdown.vue.d.ts +0 -9
  308. package/dist/v2/components/chat/BasicMarkdown.vue.d.ts.map +0 -1
  309. package/dist/v2/lib/transcription-client.d.ts +0 -19
  310. package/dist/v2/lib/transcription-client.d.ts.map +0 -1
  311. package/scripts/scope-preflight.mjs +0 -100
  312. package/src/styles/globals.css +0 -233
  313. package/src/v2/components/chat/BasicMarkdown.vue +0 -158
  314. package/src/v2/components/chat/__tests__/BasicMarkdown.test.ts +0 -69
  315. package/src/v2/lib/__tests__/processPartialHtml.test.ts +0 -84
  316. package/src/v2/lib/__tests__/transcription-client.test.ts +0 -67
  317. package/src/v2/lib/transcription-client.ts +0 -151
@@ -4,7 +4,6 @@ import {
4
4
  createAttachmentContent,
5
5
  DEFAULT_AGENT_ID,
6
6
  randomUUID,
7
- TranscriptionErrorCode,
8
7
  } from "@copilotkit/shared";
9
8
  import {
10
9
  computed,
@@ -17,7 +16,14 @@ import {
17
16
  useSlots,
18
17
  watch,
19
18
  } from "vue";
20
- import { CopilotKitCoreErrorCode, ɵisHttpAgent } from "@copilotkit/core";
19
+ import {
20
+ CopilotChatDefaultLabels,
21
+ CopilotKitCoreErrorCode,
22
+ TranscriptionError,
23
+ ɵisHttpAgent,
24
+ ɵtranscribeAudio,
25
+ ɵtranscriptionErrorMessageKey,
26
+ } from "@copilotkit/core";
21
27
  import type { Suggestion } from "@copilotkit/core";
22
28
  import CopilotChatConfigurationProvider from "../../providers/CopilotChatConfigurationProvider.vue";
23
29
  import { useCopilotChatConfiguration } from "../../providers/useCopilotChatConfiguration";
@@ -28,16 +34,13 @@ import { useAgent } from "../../hooks/use-agent";
28
34
  import { useSuggestions } from "../../hooks/use-suggestions";
29
35
  import { useAttachments } from "../../hooks/use-attachments";
30
36
  import { useShallowStableRef } from "../../lib/shallow-stable";
31
- import {
32
- transcribeAudio,
33
- TranscriptionError,
34
- } from "../../lib/transcription-client";
35
37
  import CopilotChatView from "./CopilotChatView.vue";
36
38
  import { LastUserMessageKey } from "./last-user-message-context";
37
39
  import type { LastUserMessageState } from "./last-user-message-context";
38
40
  import type { Message } from "@ag-ui/core";
39
41
  import type { InputContent } from "@copilotkit/shared";
40
42
  import { useInspectorThreadOverride } from "../../providers/use-inspector-thread-override";
43
+ import { CopilotKitStyles } from "../../styles/CopilotKitStyles";
41
44
  import type {
42
45
  CopilotChatInputSlotProps,
43
46
  CopilotChatProps,
@@ -51,6 +54,7 @@ defineOptions({ inheritAttrs: false });
51
54
 
52
55
  const props = withDefaults(defineProps<CopilotChatProps>(), {
53
56
  autoScroll: true,
57
+ messageFeedback: true,
54
58
  welcomeScreen: true,
55
59
  inputValue: undefined,
56
60
  inputMode: "input",
@@ -157,6 +161,12 @@ const isConnecting = computed(
157
161
  );
158
162
  const stableLabels = useShallowStableRef(computed(() => props.labels));
159
163
  const resolvedLabels = computed(() => stableLabels.value);
164
+ // The labels this chat shows, the same merge its configuration provider makes.
165
+ const chatLabels = computed(() => ({
166
+ ...CopilotChatDefaultLabels,
167
+ ...existingConfig.value?.labels,
168
+ ...resolvedLabels.value,
169
+ }));
160
170
 
161
171
  // `useAgent` takes no threadId: it pins one only from a surrounding chat
162
172
  // configuration, and this call sits outside the provider rendered in this
@@ -769,48 +779,19 @@ async function handleFinishTranscribeWithAudio(audioBlob: Blob) {
769
779
  isTranscribing.value = true;
770
780
  try {
771
781
  transcriptionError.value = null;
772
- const result = await transcribeAudio(copilotkit.value, audioBlob);
782
+ const result = await ɵtranscribeAudio(copilotkit.value, audioBlob);
773
783
  const trimmedPrevious = inputValue.value.trim();
774
784
  inputValue.value = trimmedPrevious
775
785
  ? `${trimmedPrevious} ${result.text}`
776
786
  : result.text;
777
787
  } catch (error) {
778
788
  console.error("CopilotChat: Transcription failed", error);
789
+ const labels = chatLabels.value;
779
790
  if (error instanceof TranscriptionError) {
780
- const { code, retryable, message } = error.info;
781
- switch (code) {
782
- case TranscriptionErrorCode.RATE_LIMITED:
783
- transcriptionError.value = "Too many requests. Please wait a moment.";
784
- break;
785
- case TranscriptionErrorCode.AUTH_FAILED:
786
- transcriptionError.value =
787
- "Authentication error. Please check your configuration.";
788
- break;
789
- case TranscriptionErrorCode.AUDIO_TOO_LONG:
790
- transcriptionError.value =
791
- "Recording is too long. Please try a shorter recording.";
792
- break;
793
- case TranscriptionErrorCode.AUDIO_TOO_SHORT:
794
- transcriptionError.value =
795
- "Recording is too short. Please try again.";
796
- break;
797
- case TranscriptionErrorCode.INVALID_AUDIO_FORMAT:
798
- transcriptionError.value = "Audio format not supported.";
799
- break;
800
- case TranscriptionErrorCode.SERVICE_NOT_CONFIGURED:
801
- transcriptionError.value = "Transcription service is not available.";
802
- break;
803
- case TranscriptionErrorCode.NETWORK_ERROR:
804
- transcriptionError.value =
805
- "Network error. Please check your connection.";
806
- break;
807
- default:
808
- transcriptionError.value = retryable
809
- ? "Transcription failed. Please try again."
810
- : message;
811
- }
791
+ const key = ɵtranscriptionErrorMessageKey(error.info);
792
+ transcriptionError.value = key ? labels[key] : error.info.message;
812
793
  } else {
813
- transcriptionError.value = "Transcription failed. Please try again.";
794
+ transcriptionError.value = labels.transcriptionErrorGenericText;
814
795
  }
815
796
  } finally {
816
797
  isTranscribing.value = false;
@@ -831,6 +812,8 @@ const chatViewSlotProps = computed<CopilotChatViewOverrideSlotProps>(() => ({
831
812
  inputToolsMenu: props.inputToolsMenu,
832
813
  isConnecting: isConnecting.value,
833
814
  hasExplicitThreadId: hasExplicitThreadId.value,
815
+ toolCallDisplay: props.toolCallDisplay,
816
+ messageFeedback: props.messageFeedback,
834
817
  canStop: shouldAllowStop.value,
835
818
  canAddFile: attachmentsEnabled.value,
836
819
  canTranscribe: showTranscription.value,
@@ -887,6 +870,7 @@ const defaultChatViewBindings = computed(() => {
887
870
  :labels="resolvedLabels"
888
871
  >
889
872
  <div ref="attachmentContainerRef" style="display: contents">
873
+ <CopilotKitStyles />
890
874
  <input
891
875
  v-if="attachmentsEnabled"
892
876
  ref="fileInputRef"
@@ -931,6 +915,8 @@ const defaultChatViewBindings = computed(() => {
931
915
  :input-tools-menu="chatViewSlotProps.inputToolsMenu"
932
916
  :is-connecting="chatViewSlotProps.isConnecting"
933
917
  :has-explicit-thread-id="chatViewSlotProps.hasExplicitThreadId"
918
+ :tool-call-display="chatViewSlotProps.toolCallDisplay"
919
+ :message-feedback="chatViewSlotProps.messageFeedback"
934
920
  :on-finish-transcribe-with-audio="
935
921
  chatViewSlotProps.onFinishTranscribeWithAudio
936
922
  "
@@ -1,5 +1,14 @@
1
1
  <script setup lang="ts">
2
- import { computed, onBeforeUnmount, ref } from "vue";
2
+ import {
3
+ computed,
4
+ inject,
5
+ onBeforeUnmount,
6
+ onUpdated,
7
+ ref,
8
+ shallowRef,
9
+ toRef,
10
+ watch,
11
+ } from "vue";
3
12
  import type { Component } from "vue";
4
13
  import type { AssistantMessage, Message } from "@ag-ui/core";
5
14
  import { useCopilotChatConfiguration } from "../../providers/useCopilotChatConfiguration";
@@ -18,8 +27,18 @@ import {
18
27
  isVueComponentRenderer,
19
28
  } from "../../providers/markdown-renderer";
20
29
  import CopilotChatToolCallsView from "./CopilotChatToolCallsView.vue";
30
+ import { CopilotChatWorkText } from "./turn-work";
31
+ import CopilotChatAssistantToolbarButton from "./CopilotChatAssistantToolbarButton.vue";
32
+ import CopilotChatFeedbackCommentPopover from "./CopilotChatFeedbackCommentPopover.vue";
33
+ import CopilotChatInspectorButton from "./CopilotChatInspectorButton.vue";
34
+ import { useInspectorShortcutsHidden } from "./inspector-shortcuts";
35
+ import { InspectorKey } from "../../providers/keys";
36
+ import { useFeedbackComment, useMessageFeedback } from "./message-feedback";
37
+ import type { MessageFeedbackRating } from "../../lib/message-feedback";
21
38
  import type {
22
39
  CopilotChatAssistantMessageCopyButtonSlotProps,
40
+ CopilotChatAssistantMessageFeedbackCommentSlotProps,
41
+ CopilotChatAssistantMessageInspectorButtonSlotProps,
23
42
  CopilotChatAssistantMessageLayoutSlotProps,
24
43
  CopilotChatAssistantMessageMessageRendererSlotProps,
25
44
  CopilotChatAssistantMessageReadAloudButtonSlotProps,
@@ -71,6 +90,12 @@ defineSlots<{
71
90
  "tool-calls-view"?: (
72
91
  props: CopilotChatAssistantMessageToolCallsViewSlotProps,
73
92
  ) => unknown;
93
+ "inspector-button"?: (
94
+ props: CopilotChatAssistantMessageInspectorButtonSlotProps,
95
+ ) => unknown;
96
+ "feedback-comment"?: (
97
+ props: CopilotChatAssistantMessageFeedbackCommentSlotProps,
98
+ ) => unknown;
74
99
  "toolbar-items"?: () => unknown;
75
100
  [key: string]: ((props: any) => unknown) | undefined;
76
101
  }>();
@@ -87,13 +112,6 @@ const labels = computed(() => config.value?.labels ?? CopilotChatDefaultLabels);
87
112
  const copied = ref(false);
88
113
  let copiedResetTimeout: ReturnType<typeof setTimeout> | null = null;
89
114
 
90
- const toolbarButtonClass = [
91
- "cpk:inline-flex cpk:h-8 cpk:w-8 cpk:items-center cpk:justify-center cpk:rounded-md cpk:p-0",
92
- "cpk:cursor-pointer cpk:text-[rgb(93,93,93)] cpk:transition-colors cpk:hover:bg-[#E8E8E8]",
93
- "cpk:hover:text-[rgb(93,93,93)] cpk:dark:text-[rgb(243,243,243)] cpk:dark:hover:bg-[#303030]",
94
- "cpk:dark:hover:text-[rgb(243,243,243)] cpk:disabled:pointer-events-none cpk:disabled:opacity-50",
95
- ].join(" ");
96
-
97
115
  function normalizeContent(content: unknown): string {
98
116
  if (!content) {
99
117
  return "";
@@ -145,8 +163,28 @@ const activeMarkdownConfig = computed(() =>
145
163
  : (providerMarkdownRenderer as Record<string, unknown>),
146
164
  );
147
165
 
148
- const hasThumbsUp = computed(() => typeof props.onThumbsUp === "function");
149
- const hasThumbsDown = computed(() => typeof props.onThumbsDown === "function");
166
+ const inspector = inject(InspectorKey, null);
167
+ const shortcutsHidden = useInspectorShortcutsHidden();
168
+ const showInspectorShortcut = computed(
169
+ () => !!inspector?.isInspectorEnabled.value && !shortcutsHidden.value,
170
+ );
171
+
172
+ // Set while this chat collects ratings for Learning: the thumbs record them.
173
+ const feedback = useMessageFeedback(toRef(props, "message"));
174
+ const comment = useFeedbackComment(feedback);
175
+ const rating = computed(() => feedback.value?.feedback?.rating);
176
+ const root = ref<HTMLElement | null>(null);
177
+ // The chosen thumb the comment popover points at, and the rating the open
178
+ // comment answers.
179
+ const commentAnchor = shallowRef<HTMLElement | null>(null);
180
+ let commentRating = rating.value;
181
+
182
+ const hasThumbsUp = computed(
183
+ () => typeof props.onThumbsUp === "function" || !!feedback.value,
184
+ );
185
+ const hasThumbsDown = computed(
186
+ () => typeof props.onThumbsDown === "function" || !!feedback.value,
187
+ );
150
188
  const hasReadAloud = computed(() => typeof props.onReadAloud === "function");
151
189
  const hasRegenerate = computed(() => typeof props.onRegenerate === "function");
152
190
  const isLatestAssistantMessage = computed(
@@ -155,10 +193,138 @@ const isLatestAssistantMessage = computed(
155
193
  const shouldShowToolbar = computed(
156
194
  () =>
157
195
  props.toolbarVisible &&
158
- hasContent.value &&
196
+ (hasContent.value || showInspectorShortcut.value) &&
159
197
  !(props.isRunning && isLatestAssistantMessage.value),
160
198
  );
161
199
 
200
+ // A custom thumb that calls its handler without an event gives no element:
201
+ // point at the chosen thumb once it renders, before the popover reads it.
202
+ function findCommentAnchor() {
203
+ if (
204
+ comment.open.value &&
205
+ !commentAnchor.value?.isConnected &&
206
+ rating.value &&
207
+ root.value
208
+ ) {
209
+ commentAnchor.value =
210
+ root.value.querySelector<HTMLElement>(
211
+ `[data-copilotkit-rating="${rating.value}"]`,
212
+ ) ??
213
+ // A custom thumb that binds only `aria-pressed`.
214
+ root.value.querySelector<HTMLElement>('button[aria-pressed="true"]') ??
215
+ null;
216
+ }
217
+ }
218
+ onUpdated(findCommentAnchor);
219
+ watch(() => comment.open.value, findCommentAnchor, { flush: "post" });
220
+
221
+ /** Whether focus came from the keyboard; a pointer click also focuses buttons. */
222
+ function isFocusVisible(element: Element): boolean {
223
+ try {
224
+ return element.matches(":focus-visible");
225
+ } catch {
226
+ return false;
227
+ }
228
+ }
229
+
230
+ // Checks `visibility: hidden` too, which a detached popover uses.
231
+ const HIDDEN_TOO = { checkVisibilityCSS: true, visibilityProperty: true };
232
+
233
+ /**
234
+ * Thumbs are toggles: a new rating is saved and opens its comment, and
235
+ * clicking the chosen thumb again removes the rating. A keyboard click
236
+ * (`detail` 0) moves focus into the comment, as there is no pointer. Custom
237
+ * thumb slots may call the handler without an event.
238
+ *
239
+ * @returns Whether the app's handler should run: true for a new rating and
240
+ * whenever this chat does not record ratings, false when one is removed.
241
+ */
242
+ function rate(value: MessageFeedbackRating, event?: MouseEvent): boolean {
243
+ const controls = feedback.value;
244
+ if (!controls) return true;
245
+ if (rating.value === value) {
246
+ comment.close({ save: false });
247
+ controls.clear();
248
+ return false;
249
+ }
250
+ controls.rate(value);
251
+ commentRating = value;
252
+ commentAnchor.value =
253
+ event?.currentTarget instanceof HTMLElement ? event.currentTarget : null;
254
+ comment.show({ comment: "", focus: event?.detail === 0 });
255
+ return true;
256
+ }
257
+
258
+ /** Attributes that let the chosen thumb open and point at its comment. */
259
+ function thumbFeedbackProps(
260
+ value: MessageFeedbackRating,
261
+ ): Record<string, unknown> {
262
+ if (!feedback.value) return {};
263
+ const thumb = { "data-copilotkit-rating": value };
264
+ if (rating.value !== value) return { ...thumb, "aria-pressed": false };
265
+ const enter = (target: HTMLElement, via: "pointer" | "focus") => {
266
+ if (!comment.open.value) commentRating = value;
267
+ commentAnchor.value = target;
268
+ comment.enter(via);
269
+ };
270
+ return {
271
+ ...thumb,
272
+ "aria-pressed": true,
273
+ "aria-haspopup": "dialog",
274
+ "aria-expanded": comment.open.value,
275
+ onPointerenter: (event: PointerEvent) => {
276
+ if (event.pointerType !== "touch")
277
+ enter(event.currentTarget as HTMLElement, "pointer");
278
+ },
279
+ onPointerleave: (event: PointerEvent) => {
280
+ if (event.pointerType !== "touch") comment.leave("pointer");
281
+ },
282
+ // Keyboard focus opens the comment; Tab moves on into its field.
283
+ onFocus: (event: FocusEvent) => {
284
+ const target = event.currentTarget as HTMLElement;
285
+ if (isFocusVisible(target)) enter(target, "focus");
286
+ },
287
+ onBlur: () => comment.leave(),
288
+ onKeydown: (event: KeyboardEvent) => {
289
+ const input = comment.input.value;
290
+ // Not while the popover hides because its thumb scrolled away.
291
+ if (
292
+ event.key === "Tab" &&
293
+ !event.shiftKey &&
294
+ comment.open.value &&
295
+ input &&
296
+ input.checkVisibility?.(HIDDEN_TOO) !== false
297
+ ) {
298
+ event.preventDefault();
299
+ input.focus();
300
+ }
301
+ },
302
+ };
303
+ }
304
+
305
+ const thumbsUpProps = computed(() => thumbFeedbackProps("up"));
306
+ const thumbsDownProps = computed(() => thumbFeedbackProps("down"));
307
+
308
+ // The popover shows only with the toolbar and a rating. Hiding the toolbar
309
+ // keeps the edit; a rating removed elsewhere or Learning turned off ends it.
310
+ watch(
311
+ [() => comment.open.value, shouldShowToolbar, rating],
312
+ ([open, showToolbar, currentRating]) => {
313
+ if (!open) return;
314
+ // Changed or removed elsewhere: the draft answered the old rating.
315
+ if (currentRating !== commentRating) comment.close({ save: false });
316
+ else if (!showToolbar) comment.close();
317
+ },
318
+ );
319
+
320
+ function handleInspect() {
321
+ inspector?.openInspector({
322
+ messageId: props.message.id,
323
+ threadId: config.value?.threadId,
324
+ agentId: config.value?.agentId,
325
+ });
326
+ }
327
+
162
328
  function resetCopiedStateWithDelay() {
163
329
  if (copiedResetTimeout) {
164
330
  clearTimeout(copiedResetTimeout);
@@ -189,12 +355,13 @@ async function handleCopyMessage() {
189
355
  }
190
356
  }
191
357
 
192
- function handleThumbsUp() {
193
- emit("thumbs-up", props.message);
358
+ function handleThumbsUp(event?: MouseEvent) {
359
+ // The app hears about a rating given, not about one removed.
360
+ if (rate("up", event)) emit("thumbs-up", props.message);
194
361
  }
195
362
 
196
- function handleThumbsDown() {
197
- emit("thumbs-down", props.message);
363
+ function handleThumbsDown(event?: MouseEvent) {
364
+ if (rate("down", event)) emit("thumbs-down", props.message);
198
365
  }
199
366
 
200
367
  function handleReadAloud() {
@@ -235,25 +402,30 @@ onBeforeUnmount(() => {
235
402
  :on-regenerate="handleRegenerate"
236
403
  >
237
404
  <div
405
+ ref="root"
238
406
  data-copilotkit
239
407
  data-testid="copilot-assistant-message"
240
- class="cpk:prose cpk:max-w-full cpk:break-words cpk:dark:prose-invert"
408
+ class="copilotKitMessage copilotKitAssistantMessage"
241
409
  :data-message-id="message.id"
242
410
  v-bind="$attrs"
243
411
  >
244
- <slot
245
- name="message-renderer"
246
- :message="message"
247
- :content="normalizedContent"
248
- >
249
- <component
250
- :is="ActiveMarkdownRenderer"
251
- v-if="hasContent"
252
- v-bind="activeMarkdownConfig"
253
- :content="normalizedContent"
254
- :is-streaming="isRunning && isLatestAssistantMessage"
255
- />
256
- </slot>
412
+ <CopilotChatWorkText :message-id="message.id">
413
+ <div class="cpk-markdown cpk-assistant-message-markdown">
414
+ <slot
415
+ name="message-renderer"
416
+ :message="message"
417
+ :content="normalizedContent"
418
+ >
419
+ <component
420
+ :is="ActiveMarkdownRenderer"
421
+ v-if="hasContent"
422
+ v-bind="activeMarkdownConfig"
423
+ :content="normalizedContent"
424
+ :is-streaming="isRunning && isLatestAssistantMessage"
425
+ />
426
+ </slot>
427
+ </div>
428
+ </CopilotChatWorkText>
257
429
 
258
430
  <slot name="tool-calls-view" :message="message" :messages="messages">
259
431
  <CopilotChatToolCallsView :message="message" :messages="messages">
@@ -274,26 +446,27 @@ onBeforeUnmount(() => {
274
446
  :should-show-toolbar="shouldShowToolbar"
275
447
  >
276
448
  <div
277
- class="cpk:w-full cpk:bg-transparent cpk:flex cpk:items-center cpk:-ml-[5px] cpk:-mt-[0px]"
449
+ data-testid="copilot-assistant-toolbar"
450
+ class="cpk-assistant-message-toolbar"
278
451
  >
279
- <div class="cpk:flex cpk:items-center cpk:gap-1">
452
+ <div class="cpk-assistant-message-toolbar-items">
280
453
  <slot
281
454
  name="copy-button"
282
455
  :on-copy="handleCopyMessage"
283
456
  :copied="copied"
284
457
  :label="labels.assistantMessageToolbarCopyMessageLabel"
285
458
  >
286
- <button
459
+ <CopilotChatAssistantToolbarButton
287
460
  data-testid="copilot-copy-button"
288
- type="button"
289
- :class="toolbarButtonClass"
290
- :aria-label="labels.assistantMessageToolbarCopyMessageLabel"
291
- :title="labels.assistantMessageToolbarCopyMessageLabel"
461
+ :label="labels.assistantMessageToolbarCopyMessageLabel"
292
462
  @click="handleCopyMessage"
293
463
  >
294
- <IconCheck v-if="copied" class="cpk:size-[18px]" />
295
- <IconCopy v-else class="cpk:size-[18px]" />
296
- </button>
464
+ <IconCheck
465
+ v-if="copied"
466
+ class="cpk-assistant-message-toolbar-icon"
467
+ />
468
+ <IconCopy v-else class="cpk-assistant-message-toolbar-icon" />
469
+ </CopilotChatAssistantToolbarButton>
297
470
  </slot>
298
471
 
299
472
  <slot
@@ -301,16 +474,20 @@ onBeforeUnmount(() => {
301
474
  name="thumbs-up-button"
302
475
  :on-thumbs-up="handleThumbsUp"
303
476
  :label="labels.assistantMessageToolbarThumbsUpLabel"
477
+ :pressed="rating === 'up'"
478
+ :thumb-props="thumbsUpProps"
304
479
  >
305
- <button
306
- type="button"
307
- :class="toolbarButtonClass"
308
- :aria-label="labels.assistantMessageToolbarThumbsUpLabel"
309
- :title="labels.assistantMessageToolbarThumbsUpLabel"
480
+ <CopilotChatAssistantToolbarButton
481
+ data-testid="copilot-thumbs-up-button"
482
+ :label="labels.assistantMessageToolbarThumbsUpLabel"
483
+ v-bind="thumbsUpProps"
310
484
  @click="handleThumbsUp"
311
485
  >
312
- <IconThumbsUp class="cpk:size-[18px]" />
313
- </button>
486
+ <IconThumbsUp
487
+ class="cpk-assistant-message-toolbar-icon"
488
+ :fill="rating === 'up' ? 'currentColor' : 'none'"
489
+ />
490
+ </CopilotChatAssistantToolbarButton>
314
491
  </slot>
315
492
 
316
493
  <slot
@@ -318,16 +495,20 @@ onBeforeUnmount(() => {
318
495
  name="thumbs-down-button"
319
496
  :on-thumbs-down="handleThumbsDown"
320
497
  :label="labels.assistantMessageToolbarThumbsDownLabel"
498
+ :pressed="rating === 'down'"
499
+ :thumb-props="thumbsDownProps"
321
500
  >
322
- <button
323
- type="button"
324
- :class="toolbarButtonClass"
325
- :aria-label="labels.assistantMessageToolbarThumbsDownLabel"
326
- :title="labels.assistantMessageToolbarThumbsDownLabel"
501
+ <CopilotChatAssistantToolbarButton
502
+ data-testid="copilot-thumbs-down-button"
503
+ :label="labels.assistantMessageToolbarThumbsDownLabel"
504
+ v-bind="thumbsDownProps"
327
505
  @click="handleThumbsDown"
328
506
  >
329
- <IconThumbsDown class="cpk:size-[18px]" />
330
- </button>
507
+ <IconThumbsDown
508
+ class="cpk-assistant-message-toolbar-icon"
509
+ :fill="rating === 'down' ? 'currentColor' : 'none'"
510
+ />
511
+ </CopilotChatAssistantToolbarButton>
331
512
  </slot>
332
513
 
333
514
  <slot
@@ -336,15 +517,13 @@ onBeforeUnmount(() => {
336
517
  :on-read-aloud="handleReadAloud"
337
518
  :label="labels.assistantMessageToolbarReadAloudLabel"
338
519
  >
339
- <button
340
- type="button"
341
- :class="toolbarButtonClass"
342
- :aria-label="labels.assistantMessageToolbarReadAloudLabel"
343
- :title="labels.assistantMessageToolbarReadAloudLabel"
520
+ <CopilotChatAssistantToolbarButton
521
+ data-testid="copilot-read-aloud-button"
522
+ :label="labels.assistantMessageToolbarReadAloudLabel"
344
523
  @click="handleReadAloud"
345
524
  >
346
- <IconVolume2 class="cpk:size-[20px]" />
347
- </button>
525
+ <IconVolume2 class="cpk-assistant-message-read-aloud-icon" />
526
+ </CopilotChatAssistantToolbarButton>
348
527
  </slot>
349
528
 
350
529
  <slot
@@ -353,21 +532,42 @@ onBeforeUnmount(() => {
353
532
  :on-regenerate="handleRegenerate"
354
533
  :label="labels.assistantMessageToolbarRegenerateLabel"
355
534
  >
356
- <button
357
- type="button"
358
- :class="toolbarButtonClass"
359
- :aria-label="labels.assistantMessageToolbarRegenerateLabel"
360
- :title="labels.assistantMessageToolbarRegenerateLabel"
535
+ <CopilotChatAssistantToolbarButton
536
+ data-testid="copilot-regenerate-button"
537
+ :label="labels.assistantMessageToolbarRegenerateLabel"
361
538
  @click="handleRegenerate"
362
539
  >
363
- <IconRefreshCw class="cpk:size-[18px]" />
364
- </button>
540
+ <IconRefreshCw class="cpk-assistant-message-toolbar-icon" />
541
+ </CopilotChatAssistantToolbarButton>
365
542
  </slot>
366
543
 
367
544
  <slot name="toolbar-items" />
545
+
546
+ <slot
547
+ v-if="showInspectorShortcut"
548
+ name="inspector-button"
549
+ :on-inspect="handleInspect"
550
+ :label="labels.assistantMessageToolbarInspectorLabel"
551
+ >
552
+ <CopilotChatInspectorButton @click="handleInspect" />
553
+ </slot>
368
554
  </div>
369
555
  </div>
370
556
  </slot>
371
557
  </div>
372
558
  </slot>
559
+
560
+ <!-- Floats in a portal next to the chosen thumb, so it never moves the chat. -->
561
+ <CopilotChatFeedbackCommentPopover
562
+ v-if="feedback?.feedback && shouldShowToolbar"
563
+ :comment="comment"
564
+ :saved-comment="feedback.feedback.comment ?? ''"
565
+ :rating="feedback.feedback.rating"
566
+ :anchor="commentAnchor"
567
+ :message-id="message.id"
568
+ >
569
+ <template v-if="$slots['feedback-comment']" #feedback-comment="slotProps">
570
+ <slot name="feedback-comment" v-bind="slotProps" />
571
+ </template>
572
+ </CopilotChatFeedbackCommentPopover>
373
573
  </template>
@@ -0,0 +1,46 @@
1
+ <script setup lang="ts">
2
+ /**
3
+ * React's `CopilotChatAssistantMessage.ToolbarButton`: an icon button named by
4
+ * `label`, with the label as its tooltip. While the button's own popup is
5
+ * open (`aria-expanded="true"`), the popup replaces the tooltip: an open
6
+ * tooltip closes, and it does not reappear when the popup closes under a
7
+ * pointer that left.
8
+ *
9
+ * @internal
10
+ */
11
+ import { computed, mergeProps, useAttrs } from "vue";
12
+ import CopilotTooltip from "../ui/CopilotTooltip.vue";
13
+
14
+ defineOptions({ inheritAttrs: false });
15
+
16
+ defineProps<{ label: string }>();
17
+
18
+ defineSlots<{ default(): unknown; tooltip?(): unknown }>();
19
+
20
+ const attrs = useAttrs();
21
+ const popupOpen = computed(
22
+ () => attrs["aria-expanded"] === true || attrs["aria-expanded"] === "true",
23
+ );
24
+
25
+ // Styles live in @copilotkit/core (ui/button.css, assistant-message.css).
26
+ const buttonClass =
27
+ "cpk-button cpk-button-assistant-message-toolbar cpk-button-size-default";
28
+ </script>
29
+
30
+ <template>
31
+ <CopilotTooltip :content="label" side="bottom" :suppressed="popupOpen">
32
+ <template #default="{ triggerProps }">
33
+ <button
34
+ type="button"
35
+ :class="buttonClass"
36
+ :aria-label="label"
37
+ v-bind="mergeProps(triggerProps, $attrs)"
38
+ >
39
+ <slot />
40
+ </button>
41
+ </template>
42
+ <template v-if="$slots.tooltip" #content>
43
+ <slot name="tooltip" />
44
+ </template>
45
+ </CopilotTooltip>
46
+ </template>