@copilotkit/react-core 0.0.0-0.0.0-max-changeset-10101010101010-20260109191632

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 (497) hide show
  1. package/CHANGELOG.md +4188 -0
  2. package/LICENSE +21 -0
  3. package/README.md +141 -0
  4. package/dist/chunk-2IDV5OHF.mjs +11 -0
  5. package/dist/chunk-2IDV5OHF.mjs.map +1 -0
  6. package/dist/chunk-336QEM3A.mjs +349 -0
  7. package/dist/chunk-336QEM3A.mjs.map +1 -0
  8. package/dist/chunk-36KQV2NA.mjs +1 -0
  9. package/dist/chunk-36KQV2NA.mjs.map +1 -0
  10. package/dist/chunk-3MHWEKFN.mjs +759 -0
  11. package/dist/chunk-3MHWEKFN.mjs.map +1 -0
  12. package/dist/chunk-4CEQJ2X6.mjs +31 -0
  13. package/dist/chunk-4CEQJ2X6.mjs.map +1 -0
  14. package/dist/chunk-4RRMC7L2.mjs +32 -0
  15. package/dist/chunk-4RRMC7L2.mjs.map +1 -0
  16. package/dist/chunk-6ESSSQ7Q.mjs +134 -0
  17. package/dist/chunk-6ESSSQ7Q.mjs.map +1 -0
  18. package/dist/chunk-6PUNP7CD.mjs +102 -0
  19. package/dist/chunk-6PUNP7CD.mjs.map +1 -0
  20. package/dist/chunk-6YOKPWQ7.mjs +1 -0
  21. package/dist/chunk-6YOKPWQ7.mjs.map +1 -0
  22. package/dist/chunk-6ZLPNY7X.mjs +225 -0
  23. package/dist/chunk-6ZLPNY7X.mjs.map +1 -0
  24. package/dist/chunk-7DTB7S5V.mjs +83 -0
  25. package/dist/chunk-7DTB7S5V.mjs.map +1 -0
  26. package/dist/chunk-7IBF6RBW.mjs +23 -0
  27. package/dist/chunk-7IBF6RBW.mjs.map +1 -0
  28. package/dist/chunk-7X3E6GHT.mjs +83 -0
  29. package/dist/chunk-7X3E6GHT.mjs.map +1 -0
  30. package/dist/chunk-A6NKSGH3.mjs +1 -0
  31. package/dist/chunk-A6NKSGH3.mjs.map +1 -0
  32. package/dist/chunk-ABWT4DRT.mjs +24 -0
  33. package/dist/chunk-ABWT4DRT.mjs.map +1 -0
  34. package/dist/chunk-AFNWX62Q.mjs +110 -0
  35. package/dist/chunk-AFNWX62Q.mjs.map +1 -0
  36. package/dist/chunk-BUSWSDYO.mjs +17 -0
  37. package/dist/chunk-BUSWSDYO.mjs.map +1 -0
  38. package/dist/chunk-CDUIA2WM.mjs +60 -0
  39. package/dist/chunk-CDUIA2WM.mjs.map +1 -0
  40. package/dist/chunk-CYDWEPFL.mjs +1 -0
  41. package/dist/chunk-CYDWEPFL.mjs.map +1 -0
  42. package/dist/chunk-DMLQZG75.mjs +25 -0
  43. package/dist/chunk-DMLQZG75.mjs.map +1 -0
  44. package/dist/chunk-E7SE25ZU.mjs +59 -0
  45. package/dist/chunk-E7SE25ZU.mjs.map +1 -0
  46. package/dist/chunk-EFL5OBKN.mjs +310 -0
  47. package/dist/chunk-EFL5OBKN.mjs.map +1 -0
  48. package/dist/chunk-F555TVE4.mjs +33 -0
  49. package/dist/chunk-F555TVE4.mjs.map +1 -0
  50. package/dist/chunk-FD6FGKYY.mjs +1 -0
  51. package/dist/chunk-FD6FGKYY.mjs.map +1 -0
  52. package/dist/chunk-FDOMAPJY.mjs +59 -0
  53. package/dist/chunk-FDOMAPJY.mjs.map +1 -0
  54. package/dist/chunk-GJOR3RI6.mjs +120 -0
  55. package/dist/chunk-GJOR3RI6.mjs.map +1 -0
  56. package/dist/chunk-GPEJNVE5.mjs +80 -0
  57. package/dist/chunk-GPEJNVE5.mjs.map +1 -0
  58. package/dist/chunk-HM6ON7AM.mjs +86 -0
  59. package/dist/chunk-HM6ON7AM.mjs.map +1 -0
  60. package/dist/chunk-I76HKHPJ.mjs +32 -0
  61. package/dist/chunk-I76HKHPJ.mjs.map +1 -0
  62. package/dist/chunk-ICIK2BSB.mjs +17 -0
  63. package/dist/chunk-ICIK2BSB.mjs.map +1 -0
  64. package/dist/chunk-JD7BAH7U.mjs +1 -0
  65. package/dist/chunk-JD7BAH7U.mjs.map +1 -0
  66. package/dist/chunk-LUGEI4YQ.mjs +1 -0
  67. package/dist/chunk-LUGEI4YQ.mjs.map +1 -0
  68. package/dist/chunk-N7FZFIWO.mjs +551 -0
  69. package/dist/chunk-N7FZFIWO.mjs.map +1 -0
  70. package/dist/chunk-NB2FKV2V.mjs +1 -0
  71. package/dist/chunk-NB2FKV2V.mjs.map +1 -0
  72. package/dist/chunk-NBK4KBLX.mjs +54 -0
  73. package/dist/chunk-NBK4KBLX.mjs.map +1 -0
  74. package/dist/chunk-O7ARI5CV.mjs +31 -0
  75. package/dist/chunk-O7ARI5CV.mjs.map +1 -0
  76. package/dist/chunk-P2YEE2ZI.mjs +36 -0
  77. package/dist/chunk-P2YEE2ZI.mjs.map +1 -0
  78. package/dist/chunk-PIF5KJYI.mjs +103 -0
  79. package/dist/chunk-PIF5KJYI.mjs.map +1 -0
  80. package/dist/chunk-PMAFHQ7P.mjs +65 -0
  81. package/dist/chunk-PMAFHQ7P.mjs.map +1 -0
  82. package/dist/chunk-QNUAXSDP.mjs +166 -0
  83. package/dist/chunk-QNUAXSDP.mjs.map +1 -0
  84. package/dist/chunk-RKTVJRK7.mjs +143 -0
  85. package/dist/chunk-RKTVJRK7.mjs.map +1 -0
  86. package/dist/chunk-SKC7AJIV.mjs +61 -0
  87. package/dist/chunk-SKC7AJIV.mjs.map +1 -0
  88. package/dist/chunk-SPCZTZCY.mjs +1 -0
  89. package/dist/chunk-SPCZTZCY.mjs.map +1 -0
  90. package/dist/chunk-SQDOUMPZ.mjs +125 -0
  91. package/dist/chunk-SQDOUMPZ.mjs.map +1 -0
  92. package/dist/chunk-WF65O6HX.mjs +66 -0
  93. package/dist/chunk-WF65O6HX.mjs.map +1 -0
  94. package/dist/chunk-XDFVCQD3.mjs +27 -0
  95. package/dist/chunk-XDFVCQD3.mjs.map +1 -0
  96. package/dist/chunk-YJ2KZDZJ.mjs +186 -0
  97. package/dist/chunk-YJ2KZDZJ.mjs.map +1 -0
  98. package/dist/chunk-YTQHRJUA.mjs +86 -0
  99. package/dist/chunk-YTQHRJUA.mjs.map +1 -0
  100. package/dist/chunk-YYN33GSG.mjs +73 -0
  101. package/dist/chunk-YYN33GSG.mjs.map +1 -0
  102. package/dist/chunk-Z6JV2LRY.mjs +37 -0
  103. package/dist/chunk-Z6JV2LRY.mjs.map +1 -0
  104. package/dist/chunk-ZVF5Q6IH.mjs +29 -0
  105. package/dist/chunk-ZVF5Q6IH.mjs.map +1 -0
  106. package/dist/chunk-ZYTXB6HH.mjs +151 -0
  107. package/dist/chunk-ZYTXB6HH.mjs.map +1 -0
  108. package/dist/components/CopilotListeners.d.ts +3 -0
  109. package/dist/components/CopilotListeners.js +101 -0
  110. package/dist/components/CopilotListeners.js.map +1 -0
  111. package/dist/components/CopilotListeners.mjs +9 -0
  112. package/dist/components/CopilotListeners.mjs.map +1 -0
  113. package/dist/components/copilot-provider/copilot-messages.d.ts +24 -0
  114. package/dist/components/copilot-provider/copilot-messages.js +351 -0
  115. package/dist/components/copilot-provider/copilot-messages.js.map +1 -0
  116. package/dist/components/copilot-provider/copilot-messages.mjs +16 -0
  117. package/dist/components/copilot-provider/copilot-messages.mjs.map +1 -0
  118. package/dist/components/copilot-provider/copilotkit-props.d.ts +160 -0
  119. package/dist/components/copilot-provider/copilotkit-props.js +19 -0
  120. package/dist/components/copilot-provider/copilotkit-props.js.map +1 -0
  121. package/dist/components/copilot-provider/copilotkit-props.mjs +1 -0
  122. package/dist/components/copilot-provider/copilotkit-props.mjs.map +1 -0
  123. package/dist/components/copilot-provider/copilotkit.d.ts +19 -0
  124. package/dist/components/copilot-provider/copilotkit.js +1960 -0
  125. package/dist/components/copilot-provider/copilotkit.js.map +1 -0
  126. package/dist/components/copilot-provider/copilotkit.mjs +31 -0
  127. package/dist/components/copilot-provider/copilotkit.mjs.map +1 -0
  128. package/dist/components/copilot-provider/index.d.ts +14 -0
  129. package/dist/components/copilot-provider/index.js +1960 -0
  130. package/dist/components/copilot-provider/index.js.map +1 -0
  131. package/dist/components/copilot-provider/index.mjs +30 -0
  132. package/dist/components/copilot-provider/index.mjs.map +1 -0
  133. package/dist/components/dev-console/console-trigger.d.ts +8 -0
  134. package/dist/components/dev-console/console-trigger.js +1202 -0
  135. package/dist/components/dev-console/console-trigger.js.map +1 -0
  136. package/dist/components/dev-console/console-trigger.mjs +233 -0
  137. package/dist/components/dev-console/console-trigger.mjs.map +1 -0
  138. package/dist/components/dev-console/developer-console-modal.d.ts +10 -0
  139. package/dist/components/dev-console/developer-console-modal.js +987 -0
  140. package/dist/components/dev-console/developer-console-modal.js.map +1 -0
  141. package/dist/components/dev-console/developer-console-modal.mjs +12 -0
  142. package/dist/components/dev-console/developer-console-modal.mjs.map +1 -0
  143. package/dist/components/dev-console/icons.d.ts +9 -0
  144. package/dist/components/dev-console/icons.js +131 -0
  145. package/dist/components/dev-console/icons.js.map +1 -0
  146. package/dist/components/dev-console/icons.mjs +16 -0
  147. package/dist/components/dev-console/icons.mjs.map +1 -0
  148. package/dist/components/error-boundary/error-boundary.d.ts +31 -0
  149. package/dist/components/error-boundary/error-boundary.js +500 -0
  150. package/dist/components/error-boundary/error-boundary.js.map +1 -0
  151. package/dist/components/error-boundary/error-boundary.mjs +15 -0
  152. package/dist/components/error-boundary/error-boundary.mjs.map +1 -0
  153. package/dist/components/error-boundary/error-utils.d.ts +11 -0
  154. package/dist/components/error-boundary/error-utils.js +190 -0
  155. package/dist/components/error-boundary/error-utils.js.map +1 -0
  156. package/dist/components/error-boundary/error-utils.mjs +14 -0
  157. package/dist/components/error-boundary/error-utils.mjs.map +1 -0
  158. package/dist/components/index.d.ts +14 -0
  159. package/dist/components/index.js +1960 -0
  160. package/dist/components/index.js.map +1 -0
  161. package/dist/components/index.mjs +31 -0
  162. package/dist/components/index.mjs.map +1 -0
  163. package/dist/components/toast/exclamation-mark-icon.d.ts +9 -0
  164. package/dist/components/toast/exclamation-mark-icon.js +55 -0
  165. package/dist/components/toast/exclamation-mark-icon.js.map +1 -0
  166. package/dist/components/toast/exclamation-mark-icon.mjs +8 -0
  167. package/dist/components/toast/exclamation-mark-icon.mjs.map +1 -0
  168. package/dist/components/toast/toast-provider.d.ts +27 -0
  169. package/dist/components/toast/toast-provider.js +347 -0
  170. package/dist/components/toast/toast-provider.js.map +1 -0
  171. package/dist/components/toast/toast-provider.mjs +10 -0
  172. package/dist/components/toast/toast-provider.mjs.map +1 -0
  173. package/dist/components/usage-banner.d.ts +29 -0
  174. package/dist/components/usage-banner.js +247 -0
  175. package/dist/components/usage-banner.js.map +1 -0
  176. package/dist/components/usage-banner.mjs +12 -0
  177. package/dist/components/usage-banner.mjs.map +1 -0
  178. package/dist/context/coagent-state-renders-context.d.ts +24 -0
  179. package/dist/context/coagent-state-renders-context.js +91 -0
  180. package/dist/context/coagent-state-renders-context.js.map +1 -0
  181. package/dist/context/coagent-state-renders-context.mjs +12 -0
  182. package/dist/context/coagent-state-renders-context.mjs.map +1 -0
  183. package/dist/context/copilot-context.d.ts +10 -0
  184. package/dist/context/copilot-context.js +161 -0
  185. package/dist/context/copilot-context.js.map +1 -0
  186. package/dist/context/copilot-context.mjs +10 -0
  187. package/dist/context/copilot-context.mjs.map +1 -0
  188. package/dist/context/copilot-messages-context.d.ts +18 -0
  189. package/dist/context/copilot-messages-context.js +60 -0
  190. package/dist/context/copilot-messages-context.js.map +1 -0
  191. package/dist/context/copilot-messages-context.mjs +10 -0
  192. package/dist/context/copilot-messages-context.mjs.map +1 -0
  193. package/dist/context/index.d.ts +15 -0
  194. package/dist/context/index.js +285 -0
  195. package/dist/context/index.js.map +1 -0
  196. package/dist/context/index.mjs +33 -0
  197. package/dist/context/index.mjs.map +1 -0
  198. package/dist/context/threads-context.d.ts +16 -0
  199. package/dist/context/threads-context.js +59 -0
  200. package/dist/context/threads-context.js.map +1 -0
  201. package/dist/context/threads-context.mjs +12 -0
  202. package/dist/context/threads-context.mjs.map +1 -0
  203. package/dist/copilot-context-ec77e921.d.ts +209 -0
  204. package/dist/hooks/index.d.ts +33 -0
  205. package/dist/hooks/index.js +1774 -0
  206. package/dist/hooks/index.js.map +1 -0
  207. package/dist/hooks/index.mjs +91 -0
  208. package/dist/hooks/index.mjs.map +1 -0
  209. package/dist/hooks/use-agent-nodename.d.ts +3 -0
  210. package/dist/hooks/use-agent-nodename.js +56 -0
  211. package/dist/hooks/use-agent-nodename.js.map +1 -0
  212. package/dist/hooks/use-agent-nodename.mjs +8 -0
  213. package/dist/hooks/use-agent-nodename.mjs.map +1 -0
  214. package/dist/hooks/use-coagent-state-render-bridge.d.ts +100 -0
  215. package/dist/hooks/use-coagent-state-render-bridge.js +214 -0
  216. package/dist/hooks/use-coagent-state-render-bridge.js.map +1 -0
  217. package/dist/hooks/use-coagent-state-render-bridge.mjs +15 -0
  218. package/dist/hooks/use-coagent-state-render-bridge.mjs.map +1 -0
  219. package/dist/hooks/use-coagent-state-render.d.ts +55 -0
  220. package/dist/hooks/use-coagent-state-render.js +255 -0
  221. package/dist/hooks/use-coagent-state-render.js.map +1 -0
  222. package/dist/hooks/use-coagent-state-render.mjs +11 -0
  223. package/dist/hooks/use-coagent-state-render.mjs.map +1 -0
  224. package/dist/hooks/use-coagent.d.ts +192 -0
  225. package/dist/hooks/use-coagent.js +233 -0
  226. package/dist/hooks/use-coagent.js.map +1 -0
  227. package/dist/hooks/use-coagent.mjs +9 -0
  228. package/dist/hooks/use-coagent.mjs.map +1 -0
  229. package/dist/hooks/use-configure-chat-suggestions.d.ts +36 -0
  230. package/dist/hooks/use-configure-chat-suggestions.js +79 -0
  231. package/dist/hooks/use-configure-chat-suggestions.js.map +1 -0
  232. package/dist/hooks/use-configure-chat-suggestions.mjs +47 -0
  233. package/dist/hooks/use-configure-chat-suggestions.mjs.map +1 -0
  234. package/dist/hooks/use-copilot-action.d.ts +103 -0
  235. package/dist/hooks/use-copilot-action.js +295 -0
  236. package/dist/hooks/use-copilot-action.js.map +1 -0
  237. package/dist/hooks/use-copilot-action.mjs +11 -0
  238. package/dist/hooks/use-copilot-action.mjs.map +1 -0
  239. package/dist/hooks/use-copilot-additional-instructions.d.ts +26 -0
  240. package/dist/hooks/use-copilot-additional-instructions.js +177 -0
  241. package/dist/hooks/use-copilot-additional-instructions.js.map +1 -0
  242. package/dist/hooks/use-copilot-additional-instructions.mjs +9 -0
  243. package/dist/hooks/use-copilot-additional-instructions.mjs.map +1 -0
  244. package/dist/hooks/use-copilot-authenticated-action.d.ts +18 -0
  245. package/dist/hooks/use-copilot-authenticated-action.js +462 -0
  246. package/dist/hooks/use-copilot-authenticated-action.js.map +1 -0
  247. package/dist/hooks/use-copilot-authenticated-action.mjs +13 -0
  248. package/dist/hooks/use-copilot-authenticated-action.mjs.map +1 -0
  249. package/dist/hooks/use-copilot-chat-headless_c.d.ts +25 -0
  250. package/dist/hooks/use-copilot-chat-headless_c.js +1044 -0
  251. package/dist/hooks/use-copilot-chat-headless_c.js.map +1 -0
  252. package/dist/hooks/use-copilot-chat-headless_c.mjs +24 -0
  253. package/dist/hooks/use-copilot-chat-headless_c.mjs.map +1 -0
  254. package/dist/hooks/use-copilot-chat-suggestions.d.ts +35 -0
  255. package/dist/hooks/use-copilot-chat-suggestions.js +60 -0
  256. package/dist/hooks/use-copilot-chat-suggestions.js.map +1 -0
  257. package/dist/hooks/use-copilot-chat-suggestions.mjs +8 -0
  258. package/dist/hooks/use-copilot-chat-suggestions.mjs.map +1 -0
  259. package/dist/hooks/use-copilot-chat.d.ts +92 -0
  260. package/dist/hooks/use-copilot-chat.js +978 -0
  261. package/dist/hooks/use-copilot-chat.js.map +1 -0
  262. package/dist/hooks/use-copilot-chat.mjs +21 -0
  263. package/dist/hooks/use-copilot-chat.mjs.map +1 -0
  264. package/dist/hooks/use-copilot-chat_internal.d.ts +244 -0
  265. package/dist/hooks/use-copilot-chat_internal.js +976 -0
  266. package/dist/hooks/use-copilot-chat_internal.js.map +1 -0
  267. package/dist/hooks/use-copilot-chat_internal.mjs +22 -0
  268. package/dist/hooks/use-copilot-chat_internal.mjs.map +1 -0
  269. package/dist/hooks/use-copilot-readable.d.ts +37 -0
  270. package/dist/hooks/use-copilot-readable.js +61 -0
  271. package/dist/hooks/use-copilot-readable.js.map +1 -0
  272. package/dist/hooks/use-copilot-readable.mjs +8 -0
  273. package/dist/hooks/use-copilot-readable.mjs.map +1 -0
  274. package/dist/hooks/use-copilot-runtime-client.d.ts +10 -0
  275. package/dist/hooks/use-copilot-runtime-client.js +203 -0
  276. package/dist/hooks/use-copilot-runtime-client.js.map +1 -0
  277. package/dist/hooks/use-copilot-runtime-client.mjs +9 -0
  278. package/dist/hooks/use-copilot-runtime-client.mjs.map +1 -0
  279. package/dist/hooks/use-default-tool.d.ts +8 -0
  280. package/dist/hooks/use-default-tool.js +302 -0
  281. package/dist/hooks/use-default-tool.js.map +1 -0
  282. package/dist/hooks/use-default-tool.mjs +12 -0
  283. package/dist/hooks/use-default-tool.mjs.map +1 -0
  284. package/dist/hooks/use-flat-category-store.d.ts +9 -0
  285. package/dist/hooks/use-flat-category-store.js +93 -0
  286. package/dist/hooks/use-flat-category-store.js.map +1 -0
  287. package/dist/hooks/use-flat-category-store.mjs +8 -0
  288. package/dist/hooks/use-flat-category-store.mjs.map +1 -0
  289. package/dist/hooks/use-frontend-tool.d.ts +11 -0
  290. package/dist/hooks/use-frontend-tool.js +104 -0
  291. package/dist/hooks/use-frontend-tool.js.map +1 -0
  292. package/dist/hooks/use-frontend-tool.mjs +8 -0
  293. package/dist/hooks/use-frontend-tool.mjs.map +1 -0
  294. package/dist/hooks/use-human-in-the-loop.d.ts +13 -0
  295. package/dist/hooks/use-human-in-the-loop.js +122 -0
  296. package/dist/hooks/use-human-in-the-loop.js.map +1 -0
  297. package/dist/hooks/use-human-in-the-loop.mjs +8 -0
  298. package/dist/hooks/use-human-in-the-loop.mjs.map +1 -0
  299. package/dist/hooks/use-langgraph-interrupt-render.d.ts +6 -0
  300. package/dist/hooks/use-langgraph-interrupt-render.js +318 -0
  301. package/dist/hooks/use-langgraph-interrupt-render.js.map +1 -0
  302. package/dist/hooks/use-langgraph-interrupt-render.mjs +14 -0
  303. package/dist/hooks/use-langgraph-interrupt-render.mjs.map +1 -0
  304. package/dist/hooks/use-langgraph-interrupt.d.ts +14 -0
  305. package/dist/hooks/use-langgraph-interrupt.js +201 -0
  306. package/dist/hooks/use-langgraph-interrupt.js.map +1 -0
  307. package/dist/hooks/use-langgraph-interrupt.mjs +10 -0
  308. package/dist/hooks/use-langgraph-interrupt.mjs.map +1 -0
  309. package/dist/hooks/use-lazy-tool-renderer.d.ts +6 -0
  310. package/dist/hooks/use-lazy-tool-renderer.js +53 -0
  311. package/dist/hooks/use-lazy-tool-renderer.js.map +1 -0
  312. package/dist/hooks/use-lazy-tool-renderer.mjs +8 -0
  313. package/dist/hooks/use-lazy-tool-renderer.mjs.map +1 -0
  314. package/dist/hooks/use-make-copilot-document-readable.d.ts +12 -0
  315. package/dist/hooks/use-make-copilot-document-readable.js +176 -0
  316. package/dist/hooks/use-make-copilot-document-readable.js.map +1 -0
  317. package/dist/hooks/use-make-copilot-document-readable.mjs +9 -0
  318. package/dist/hooks/use-make-copilot-document-readable.mjs.map +1 -0
  319. package/dist/hooks/use-render-tool-call.d.ts +12 -0
  320. package/dist/hooks/use-render-tool-call.js +90 -0
  321. package/dist/hooks/use-render-tool-call.js.map +1 -0
  322. package/dist/hooks/use-render-tool-call.mjs +8 -0
  323. package/dist/hooks/use-render-tool-call.mjs.map +1 -0
  324. package/dist/hooks/use-tree.d.ts +19 -0
  325. package/dist/hooks/use-tree.js +175 -0
  326. package/dist/hooks/use-tree.js.map +1 -0
  327. package/dist/hooks/use-tree.mjs +8 -0
  328. package/dist/hooks/use-tree.mjs.map +1 -0
  329. package/dist/index.d.ts +43 -0
  330. package/dist/index.js +3528 -0
  331. package/dist/index.js.map +1 -0
  332. package/dist/index.mjs +149 -0
  333. package/dist/index.mjs.map +1 -0
  334. package/dist/lib/copilot-task.d.ts +97 -0
  335. package/dist/lib/copilot-task.js +194 -0
  336. package/dist/lib/copilot-task.js.map +1 -0
  337. package/dist/lib/copilot-task.mjs +31 -0
  338. package/dist/lib/copilot-task.mjs.map +1 -0
  339. package/dist/lib/index.d.ts +11 -0
  340. package/dist/lib/index.js +196 -0
  341. package/dist/lib/index.js.map +1 -0
  342. package/dist/lib/index.mjs +32 -0
  343. package/dist/lib/index.mjs.map +1 -0
  344. package/dist/lib/status-checker.d.ts +17 -0
  345. package/dist/lib/status-checker.js +102 -0
  346. package/dist/lib/status-checker.js.map +1 -0
  347. package/dist/lib/status-checker.mjs +8 -0
  348. package/dist/lib/status-checker.mjs.map +1 -0
  349. package/dist/setupTests.d.ts +2 -0
  350. package/dist/setupTests.js +26 -0
  351. package/dist/setupTests.js.map +1 -0
  352. package/dist/setupTests.mjs +24 -0
  353. package/dist/setupTests.mjs.map +1 -0
  354. package/dist/types/chat-suggestion-configuration.d.ts +22 -0
  355. package/dist/types/chat-suggestion-configuration.js +19 -0
  356. package/dist/types/chat-suggestion-configuration.js.map +1 -0
  357. package/dist/types/chat-suggestion-configuration.mjs +1 -0
  358. package/dist/types/chat-suggestion-configuration.mjs.map +1 -0
  359. package/dist/types/coagent-action.d.ts +29 -0
  360. package/dist/types/coagent-action.js +19 -0
  361. package/dist/types/coagent-action.js.map +1 -0
  362. package/dist/types/coagent-action.mjs +1 -0
  363. package/dist/types/coagent-action.mjs.map +1 -0
  364. package/dist/types/coagent-state.d.ts +15 -0
  365. package/dist/types/coagent-state.js +19 -0
  366. package/dist/types/coagent-state.js.map +1 -0
  367. package/dist/types/coagent-state.mjs +1 -0
  368. package/dist/types/coagent-state.mjs.map +1 -0
  369. package/dist/types/crew.d.ts +79 -0
  370. package/dist/types/crew.js +19 -0
  371. package/dist/types/crew.js.map +1 -0
  372. package/dist/types/crew.mjs +2 -0
  373. package/dist/types/crew.mjs.map +1 -0
  374. package/dist/types/document-pointer.d.ts +9 -0
  375. package/dist/types/document-pointer.js +19 -0
  376. package/dist/types/document-pointer.js.map +1 -0
  377. package/dist/types/document-pointer.mjs +1 -0
  378. package/dist/types/document-pointer.mjs.map +1 -0
  379. package/dist/types/frontend-action.d.ts +127 -0
  380. package/dist/types/frontend-action.js +53 -0
  381. package/dist/types/frontend-action.js.map +1 -0
  382. package/dist/types/frontend-action.mjs +8 -0
  383. package/dist/types/frontend-action.mjs.map +1 -0
  384. package/dist/types/index.d.ts +12 -0
  385. package/dist/types/index.js +19 -0
  386. package/dist/types/index.js.map +1 -0
  387. package/dist/types/index.mjs +4 -0
  388. package/dist/types/index.mjs.map +1 -0
  389. package/dist/types/interrupt-action.d.ts +10 -0
  390. package/dist/types/interrupt-action.js +19 -0
  391. package/dist/types/interrupt-action.js.map +1 -0
  392. package/dist/types/interrupt-action.mjs +2 -0
  393. package/dist/types/interrupt-action.mjs.map +1 -0
  394. package/dist/types/system-message.d.ts +3 -0
  395. package/dist/types/system-message.js +19 -0
  396. package/dist/types/system-message.js.map +1 -0
  397. package/dist/types/system-message.mjs +1 -0
  398. package/dist/types/system-message.mjs.map +1 -0
  399. package/dist/utils/dev-console.d.ts +3 -0
  400. package/dist/utils/dev-console.js +41 -0
  401. package/dist/utils/dev-console.js.map +1 -0
  402. package/dist/utils/dev-console.mjs +8 -0
  403. package/dist/utils/dev-console.mjs.map +1 -0
  404. package/dist/utils/index.d.ts +2 -0
  405. package/dist/utils/index.js +52 -0
  406. package/dist/utils/index.js.map +1 -0
  407. package/dist/utils/index.mjs +13 -0
  408. package/dist/utils/index.mjs.map +1 -0
  409. package/dist/utils/suggestions-constants.d.ts +9 -0
  410. package/dist/utils/suggestions-constants.js +35 -0
  411. package/dist/utils/suggestions-constants.js.map +1 -0
  412. package/dist/utils/suggestions-constants.mjs +8 -0
  413. package/dist/utils/suggestions-constants.mjs.map +1 -0
  414. package/dist/utils/utils.d.ts +2 -0
  415. package/dist/utils/utils.js +19 -0
  416. package/dist/utils/utils.js.map +1 -0
  417. package/dist/utils/utils.mjs +1 -0
  418. package/dist/utils/utils.mjs.map +1 -0
  419. package/dist/v2/index.css +4 -0
  420. package/dist/v2/index.css.map +1 -0
  421. package/dist/v2/index.d.ts +2 -0
  422. package/dist/v2/index.js +27 -0
  423. package/dist/v2/index.js.map +1 -0
  424. package/dist/v2/index.mjs +6 -0
  425. package/dist/v2/index.mjs.map +1 -0
  426. package/jest.config.js +25 -0
  427. package/package.json +92 -0
  428. package/src/components/CopilotListeners.tsx +81 -0
  429. package/src/components/copilot-provider/__tests__/copilotkit-error.test.tsx +75 -0
  430. package/src/components/copilot-provider/copilot-messages.tsx +274 -0
  431. package/src/components/copilot-provider/copilotkit-props.tsx +169 -0
  432. package/src/components/copilot-provider/copilotkit.tsx +671 -0
  433. package/src/components/copilot-provider/index.ts +3 -0
  434. package/src/components/dev-console/console-trigger.tsx +254 -0
  435. package/src/components/dev-console/developer-console-modal.tsx +866 -0
  436. package/src/components/dev-console/icons.tsx +101 -0
  437. package/src/components/error-boundary/error-boundary.tsx +91 -0
  438. package/src/components/error-boundary/error-utils.tsx +100 -0
  439. package/src/components/index.ts +1 -0
  440. package/src/components/toast/exclamation-mark-icon.tsx +27 -0
  441. package/src/components/toast/toast-provider.tsx +363 -0
  442. package/src/components/usage-banner.tsx +259 -0
  443. package/src/context/coagent-state-renders-context.tsx +76 -0
  444. package/src/context/copilot-context.tsx +332 -0
  445. package/src/context/copilot-messages-context.tsx +35 -0
  446. package/src/context/index.ts +16 -0
  447. package/src/context/threads-context.tsx +41 -0
  448. package/src/hooks/__tests__/use-coagent-config.test.ts +351 -0
  449. package/src/hooks/index.ts +34 -0
  450. package/src/hooks/use-agent-nodename.ts +30 -0
  451. package/src/hooks/use-coagent-state-render-bridge.tsx +293 -0
  452. package/src/hooks/use-coagent-state-render.ts +152 -0
  453. package/src/hooks/use-coagent.ts +366 -0
  454. package/src/hooks/use-configure-chat-suggestions.tsx +86 -0
  455. package/src/hooks/use-copilot-action.ts +236 -0
  456. package/src/hooks/use-copilot-additional-instructions.ts +85 -0
  457. package/src/hooks/use-copilot-authenticated-action.ts +70 -0
  458. package/src/hooks/use-copilot-chat-headless_c.ts +258 -0
  459. package/src/hooks/use-copilot-chat-suggestions.tsx +124 -0
  460. package/src/hooks/use-copilot-chat.ts +130 -0
  461. package/src/hooks/use-copilot-chat_internal.ts +696 -0
  462. package/src/hooks/use-copilot-readable.ts +135 -0
  463. package/src/hooks/use-copilot-runtime-client.ts +164 -0
  464. package/src/hooks/use-default-tool.ts +7 -0
  465. package/src/hooks/use-flat-category-store.ts +105 -0
  466. package/src/hooks/use-frontend-tool.ts +96 -0
  467. package/src/hooks/use-human-in-the-loop.ts +122 -0
  468. package/src/hooks/use-langgraph-interrupt-render.ts +136 -0
  469. package/src/hooks/use-langgraph-interrupt.ts +36 -0
  470. package/src/hooks/use-lazy-tool-renderer.tsx +30 -0
  471. package/src/hooks/use-make-copilot-document-readable.ts +30 -0
  472. package/src/hooks/use-render-tool-call.ts +80 -0
  473. package/src/hooks/use-tree.ts +207 -0
  474. package/src/index.tsx +7 -0
  475. package/src/lib/copilot-task.ts +201 -0
  476. package/src/lib/index.ts +1 -0
  477. package/src/lib/status-checker.ts +64 -0
  478. package/src/setupTests.ts +26 -0
  479. package/src/types/chat-suggestion-configuration.ts +23 -0
  480. package/src/types/coagent-action.ts +31 -0
  481. package/src/types/coagent-state.ts +13 -0
  482. package/src/types/crew.ts +89 -0
  483. package/src/types/document-pointer.ts +7 -0
  484. package/src/types/frontend-action.ts +202 -0
  485. package/src/types/index.ts +17 -0
  486. package/src/types/interrupt-action.ts +43 -0
  487. package/src/types/system-message.ts +4 -0
  488. package/src/utils/dev-console.ts +19 -0
  489. package/src/utils/index.ts +2 -0
  490. package/src/utils/suggestions-constants.ts +8 -0
  491. package/src/utils/utils.test.ts +7 -0
  492. package/src/utils/utils.ts +8 -0
  493. package/src/v2/index.css +1 -0
  494. package/src/v2/index.ts +4 -0
  495. package/tsconfig.json +8 -0
  496. package/tsup.config.ts +16 -0
  497. package/typedoc.json +4 -0
@@ -0,0 +1,351 @@
1
+ import { renderHook, waitFor } from "@testing-library/react";
2
+ import { useCoAgent } from "../use-coagent";
3
+ import type { AgentSubscriber } from "@ag-ui/client";
4
+
5
+ // Mock functions for @copilotkitnext/react
6
+ const mockSetState = jest.fn();
7
+ const mockRunAgent = jest.fn();
8
+ const mockAbortRun = jest.fn();
9
+ const mockSubscribe = jest.fn();
10
+ const mockSetProperties = jest.fn();
11
+
12
+ // Store the last subscriber for triggering events
13
+ let lastSubscriber: AgentSubscriber | null = null;
14
+
15
+ const mockAgent = {
16
+ agentId: "test-agent",
17
+ state: { count: 0 },
18
+ isRunning: false,
19
+ threadId: "thread-123",
20
+ setState: mockSetState,
21
+ runAgent: mockRunAgent,
22
+ abortRun: mockAbortRun,
23
+ subscribe: mockSubscribe.mockImplementation((subscriber: AgentSubscriber) => {
24
+ lastSubscriber = subscriber;
25
+ return {
26
+ unsubscribe: jest.fn(),
27
+ };
28
+ }),
29
+ };
30
+
31
+ jest.mock("@copilotkitnext/react", () => ({
32
+ useAgent: jest.fn(() => ({ agent: mockAgent })),
33
+ useCopilotKit: jest.fn(() => ({
34
+ copilotkit: {
35
+ setProperties: mockSetProperties,
36
+ },
37
+ })),
38
+ }));
39
+
40
+ // Mock other dependencies
41
+ const mockAppendMessage = jest.fn();
42
+ const mockRunChatCompletion = jest.fn();
43
+
44
+ jest.mock("../use-copilot-chat_internal", () => ({
45
+ useCopilotChat: () => ({
46
+ appendMessage: mockAppendMessage,
47
+ runChatCompletion: mockRunChatCompletion,
48
+ }),
49
+ }));
50
+
51
+ jest.mock("../use-copilot-runtime-client", () => ({
52
+ useCopilotRuntimeClient: () => ({
53
+ loadAgentState: jest.fn().mockResolvedValue({
54
+ data: { loadAgentState: { state: "{}", threadExists: false } },
55
+ error: null,
56
+ }),
57
+ }),
58
+ }));
59
+
60
+ jest.mock("../../context", () => ({
61
+ useCopilotContext: () => ({
62
+ availableAgents: [],
63
+ coagentStates: {},
64
+ coagentStatesRef: { current: {} },
65
+ threadId: "test-thread",
66
+ copilotApiConfig: {
67
+ headers: {},
68
+ chatApiEndpoint: "test-endpoint",
69
+ publicApiKey: "test-key",
70
+ },
71
+ showDevConsole: false,
72
+ }),
73
+ useCopilotMessagesContext: () => ({
74
+ messages: [],
75
+ }),
76
+ }));
77
+
78
+ jest.mock("../../components/toast/toast-provider", () => ({
79
+ useToast: () => ({
80
+ setBannerError: jest.fn(),
81
+ }),
82
+ }));
83
+
84
+ jest.mock("../../components/error-boundary/error-utils", () => ({
85
+ useAsyncCallback: (fn: any) => fn,
86
+ }));
87
+
88
+ jest.mock("../../components/copilot-provider/copilot-messages", () => ({
89
+ useMessagesTap: () => ({
90
+ getMessagesFromTap: jest.fn(() => []),
91
+ updateTapMessages: jest.fn(),
92
+ }),
93
+ }));
94
+
95
+ describe("useCoAgent config synchronization", () => {
96
+ beforeEach(() => {
97
+ jest.clearAllMocks();
98
+ lastSubscriber = null;
99
+ });
100
+
101
+ it("should call setProperties when config changes", async () => {
102
+ const { rerender } = renderHook(
103
+ ({ config }) =>
104
+ useCoAgent({
105
+ name: "test-agent",
106
+ initialState: { count: 0 },
107
+ config,
108
+ }),
109
+ {
110
+ initialProps: { config: { configurable: { model: "gpt-4" } } },
111
+ },
112
+ );
113
+
114
+ // Clear the initial calls
115
+ mockSetProperties.mockClear();
116
+
117
+ // Change config
118
+ rerender({ config: { configurable: { model: "gpt-4o" } } });
119
+
120
+ // Wait for effect to complete and verify setProperties was called
121
+ await waitFor(() => {
122
+ expect(mockSetProperties).toHaveBeenCalledWith({
123
+ configurable: { model: "gpt-4o" },
124
+ });
125
+ });
126
+ });
127
+
128
+ it("should not call setProperties when config is unchanged", () => {
129
+ const config = { configurable: { model: "gpt-4" } };
130
+
131
+ const { rerender } = renderHook(
132
+ ({ config }) =>
133
+ useCoAgent({
134
+ name: "test-agent",
135
+ initialState: { count: 0 },
136
+ config,
137
+ }),
138
+ {
139
+ initialProps: { config },
140
+ },
141
+ );
142
+
143
+ // Clear the initial calls
144
+ mockSetProperties.mockClear();
145
+
146
+ // Re-render with same config reference
147
+ rerender({ config });
148
+
149
+ // Should not have called setProperties
150
+ expect(mockSetProperties).not.toHaveBeenCalled();
151
+ });
152
+
153
+ it("should handle backward compatibility with configurable prop", async () => {
154
+ const { rerender } = renderHook(
155
+ ({ configurable }) =>
156
+ useCoAgent({
157
+ name: "test-agent",
158
+ initialState: { count: 0 },
159
+ configurable,
160
+ }),
161
+ {
162
+ initialProps: { configurable: { model: "gpt-4" } },
163
+ },
164
+ );
165
+
166
+ // Clear the initial calls
167
+ mockSetProperties.mockClear();
168
+
169
+ // Change configurable prop
170
+ rerender({ configurable: { model: "gpt-4o" } });
171
+
172
+ // Wait for effect to complete and verify setProperties was called
173
+ await waitFor(() => {
174
+ expect(mockSetProperties).toHaveBeenCalledWith({
175
+ configurable: { model: "gpt-4o" },
176
+ });
177
+ });
178
+ });
179
+
180
+ it("should not call setProperties when both config and configurable are undefined", () => {
181
+ renderHook(() =>
182
+ useCoAgent({
183
+ name: "test-agent",
184
+ initialState: { count: 0 },
185
+ }),
186
+ );
187
+
188
+ // Should not have called setProperties
189
+ expect(mockSetProperties).not.toHaveBeenCalled();
190
+ });
191
+
192
+ it("should handle deeply nested config changes", async () => {
193
+ const { rerender } = renderHook(
194
+ ({ config }) =>
195
+ useCoAgent({
196
+ name: "test-agent",
197
+ initialState: { count: 0 },
198
+ config,
199
+ }),
200
+ {
201
+ initialProps: {
202
+ config: {
203
+ configurable: {
204
+ model: "gpt-4",
205
+ settings: { temperature: 0.5 },
206
+ },
207
+ },
208
+ },
209
+ },
210
+ );
211
+
212
+ // Clear the initial calls
213
+ mockSetProperties.mockClear();
214
+
215
+ // Change nested config
216
+ rerender({
217
+ config: {
218
+ configurable: {
219
+ model: "gpt-4",
220
+ settings: { temperature: 0.7 }, // Only nested property changed
221
+ },
222
+ },
223
+ });
224
+
225
+ // Wait for effect to complete and verify setProperties was called
226
+ await waitFor(() => {
227
+ expect(mockSetProperties).toHaveBeenCalledWith({
228
+ configurable: {
229
+ model: "gpt-4",
230
+ settings: { temperature: 0.7 },
231
+ },
232
+ });
233
+ });
234
+ });
235
+
236
+ describe("State Management", () => {
237
+ // Helper to create mock subscriber params
238
+ const createMockParams = (stateOverride: any = {}) => ({
239
+ messages: [],
240
+ state: stateOverride,
241
+ agent: mockAgent as any,
242
+ input: {} as any,
243
+ });
244
+
245
+ it("should initialize agent state via onRunInitialized event", () => {
246
+ // Set agent to have NO state (empty object)
247
+ mockAgent.state = {} as any;
248
+
249
+ renderHook(() =>
250
+ useCoAgent({
251
+ name: "test-agent",
252
+ initialState: { count: 42 },
253
+ }),
254
+ );
255
+
256
+ // Verify subscription was created
257
+ expect(mockSubscribe).toHaveBeenCalled();
258
+ expect(lastSubscriber).toBeTruthy();
259
+
260
+ // Clear any initial state calls
261
+ mockSetState.mockClear();
262
+
263
+ // Trigger onRunInitialized with no run state
264
+ lastSubscriber?.onRunInitialized?.(createMockParams({}));
265
+
266
+ // Should set state to initialState
267
+ expect(mockSetState).toHaveBeenCalledWith({ count: 42 });
268
+
269
+ // Reset agent state
270
+ mockAgent.state = { count: 0 };
271
+ });
272
+
273
+ it("should preserve existing agent state on onRunInitialized", () => {
274
+ // Set agent to have existing state
275
+ mockAgent.state = { count: 100 };
276
+
277
+ renderHook(() =>
278
+ useCoAgent({
279
+ name: "test-agent",
280
+ initialState: { count: 42 },
281
+ }),
282
+ );
283
+
284
+ // Clear any initial state calls
285
+ mockSetState.mockClear();
286
+
287
+ // Trigger onRunInitialized with no new state
288
+ lastSubscriber?.onRunInitialized?.(createMockParams({}));
289
+
290
+ // Should NOT override existing state
291
+ expect(mockSetState).not.toHaveBeenCalled();
292
+
293
+ // Reset agent state
294
+ mockAgent.state = { count: 0 };
295
+ });
296
+
297
+ it("should prioritize run state over initialState", () => {
298
+ renderHook(() =>
299
+ useCoAgent({
300
+ name: "test-agent",
301
+ initialState: { count: 42 },
302
+ }),
303
+ );
304
+
305
+ // Clear any initial state calls
306
+ mockSetState.mockClear();
307
+
308
+ // Trigger onRunInitialized with state from the run
309
+ lastSubscriber?.onRunInitialized?.(createMockParams({ count: 999 }));
310
+
311
+ // Should use run state, not initialState
312
+ expect(mockSetState).toHaveBeenCalledWith({ count: 999 });
313
+ });
314
+
315
+ it("should handle setState with object updates", () => {
316
+ const { result } = renderHook(() =>
317
+ useCoAgent({
318
+ name: "test-agent",
319
+ initialState: { count: 0 },
320
+ }),
321
+ );
322
+
323
+ // Update state with object
324
+ result.current.setState({ count: 5 });
325
+
326
+ // Should merge with existing state
327
+ expect(mockSetState).toHaveBeenCalledWith({ count: 5 });
328
+ });
329
+
330
+ it("should handle setState with function updaters", () => {
331
+ // Set current agent state
332
+ mockAgent.state = { count: 10 };
333
+
334
+ const { result } = renderHook(() =>
335
+ useCoAgent({
336
+ name: "test-agent",
337
+ initialState: { count: 0 },
338
+ }),
339
+ );
340
+
341
+ // Update state with function
342
+ result.current.setState((prev) => ({ count: (prev?.count || 0) + 5 }));
343
+
344
+ // Should call function with current state and set result
345
+ expect(mockSetState).toHaveBeenCalledWith({ count: 15 });
346
+
347
+ // Reset agent state
348
+ mockAgent.state = { count: 0 };
349
+ });
350
+ });
351
+ });
@@ -0,0 +1,34 @@
1
+ export { useCopilotChat } from "./use-copilot-chat";
2
+ export type { UseCopilotChatReturn } from "./use-copilot-chat";
3
+ export type { UseCopilotChatOptions } from "./use-copilot-chat_internal";
4
+ export {
5
+ type UseCopilotChatReturn_c,
6
+ type UseCopilotChatOptions_c,
7
+ useCopilotChatHeadless_c,
8
+ } from "./use-copilot-chat-headless_c";
9
+ export {
10
+ useCopilotChatInternal,
11
+ type ChatSuggestions,
12
+ type OnReloadMessages,
13
+ type OnStopGeneration,
14
+ } from "./use-copilot-chat_internal";
15
+ export { useCopilotAction } from "./use-copilot-action";
16
+ export { useCoAgentStateRender } from "./use-coagent-state-render";
17
+ export { useMakeCopilotDocumentReadable } from "./use-make-copilot-document-readable";
18
+ export { useCopilotReadable } from "./use-copilot-readable";
19
+ export { useCoAgent, type HintFunction } from "./use-coagent";
20
+ export { useCopilotRuntimeClient } from "./use-copilot-runtime-client";
21
+ export { useCopilotAuthenticatedAction_c } from "./use-copilot-authenticated-action";
22
+ export { useLangGraphInterrupt } from "./use-langgraph-interrupt";
23
+ export { useLangGraphInterruptRender } from "./use-langgraph-interrupt-render";
24
+ export { useCopilotAdditionalInstructions } from "./use-copilot-additional-instructions";
25
+ export type { Tree, TreeNode } from "./use-tree";
26
+ export { useFrontendTool } from "./use-frontend-tool";
27
+ export { useHumanInTheLoop } from "./use-human-in-the-loop";
28
+ export { useRenderToolCall } from "./use-render-tool-call";
29
+ export { useDefaultTool } from "./use-default-tool";
30
+ export { useLazyToolRenderer } from "./use-lazy-tool-renderer";
31
+ export {
32
+ useCopilotChatSuggestions,
33
+ type UseCopilotChatSuggestionsConfiguration,
34
+ } from "./use-copilot-chat-suggestions";
@@ -0,0 +1,30 @@
1
+ import { useEffect, useRef } from "react";
2
+ import type { AgentSubscriber } from "@ag-ui/client";
3
+ import { useAgent } from "@copilotkitnext/react";
4
+
5
+ export function useAgentNodeName(agentName?: string) {
6
+ const { agent } = useAgent({ agentId: agentName });
7
+ const nodeNameRef = useRef<string>("start");
8
+
9
+ useEffect(() => {
10
+ if (!agent) return;
11
+ const subscriber: AgentSubscriber = {
12
+ onStepStartedEvent: ({ event }) => {
13
+ nodeNameRef.current = event.stepName;
14
+ },
15
+ onRunStartedEvent: () => {
16
+ nodeNameRef.current = "start";
17
+ },
18
+ onRunFinishedEvent: () => {
19
+ nodeNameRef.current = "end";
20
+ },
21
+ };
22
+
23
+ const subscription = agent.subscribe(subscriber);
24
+ return () => {
25
+ subscription.unsubscribe();
26
+ };
27
+ }, [agent]);
28
+
29
+ return nodeNameRef.current;
30
+ }
@@ -0,0 +1,293 @@
1
+ import { ReactCustomMessageRendererPosition, useAgent } from "@copilotkitnext/react";
2
+ import { useCallback, useEffect, useMemo, useState } from "react";
3
+ import type { AgentSubscriber } from "@ag-ui/client";
4
+ import { useCoAgentStateRenders } from "../context";
5
+ import { dataToUUID, parseJson } from "@copilotkit/shared";
6
+
7
+ function getStateWithoutConstantKeys(state: any) {
8
+ if (!state) return {};
9
+ const { messages, tools, copilotkit, ...stateWithoutConstantKeys } = state;
10
+ return stateWithoutConstantKeys;
11
+ }
12
+
13
+ // Function that compares states, without the constant keys
14
+ function areStatesEquals(a: any, b: any) {
15
+ if ((a && !b) || (!a && b)) return false;
16
+ const { messages, tools, copilotkit, ...aWithoutConstantKeys } = a;
17
+ const {
18
+ messages: bMessages,
19
+ tools: bTools,
20
+ copilotkit: bCopilotkit,
21
+ ...bWithoutConstantKeys
22
+ } = b;
23
+
24
+ return JSON.stringify(aWithoutConstantKeys) === JSON.stringify(bWithoutConstantKeys);
25
+ }
26
+
27
+ /**
28
+ * Bridge hook that connects agent state renders to chat messages.
29
+ *
30
+ * ## Purpose
31
+ * This hook finds matching state render configurations (registered via useCoAgentStateRender)
32
+ * and returns UI to render in chat.
33
+ * It ensures each state render appears bound to a specific message, preventing duplicates while
34
+ * allowing re-binding when the underlying state changes significantly.
35
+ *
36
+ * ## Message-ID-Based Claiming System
37
+ *
38
+ * ### The Problem
39
+ * Multiple bridge component instances render simultaneously (one per message). Without coordination,
40
+ * they would all try to render the same state render, causing duplicates.
41
+ *
42
+ * ### The Solution: Message-ID Claims with State Comparison
43
+ * Each state render is "claimed" by exactly one **message ID** (not runId):
44
+ *
45
+ * **Claim Structure**: `claimsRef.current[messageId] = { stateRenderId, runId, stateSnapshot, locked }`
46
+ *
47
+ * **Primary binding is by messageId because**:
48
+ * - runId is not always available immediately (starts as "pending")
49
+ * - messageId is the stable identifier throughout the message lifecycle
50
+ * - Claims persist across component remounts via context ref
51
+ *
52
+ * ### Claiming Logic Flow
53
+ *
54
+ * 1. **Message already has a claim**:
55
+ * - Check if the claim matches the current stateRenderId
56
+ * - If yes → render (this message owns this render)
57
+ * - Update runId if it was "pending" and now available
58
+ *
59
+ * 2. **State render claimed by another message**:
60
+ * - Compare state snapshots (ignoring constant keys: messages, tools, copilotkit)
61
+ * - If states are identical → block rendering (duplicate)
62
+ * - **If states are different → allow claiming** (new data, new message)
63
+ * - This handles cases where the same render type shows different states in different messages
64
+ *
65
+ * 3. **Unclaimed state render**:
66
+ * - Only allow claiming if runId is "pending" (initial render)
67
+ * - If runId is real but no claim exists → block (edge case protection)
68
+ * - Create new claim: `claimsRef.current[messageId] = { stateRenderId, runId }`
69
+ *
70
+ * ### State Snapshot Locking
71
+ *
72
+ * Once a state snapshot is captured and locked for a message:
73
+ * - The UI always renders with the locked snapshot (not live agent.state)
74
+ * - Prevents UI from appearing "wiped" during state transitions
75
+ * - Locked when: stateSnapshot prop is available (from message persistence)
76
+ * - Unlocked state: can still update from live agent.state
77
+ *
78
+ * ### Synchronous Claiming (Ref-based)
79
+ *
80
+ * Claims are stored in a context-level ref (not React state):
81
+ * - Multiple bridges render in the same tick
82
+ * - State updates are async - would allow duplicates before update completes
83
+ * - Ref provides immediate, synchronous claim checking
84
+ * - Survives component remounts (stored in context, not component)
85
+ *
86
+ * ## Flow Example
87
+ *
88
+ * ```
89
+ * Time 1: Message A renders, runId=undefined, state={progress: 50%}
90
+ * → effectiveRunId = "pending"
91
+ * → Claims: claimsRef["msgA"] = { stateRenderId: "tasks", runId: "pending", stateSnapshot: {progress: 50%} }
92
+ * → Renders UI with 50% progress
93
+ *
94
+ * Time 2: Message B renders, runId=undefined, same state
95
+ * → Checks: "tasks" already claimed by msgA with same state
96
+ * → Returns null (blocked - duplicate)
97
+ *
98
+ * Time 3: Real runId appears (e.g., "run-123")
99
+ * → Updates claim: claimsRef["msgA"].runId = "run-123"
100
+ * → Message A continues rendering
101
+ *
102
+ * Time 4: Agent processes more, state={progress: 100%}
103
+ * → Message A: locked to 50% (stateSnapshot locked)
104
+ * → Message C renders with state={progress: 100%}
105
+ * → Checks: "tasks" claimed by msgA but state is DIFFERENT (50% vs 100%)
106
+ * → Allows new claim: claimsRef["msgC"] = { stateRenderId: "tasks", runId: "run-123", stateSnapshot: {progress: 100%} }
107
+ * → Both messages render independently with their own snapshots
108
+ * ```
109
+ */
110
+ export interface CoAgentStateRenderBridgeProps {
111
+ message: any;
112
+ position: ReactCustomMessageRendererPosition;
113
+ runId: string;
114
+ messageIndex: number;
115
+ messageIndexInRun: number;
116
+ numberOfMessagesInRun: number;
117
+ agentId: string;
118
+ stateSnapshot: any;
119
+ }
120
+
121
+ export function useCoagentStateRenderBridge(agentId: string, props: CoAgentStateRenderBridgeProps) {
122
+ const { stateSnapshot, messageIndexInRun, message } = props;
123
+ const { coAgentStateRenders, claimsRef } = useCoAgentStateRenders();
124
+ const { agent } = useAgent({ agentId });
125
+ const [nodeName, setNodeName] = useState<string | undefined>(undefined);
126
+
127
+ const runId = props.runId ?? message.runId;
128
+ const effectiveRunId = runId || "pending";
129
+
130
+ useEffect(() => {
131
+ if (!agent) return;
132
+ const subscriber: AgentSubscriber = {
133
+ onStepStartedEvent: ({ event }) => {
134
+ if (event.stepName !== nodeName) {
135
+ setNodeName(event.stepName);
136
+ }
137
+ },
138
+ onStepFinishedEvent: ({ event }) => {
139
+ if (event.stepName === nodeName) {
140
+ setNodeName(undefined);
141
+ }
142
+ },
143
+ };
144
+
145
+ const { unsubscribe } = agent.subscribe(subscriber);
146
+ return () => {
147
+ unsubscribe();
148
+ };
149
+ // eslint-disable-next-line react-hooks/exhaustive-deps
150
+ }, [agentId, nodeName]);
151
+
152
+ const getStateRender = useCallback(
153
+ (messageId: string) => {
154
+ return Object.entries(coAgentStateRenders).find(([stateRenderId, stateRender]) => {
155
+ if (claimsRef.current[messageId]) {
156
+ return stateRenderId === claimsRef.current[messageId].stateRenderId;
157
+ }
158
+ const matchingAgentName = stateRender.name === agentId;
159
+ const matchesNodeContext = stateRender.nodeName ? stateRender.nodeName === nodeName : true;
160
+ return matchingAgentName && matchesNodeContext;
161
+ });
162
+ },
163
+ [coAgentStateRenders, nodeName, agentId],
164
+ );
165
+
166
+ // Message ID-based claim system - A state render can only be claimed by one message ID
167
+ const handleRenderRequest = ({
168
+ stateRenderId,
169
+ messageId,
170
+ runId,
171
+ stateSnapshot: renderSnapshot,
172
+ }: {
173
+ stateRenderId: string;
174
+ messageId: string;
175
+ runId?: string;
176
+ stateSnapshot?: any;
177
+ }): boolean => {
178
+ // Check if this message has already claimed this state render
179
+ if (claimsRef.current[messageId]) {
180
+ const canRender = claimsRef.current[messageId].stateRenderId === stateRenderId;
181
+
182
+ // Update runId if it doesn't exist
183
+ if (
184
+ canRender &&
185
+ runId &&
186
+ (!claimsRef.current[messageId].runId || claimsRef.current[messageId].runId === "pending")
187
+ ) {
188
+ claimsRef.current[messageId].runId = runId;
189
+ }
190
+
191
+ return canRender;
192
+ }
193
+
194
+ // Do not allow render if any other message has claimed this state render
195
+ const renderClaimedByOtherMessage = Object.values(claimsRef.current).find(
196
+ (c) =>
197
+ c.stateRenderId === stateRenderId &&
198
+ dataToUUID(getStateWithoutConstantKeys(c.stateSnapshot)) ===
199
+ dataToUUID(getStateWithoutConstantKeys(renderSnapshot)),
200
+ );
201
+ if (renderClaimedByOtherMessage) {
202
+ // If:
203
+ // - state render already claimed
204
+ // - snapshot exists in the claiming object and is different from current,
205
+ if (
206
+ renderSnapshot &&
207
+ renderClaimedByOtherMessage.stateSnapshot &&
208
+ !areStatesEquals(renderClaimedByOtherMessage.stateSnapshot, renderSnapshot)
209
+ ) {
210
+ claimsRef.current[messageId] = { stateRenderId, runId };
211
+ return true;
212
+ }
213
+ return false;
214
+ }
215
+
216
+ // No existing claim anywhere yet – allow this message to claim even if we already know the runId.
217
+ if (!runId) {
218
+ return false;
219
+ }
220
+
221
+ claimsRef.current[messageId] = { stateRenderId, runId };
222
+ return true;
223
+ };
224
+
225
+ return useMemo(() => {
226
+ if (messageIndexInRun !== 0) {
227
+ return null;
228
+ }
229
+
230
+ const [stateRenderId, stateRender] = getStateRender(message.id) ?? [];
231
+
232
+ if (!stateRender || !stateRenderId) {
233
+ return null;
234
+ }
235
+
236
+ // Is there any state we can use?
237
+ const snapshot = stateSnapshot ? parseJson(stateSnapshot, stateSnapshot) : agent?.state;
238
+
239
+ // Synchronously check/claim - returns true if this message can render
240
+ const canRender = handleRenderRequest({
241
+ stateRenderId,
242
+ messageId: message.id,
243
+ runId: effectiveRunId,
244
+ stateSnapshot: snapshot,
245
+ });
246
+ if (!canRender) {
247
+ return null;
248
+ }
249
+
250
+ // If we found state, and given that now there's a claim for the current message, let's save it in the claim
251
+ if (snapshot && !claimsRef.current[message.id].locked) {
252
+ if (stateSnapshot) {
253
+ claimsRef.current[message.id].stateSnapshot = snapshot;
254
+ claimsRef.current[message.id].locked = true;
255
+ } else {
256
+ claimsRef.current[message.id].stateSnapshot = snapshot;
257
+ }
258
+ }
259
+
260
+ if (stateRender.handler) {
261
+ stateRender.handler({
262
+ state: stateSnapshot ? parseJson(stateSnapshot, stateSnapshot) : (agent?.state ?? {}),
263
+ nodeName: nodeName ?? "",
264
+ });
265
+ }
266
+
267
+ if (stateRender.render) {
268
+ const status = agent?.isRunning ? "inProgress" : "complete";
269
+
270
+ if (typeof stateRender.render === "string") return stateRender.render;
271
+
272
+ return stateRender.render({
273
+ status,
274
+ // Always use state from claim, to make sure the state does not seem "wiped" for a fraction of a second
275
+ state: claimsRef.current[message.id].stateSnapshot ?? {},
276
+ nodeName: nodeName ?? "",
277
+ });
278
+ }
279
+ }, [
280
+ getStateRender,
281
+ stateSnapshot,
282
+ agent?.state,
283
+ agent?.isRunning,
284
+ nodeName,
285
+ effectiveRunId,
286
+ message.id,
287
+ messageIndexInRun,
288
+ ]);
289
+ }
290
+
291
+ export function CoAgentStateRenderBridge(props: CoAgentStateRenderBridgeProps) {
292
+ return useCoagentStateRenderBridge(props.agentId, props);
293
+ }