@athenaintel/react 0.57.2 → 0.60.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (852) hide show
  1. package/README.md +795 -12
  2. package/dist/agent-runtime/src/addressed-agents.cjs +16 -0
  3. package/dist/agent-runtime/src/addressed-agents.cjs.map +1 -0
  4. package/dist/agent-runtime/src/addressed-agents.d.ts +30 -0
  5. package/dist/agent-runtime/src/addressed-agents.js +16 -0
  6. package/dist/agent-runtime/src/addressed-agents.js.map +1 -0
  7. package/dist/agent-runtime/src/answer-label.cjs +4 -3
  8. package/dist/agent-runtime/src/answer-label.cjs.map +1 -1
  9. package/dist/agent-runtime/src/answer-label.d.ts +13 -6
  10. package/dist/agent-runtime/src/answer-label.js +4 -3
  11. package/dist/agent-runtime/src/answer-label.js.map +1 -1
  12. package/dist/agent-runtime/src/chat-outbox-attachments.cjs.map +1 -1
  13. package/dist/agent-runtime/src/chat-outbox-attachments.d.ts +1 -1
  14. package/dist/agent-runtime/src/chat-outbox-attachments.js.map +1 -1
  15. package/dist/agent-runtime/src/chat-outbox-entry.cjs +101 -0
  16. package/dist/agent-runtime/src/chat-outbox-entry.cjs.map +1 -0
  17. package/dist/agent-runtime/src/chat-outbox-entry.d.ts +99 -0
  18. package/dist/agent-runtime/src/chat-outbox-entry.js +101 -0
  19. package/dist/agent-runtime/src/chat-outbox-entry.js.map +1 -0
  20. package/dist/agent-runtime/src/chat-outbox-legacy.cjs +252 -0
  21. package/dist/agent-runtime/src/chat-outbox-legacy.cjs.map +1 -0
  22. package/dist/agent-runtime/src/chat-outbox-legacy.d.ts +96 -0
  23. package/dist/agent-runtime/src/chat-outbox-legacy.js +252 -0
  24. package/dist/agent-runtime/src/chat-outbox-legacy.js.map +1 -0
  25. package/dist/agent-runtime/src/chat-outbox-policy.cjs +30 -0
  26. package/dist/agent-runtime/src/chat-outbox-policy.cjs.map +1 -0
  27. package/dist/agent-runtime/src/chat-outbox-policy.d.ts +42 -0
  28. package/dist/agent-runtime/src/chat-outbox-policy.js +30 -0
  29. package/dist/agent-runtime/src/chat-outbox-policy.js.map +1 -0
  30. package/dist/agent-runtime/src/chat-outbox-storage.cjs +306 -0
  31. package/dist/agent-runtime/src/chat-outbox-storage.cjs.map +1 -0
  32. package/dist/agent-runtime/src/chat-outbox-storage.d.ts +194 -0
  33. package/dist/agent-runtime/src/chat-outbox-storage.js +306 -0
  34. package/dist/agent-runtime/src/chat-outbox-storage.js.map +1 -0
  35. package/dist/agent-runtime/src/chat-outbox-thread.cjs +21 -94
  36. package/dist/agent-runtime/src/chat-outbox-thread.cjs.map +1 -1
  37. package/dist/agent-runtime/src/chat-outbox-thread.d.ts +22 -18
  38. package/dist/agent-runtime/src/chat-outbox-thread.js +21 -94
  39. package/dist/agent-runtime/src/chat-outbox-thread.js.map +1 -1
  40. package/dist/agent-runtime/src/chat-outbox.cjs +492 -547
  41. package/dist/agent-runtime/src/chat-outbox.cjs.map +1 -1
  42. package/dist/agent-runtime/src/chat-outbox.d.ts +110 -142
  43. package/dist/agent-runtime/src/chat-outbox.js +492 -547
  44. package/dist/agent-runtime/src/chat-outbox.js.map +1 -1
  45. package/dist/agent-runtime/src/composer-markdown.cjs +0 -16
  46. package/dist/agent-runtime/src/composer-markdown.cjs.map +1 -1
  47. package/dist/agent-runtime/src/composer-markdown.d.ts +1 -1
  48. package/dist/agent-runtime/src/composer-markdown.js +1 -17
  49. package/dist/agent-runtime/src/composer-markdown.js.map +1 -1
  50. package/dist/agent-runtime/src/deep-agent-transport-recipe.cjs +3 -1
  51. package/dist/agent-runtime/src/deep-agent-transport-recipe.cjs.map +1 -1
  52. package/dist/agent-runtime/src/deep-agent-transport-recipe.d.ts +8 -1
  53. package/dist/agent-runtime/src/deep-agent-transport-recipe.js +3 -1
  54. package/dist/agent-runtime/src/deep-agent-transport-recipe.js.map +1 -1
  55. package/dist/agent-runtime/src/dictation-preferences.d.ts +356 -0
  56. package/dist/agent-runtime/src/dictation-record.d.ts +279 -0
  57. package/dist/agent-runtime/src/dictation-session.d.ts +106 -7
  58. package/dist/agent-runtime/src/dictation-snippets.d.ts +9 -0
  59. package/dist/agent-runtime/src/dictation-transfer.d.ts +142 -0
  60. package/dist/agent-runtime/src/edit-command.cjs.map +1 -1
  61. package/dist/agent-runtime/src/edit-command.d.ts +1 -1
  62. package/dist/agent-runtime/src/edit-command.js.map +1 -1
  63. package/dist/agent-runtime/src/errors.cjs +1 -0
  64. package/dist/agent-runtime/src/errors.cjs.map +1 -1
  65. package/dist/agent-runtime/src/errors.js +1 -0
  66. package/dist/agent-runtime/src/errors.js.map +1 -1
  67. package/dist/agent-runtime/src/generated/runconfig-contract.cjs +24 -0
  68. package/dist/agent-runtime/src/generated/runconfig-contract.cjs.map +1 -1
  69. package/dist/agent-runtime/src/generated/runconfig-contract.d.ts +3 -3
  70. package/dist/agent-runtime/src/generated/runconfig-contract.js +24 -0
  71. package/dist/agent-runtime/src/generated/runconfig-contract.js.map +1 -1
  72. package/dist/agent-runtime/src/index.d.ts +14 -8
  73. package/dist/agent-runtime/src/lane-follow.cjs +289 -0
  74. package/dist/agent-runtime/src/lane-follow.cjs.map +1 -0
  75. package/dist/agent-runtime/src/lane-follow.js +289 -0
  76. package/dist/agent-runtime/src/lane-follow.js.map +1 -0
  77. package/dist/agent-runtime/src/lane-images.cjs +387 -0
  78. package/dist/agent-runtime/src/lane-images.cjs.map +1 -0
  79. package/dist/agent-runtime/src/lane-images.js +387 -0
  80. package/dist/agent-runtime/src/lane-images.js.map +1 -0
  81. package/dist/agent-runtime/src/message-window.js +1 -1
  82. package/dist/agent-runtime/src/messages.cjs +19 -1
  83. package/dist/agent-runtime/src/messages.cjs.map +1 -1
  84. package/dist/agent-runtime/src/messages.d.ts +8 -0
  85. package/dist/agent-runtime/src/messages.js +21 -3
  86. package/dist/agent-runtime/src/messages.js.map +1 -1
  87. package/dist/agent-runtime/src/named-agents.cjs +301 -0
  88. package/dist/agent-runtime/src/named-agents.cjs.map +1 -0
  89. package/dist/agent-runtime/src/named-agents.d.ts +246 -0
  90. package/dist/agent-runtime/src/named-agents.js +301 -0
  91. package/dist/agent-runtime/src/named-agents.js.map +1 -0
  92. package/dist/agent-runtime/src/offline-status.cjs.map +1 -1
  93. package/dist/agent-runtime/src/offline-status.d.ts +93 -2
  94. package/dist/agent-runtime/src/offline-status.js.map +1 -1
  95. package/dist/agent-runtime/src/ptc-subcalls.cjs +41 -0
  96. package/dist/agent-runtime/src/ptc-subcalls.cjs.map +1 -0
  97. package/dist/agent-runtime/src/ptc-subcalls.js +41 -0
  98. package/dist/agent-runtime/src/ptc-subcalls.js.map +1 -0
  99. package/dist/agent-runtime/src/queue.cjs +2 -2
  100. package/dist/agent-runtime/src/queue.cjs.map +1 -1
  101. package/dist/agent-runtime/src/queue.d.ts +20 -25
  102. package/dist/agent-runtime/src/queue.js +2 -2
  103. package/dist/agent-runtime/src/queue.js.map +1 -1
  104. package/dist/agent-runtime/src/quota-safe-local-storage-session.cjs +314 -84
  105. package/dist/agent-runtime/src/quota-safe-local-storage-session.cjs.map +1 -1
  106. package/dist/agent-runtime/src/quota-safe-local-storage-session.d.ts +137 -40
  107. package/dist/agent-runtime/src/quota-safe-local-storage-session.js +318 -88
  108. package/dist/agent-runtime/src/quota-safe-local-storage-session.js.map +1 -1
  109. package/dist/agent-runtime/src/run-send.cjs +54 -0
  110. package/dist/agent-runtime/src/run-send.cjs.map +1 -0
  111. package/dist/agent-runtime/src/run-send.d.ts +51 -0
  112. package/dist/agent-runtime/src/run-send.js +54 -0
  113. package/dist/agent-runtime/src/run-send.js.map +1 -0
  114. package/dist/agent-runtime/src/running-tool-placeholder.cjs +6 -0
  115. package/dist/agent-runtime/src/running-tool-placeholder.cjs.map +1 -1
  116. package/dist/agent-runtime/src/running-tool-placeholder.js +6 -0
  117. package/dist/agent-runtime/src/running-tool-placeholder.js.map +1 -1
  118. package/dist/agent-runtime/src/runtime.d.ts +9 -5
  119. package/dist/agent-runtime/src/sealed-idb.cjs +64 -0
  120. package/dist/agent-runtime/src/sealed-idb.cjs.map +1 -1
  121. package/dist/agent-runtime/src/sealed-idb.d.ts +16 -0
  122. package/dist/agent-runtime/src/sealed-idb.js +64 -0
  123. package/dist/agent-runtime/src/sealed-idb.js.map +1 -1
  124. package/dist/agent-runtime/src/send-recovery.cjs +90 -118
  125. package/dist/agent-runtime/src/send-recovery.cjs.map +1 -1
  126. package/dist/agent-runtime/src/send-recovery.d.ts +25 -29
  127. package/dist/agent-runtime/src/send-recovery.js +90 -118
  128. package/dist/agent-runtime/src/send-recovery.js.map +1 -1
  129. package/dist/agent-runtime/src/statewire-diagnostics.d.ts +4 -1
  130. package/dist/agent-runtime/src/statewire-held-sends.cjs +191 -0
  131. package/dist/agent-runtime/src/statewire-held-sends.cjs.map +1 -0
  132. package/dist/agent-runtime/src/statewire-held-sends.d.ts +119 -0
  133. package/dist/agent-runtime/src/statewire-held-sends.js +191 -0
  134. package/dist/agent-runtime/src/statewire-held-sends.js.map +1 -0
  135. package/dist/agent-runtime/src/statewire-state.cjs +4 -0
  136. package/dist/agent-runtime/src/statewire-state.cjs.map +1 -1
  137. package/dist/agent-runtime/src/statewire-state.js +4 -0
  138. package/dist/agent-runtime/src/statewire-state.js.map +1 -1
  139. package/dist/agent-runtime/src/statewire-transport.cjs +8 -2
  140. package/dist/agent-runtime/src/statewire-transport.cjs.map +1 -1
  141. package/dist/agent-runtime/src/statewire-transport.d.ts +14 -5
  142. package/dist/agent-runtime/src/statewire-transport.js +8 -2
  143. package/dist/agent-runtime/src/statewire-transport.js.map +1 -1
  144. package/dist/agent-runtime/src/subagent-transcripts.cjs +1 -23
  145. package/dist/agent-runtime/src/subagent-transcripts.cjs.map +1 -1
  146. package/dist/agent-runtime/src/subagent-transcripts.js +3 -25
  147. package/dist/agent-runtime/src/subagent-transcripts.js.map +1 -1
  148. package/dist/agent-runtime/src/subagents.cjs +22 -29
  149. package/dist/agent-runtime/src/subagents.cjs.map +1 -1
  150. package/dist/agent-runtime/src/subagents.js +23 -30
  151. package/dist/agent-runtime/src/subagents.js.map +1 -1
  152. package/dist/agent-runtime/src/thread-extras.cjs +27 -19
  153. package/dist/agent-runtime/src/thread-extras.cjs.map +1 -1
  154. package/dist/agent-runtime/src/thread-extras.d.ts +19 -6
  155. package/dist/agent-runtime/src/thread-extras.js +27 -19
  156. package/dist/agent-runtime/src/thread-extras.js.map +1 -1
  157. package/dist/agent-runtime/src/thread-handoff-flow-machine.d.ts +8 -8
  158. package/dist/agent-runtime/src/tool-metadata.cjs +19 -0
  159. package/dist/agent-runtime/src/tool-metadata.cjs.map +1 -1
  160. package/dist/agent-runtime/src/tool-metadata.js +19 -0
  161. package/dist/agent-runtime/src/tool-metadata.js.map +1 -1
  162. package/dist/agent-runtime/src/tool-names.cjs +21 -0
  163. package/dist/agent-runtime/src/tool-names.cjs.map +1 -1
  164. package/dist/agent-runtime/src/tool-names.d.ts +8 -0
  165. package/dist/agent-runtime/src/tool-names.js +21 -0
  166. package/dist/agent-runtime/src/tool-names.js.map +1 -1
  167. package/dist/agent-runtime/src/typed-interrupt-kinds.cjs +247 -0
  168. package/dist/agent-runtime/src/typed-interrupt-kinds.cjs.map +1 -0
  169. package/dist/agent-runtime/src/typed-interrupt-kinds.d.ts +173 -0
  170. package/dist/agent-runtime/src/typed-interrupt-kinds.js +247 -0
  171. package/dist/agent-runtime/src/typed-interrupt-kinds.js.map +1 -0
  172. package/dist/agent-runtime/src/typed-interrupts.cjs +48 -0
  173. package/dist/agent-runtime/src/typed-interrupts.cjs.map +1 -0
  174. package/dist/agent-runtime/src/typed-interrupts.d.ts +75 -0
  175. package/dist/agent-runtime/src/typed-interrupts.js +48 -0
  176. package/dist/agent-runtime/src/typed-interrupts.js.map +1 -0
  177. package/dist/agent-runtime/src/types.d.ts +1 -1
  178. package/dist/agent-runtime/src/use-conversation-list.cjs +1 -0
  179. package/dist/agent-runtime/src/use-conversation-list.cjs.map +1 -1
  180. package/dist/agent-runtime/src/use-conversation-list.d.ts +7 -0
  181. package/dist/agent-runtime/src/use-conversation-list.js +1 -0
  182. package/dist/agent-runtime/src/use-conversation-list.js.map +1 -1
  183. package/dist/agent-runtime/src/use-deep-agent-chat-outbox.cjs +46 -29
  184. package/dist/agent-runtime/src/use-deep-agent-chat-outbox.cjs.map +1 -1
  185. package/dist/agent-runtime/src/use-deep-agent-chat-outbox.d.ts +14 -22
  186. package/dist/agent-runtime/src/use-deep-agent-chat-outbox.js +46 -29
  187. package/dist/agent-runtime/src/use-deep-agent-chat-outbox.js.map +1 -1
  188. package/dist/agent-runtime/src/use-deep-agent-runtime.cjs +78 -14
  189. package/dist/agent-runtime/src/use-deep-agent-runtime.cjs.map +1 -1
  190. package/dist/agent-runtime/src/use-deep-agent-runtime.d.ts +34 -7
  191. package/dist/agent-runtime/src/use-deep-agent-runtime.js +79 -15
  192. package/dist/agent-runtime/src/use-deep-agent-runtime.js.map +1 -1
  193. package/dist/agent-runtime/src/use-deep-agent-thread.cjs +16 -1
  194. package/dist/agent-runtime/src/use-deep-agent-thread.cjs.map +1 -1
  195. package/dist/agent-runtime/src/use-deep-agent-thread.d.ts +7 -2
  196. package/dist/agent-runtime/src/use-deep-agent-thread.js +16 -1
  197. package/dist/agent-runtime/src/use-deep-agent-thread.js.map +1 -1
  198. package/dist/agent-runtime/src/use-deep-agent-voice.cjs +30 -4
  199. package/dist/agent-runtime/src/use-deep-agent-voice.cjs.map +1 -1
  200. package/dist/agent-runtime/src/use-deep-agent-voice.d.ts +22 -4
  201. package/dist/agent-runtime/src/use-deep-agent-voice.js +30 -4
  202. package/dist/agent-runtime/src/use-deep-agent-voice.js.map +1 -1
  203. package/dist/agent-runtime/src/withdrawn-turns.d.ts +5 -4
  204. package/dist/agent-runtime/src/word-device-fit.d.ts +174 -0
  205. package/dist/agent-runtime/src/work-in.d.ts +127 -0
  206. package/dist/assets/AthenaAssetEmbed.cjs.map +1 -1
  207. package/dist/assets/AthenaAssetEmbed.d.ts +6 -1
  208. package/dist/assets/AthenaAssetEmbed.js.map +1 -1
  209. package/dist/assets/asset-panel-store.cjs +13 -5
  210. package/dist/assets/asset-panel-store.cjs.map +1 -1
  211. package/dist/assets/asset-panel-store.d.ts +33 -2
  212. package/dist/assets/asset-panel-store.js +13 -5
  213. package/dist/assets/asset-panel-store.js.map +1 -1
  214. package/dist/auth/AthenaCredentialSourceContext.cjs +11 -0
  215. package/dist/auth/AthenaCredentialSourceContext.cjs.map +1 -1
  216. package/dist/auth/AthenaCredentialSourceContext.d.ts +6 -0
  217. package/dist/auth/AthenaCredentialSourceContext.js +11 -0
  218. package/dist/auth/AthenaCredentialSourceContext.js.map +1 -1
  219. package/dist/auth/account-identity.cjs +13 -2
  220. package/dist/auth/account-identity.cjs.map +1 -1
  221. package/dist/auth/account-identity.d.ts +9 -0
  222. package/dist/auth/account-identity.js +13 -2
  223. package/dist/auth/account-identity.js.map +1 -1
  224. package/dist/auth/credential-source.cjs +20 -4
  225. package/dist/auth/credential-source.cjs.map +1 -1
  226. package/dist/auth/credential-source.d.ts +9 -0
  227. package/dist/auth/credential-source.js +20 -4
  228. package/dist/auth/credential-source.js.map +1 -1
  229. package/dist/catalog/chat-pickers.cjs +31 -0
  230. package/dist/catalog/chat-pickers.cjs.map +1 -1
  231. package/dist/catalog/chat-pickers.d.ts +17 -0
  232. package/dist/catalog/chat-pickers.js +33 -2
  233. package/dist/catalog/chat-pickers.js.map +1 -1
  234. package/dist/catalog/runtime-catalog.cjs +63 -3
  235. package/dist/catalog/runtime-catalog.cjs.map +1 -1
  236. package/dist/catalog/runtime-catalog.d.ts +63 -3
  237. package/dist/catalog/runtime-catalog.js +64 -4
  238. package/dist/catalog/runtime-catalog.js.map +1 -1
  239. package/dist/chat/AthenaChat.cjs +301 -98
  240. package/dist/chat/AthenaChat.cjs.map +1 -1
  241. package/dist/chat/AthenaChat.d.ts +80 -4
  242. package/dist/chat/AthenaChat.js +302 -99
  243. package/dist/chat/AthenaChat.js.map +1 -1
  244. package/dist/chat/StatewireApprovalCard.cjs +35 -5
  245. package/dist/chat/StatewireApprovalCard.cjs.map +1 -1
  246. package/dist/chat/StatewireApprovalCard.d.ts +55 -2
  247. package/dist/chat/StatewireApprovalCard.js +37 -7
  248. package/dist/chat/StatewireApprovalCard.js.map +1 -1
  249. package/dist/chat/StatewireQueuedMessages.cjs +17 -2
  250. package/dist/chat/StatewireQueuedMessages.cjs.map +1 -1
  251. package/dist/chat/StatewireQueuedMessages.d.ts +8 -45
  252. package/dist/chat/StatewireQueuedMessages.js +18 -3
  253. package/dist/chat/StatewireQueuedMessages.js.map +1 -1
  254. package/dist/chat/chat-agent-mentions.cjs +70 -0
  255. package/dist/chat/chat-agent-mentions.cjs.map +1 -0
  256. package/dist/chat/chat-agent-mentions.d.ts +13 -0
  257. package/dist/chat/chat-agent-mentions.js +70 -0
  258. package/dist/chat/chat-agent-mentions.js.map +1 -0
  259. package/dist/chat/composer-actions.cjs +12 -0
  260. package/dist/chat/composer-actions.cjs.map +1 -0
  261. package/dist/chat/composer-actions.d.ts +22 -0
  262. package/dist/chat/composer-actions.js +12 -0
  263. package/dist/chat/composer-actions.js.map +1 -0
  264. package/dist/chat/follow-up-suggestions.cjs +185 -0
  265. package/dist/chat/follow-up-suggestions.cjs.map +1 -0
  266. package/dist/chat/follow-up-suggestions.d.ts +64 -0
  267. package/dist/chat/follow-up-suggestions.js +185 -0
  268. package/dist/chat/follow-up-suggestions.js.map +1 -0
  269. package/dist/chat/super-grouping/ToolTimeline.cjs +4 -3
  270. package/dist/chat/super-grouping/ToolTimeline.cjs.map +1 -1
  271. package/dist/chat/super-grouping/ToolTimeline.d.ts +7 -3
  272. package/dist/chat/super-grouping/ToolTimeline.js +4 -3
  273. package/dist/chat/super-grouping/ToolTimeline.js.map +1 -1
  274. package/dist/chat/turn-changes.cjs +284 -0
  275. package/dist/chat/turn-changes.cjs.map +1 -0
  276. package/dist/chat/turn-changes.d.ts +130 -0
  277. package/dist/chat/turn-changes.js +284 -0
  278. package/dist/chat/turn-changes.js.map +1 -0
  279. package/dist/chat/typed-interrupts/StatewireTypedInterruptCard.cjs +31 -0
  280. package/dist/chat/typed-interrupts/StatewireTypedInterruptCard.cjs.map +1 -0
  281. package/dist/chat/typed-interrupts/StatewireTypedInterruptCard.d.ts +31 -0
  282. package/dist/chat/typed-interrupts/StatewireTypedInterruptCard.js +31 -0
  283. package/dist/chat/typed-interrupts/StatewireTypedInterruptCard.js.map +1 -0
  284. package/dist/chat/typed-interrupts/approval-cards.cjs +250 -0
  285. package/dist/chat/typed-interrupts/approval-cards.cjs.map +1 -0
  286. package/dist/chat/typed-interrupts/approval-cards.d.ts +22 -0
  287. package/dist/chat/typed-interrupts/approval-cards.js +250 -0
  288. package/dist/chat/typed-interrupts/approval-cards.js.map +1 -0
  289. package/dist/chat/typed-interrupts/form-cards.cjs +289 -0
  290. package/dist/chat/typed-interrupts/form-cards.cjs.map +1 -0
  291. package/dist/chat/typed-interrupts/form-cards.d.ts +6 -0
  292. package/dist/chat/typed-interrupts/form-cards.js +289 -0
  293. package/dist/chat/typed-interrupts/form-cards.js.map +1 -0
  294. package/dist/chat/typed-interrupts/interrupt-card-shell.cjs +182 -0
  295. package/dist/chat/typed-interrupts/interrupt-card-shell.cjs.map +1 -0
  296. package/dist/chat/typed-interrupts/interrupt-card-shell.d.ts +47 -0
  297. package/dist/chat/typed-interrupts/interrupt-card-shell.js +182 -0
  298. package/dist/chat/typed-interrupts/interrupt-card-shell.js.map +1 -0
  299. package/dist/chat/typed-interrupts/json-schema-form.cjs +388 -0
  300. package/dist/chat/typed-interrupts/json-schema-form.cjs.map +1 -0
  301. package/dist/chat/typed-interrupts/json-schema-form.d.ts +33 -0
  302. package/dist/chat/typed-interrupts/json-schema-form.js +388 -0
  303. package/dist/chat/typed-interrupts/json-schema-form.js.map +1 -0
  304. package/dist/chat/typed-interrupts/questionnaire-card.cjs +449 -0
  305. package/dist/chat/typed-interrupts/questionnaire-card.cjs.map +1 -0
  306. package/dist/chat/typed-interrupts/questionnaire-card.d.ts +20 -0
  307. package/dist/chat/typed-interrupts/questionnaire-card.js +449 -0
  308. package/dist/chat/typed-interrupts/questionnaire-card.js.map +1 -0
  309. package/dist/chat/typed-interrupts/request-file-card.cjs +159 -0
  310. package/dist/chat/typed-interrupts/request-file-card.cjs.map +1 -0
  311. package/dist/chat/typed-interrupts/request-file-card.d.ts +2 -0
  312. package/dist/chat/typed-interrupts/request-file-card.js +159 -0
  313. package/dist/chat/typed-interrupts/request-file-card.js.map +1 -0
  314. package/dist/chat/typed-interrupts/toolkit-selection-card.cjs +189 -0
  315. package/dist/chat/typed-interrupts/toolkit-selection-card.cjs.map +1 -0
  316. package/dist/chat/typed-interrupts/toolkit-selection-card.d.ts +23 -0
  317. package/dist/chat/typed-interrupts/toolkit-selection-card.js +189 -0
  318. package/dist/chat/typed-interrupts/toolkit-selection-card.js.map +1 -0
  319. package/dist/chat/typed-interrupts/typed-interrupt-body.cjs +26 -0
  320. package/dist/chat/typed-interrupts/typed-interrupt-body.cjs.map +1 -0
  321. package/dist/chat/typed-interrupts/typed-interrupt-body.d.ts +3 -0
  322. package/dist/chat/typed-interrupts/typed-interrupt-body.js +26 -0
  323. package/dist/chat/typed-interrupts/typed-interrupt-body.js.map +1 -0
  324. package/dist/chat/typed-interrupts/typed-interrupt-graphql.cjs +105 -0
  325. package/dist/chat/typed-interrupts/typed-interrupt-graphql.cjs.map +1 -0
  326. package/dist/chat/typed-interrupts/typed-interrupt-graphql.d.ts +29 -0
  327. package/dist/chat/typed-interrupts/typed-interrupt-graphql.js +105 -0
  328. package/dist/chat/typed-interrupts/typed-interrupt-graphql.js.map +1 -0
  329. package/dist/chat/typed-interrupts/typed-interrupt-notice.cjs +70 -0
  330. package/dist/chat/typed-interrupts/typed-interrupt-notice.cjs.map +1 -0
  331. package/dist/chat/typed-interrupts/typed-interrupt-notice.d.ts +45 -0
  332. package/dist/chat/typed-interrupts/typed-interrupt-notice.js +70 -0
  333. package/dist/chat/typed-interrupts/typed-interrupt-notice.js.map +1 -0
  334. package/dist/chat/typed-interrupts/typed-interrupt-panel.cjs +76 -0
  335. package/dist/chat/typed-interrupts/typed-interrupt-panel.cjs.map +1 -0
  336. package/dist/chat/typed-interrupts/typed-interrupt-panel.d.ts +11 -0
  337. package/dist/chat/typed-interrupts/typed-interrupt-panel.js +76 -0
  338. package/dist/chat/typed-interrupts/typed-interrupt-panel.js.map +1 -0
  339. package/dist/chat/typed-interrupts/typed-interrupt-types.d.ts +46 -0
  340. package/dist/chat/typed-interrupts/use-interrupt-draft.cjs +106 -0
  341. package/dist/chat/typed-interrupts/use-interrupt-draft.cjs.map +1 -0
  342. package/dist/chat/typed-interrupts/use-interrupt-draft.d.ts +29 -0
  343. package/dist/chat/typed-interrupts/use-interrupt-draft.js +106 -0
  344. package/dist/chat/typed-interrupts/use-interrupt-draft.js.map +1 -0
  345. package/dist/chat/typed-interrupts/use-statewire-typed-interrupt.cjs +231 -0
  346. package/dist/chat/typed-interrupts/use-statewire-typed-interrupt.cjs.map +1 -0
  347. package/dist/chat/typed-interrupts/use-statewire-typed-interrupt.d.ts +66 -0
  348. package/dist/chat/typed-interrupts/use-statewire-typed-interrupt.js +231 -0
  349. package/dist/chat/typed-interrupts/use-statewire-typed-interrupt.js.map +1 -0
  350. package/dist/chat-ui/composer/composer-named-agents.cjs +13 -0
  351. package/dist/chat-ui/composer/composer-named-agents.cjs.map +1 -0
  352. package/dist/chat-ui/composer/composer-named-agents.d.ts +20 -0
  353. package/dist/chat-ui/composer/composer-named-agents.js +13 -0
  354. package/dist/chat-ui/composer/composer-named-agents.js.map +1 -0
  355. package/dist/chat-ui/composer/slash-command-menu.cjs +143 -0
  356. package/dist/chat-ui/composer/slash-command-menu.cjs.map +1 -0
  357. package/dist/chat-ui/composer/slash-command-menu.d.ts +19 -0
  358. package/dist/chat-ui/composer/slash-command-menu.js +143 -0
  359. package/dist/chat-ui/composer/slash-command-menu.js.map +1 -0
  360. package/dist/chat-ui/composer/slash-commands-extension.cjs +51 -0
  361. package/dist/chat-ui/composer/slash-commands-extension.cjs.map +1 -0
  362. package/dist/chat-ui/composer/slash-commands-extension.d.ts +39 -0
  363. package/dist/chat-ui/composer/slash-commands-extension.js +51 -0
  364. package/dist/chat-ui/composer/slash-commands-extension.js.map +1 -0
  365. package/dist/chat-ui/composer/slash-commands.cjs +74 -0
  366. package/dist/chat-ui/composer/slash-commands.cjs.map +1 -0
  367. package/dist/chat-ui/composer/slash-commands.d.ts +82 -0
  368. package/dist/chat-ui/composer/slash-commands.js +74 -0
  369. package/dist/chat-ui/composer/slash-commands.js.map +1 -0
  370. package/dist/chat-ui/composer/tiptap-composer.cjs +135 -9
  371. package/dist/chat-ui/composer/tiptap-composer.cjs.map +1 -1
  372. package/dist/chat-ui/composer/tiptap-composer.d.ts +61 -2
  373. package/dist/chat-ui/composer/tiptap-composer.js +135 -9
  374. package/dist/chat-ui/composer/tiptap-composer.js.map +1 -1
  375. package/dist/chat-ui/index.cjs +5 -0
  376. package/dist/chat-ui/index.cjs.map +1 -1
  377. package/dist/chat-ui/index.d.ts +4 -2
  378. package/dist/chat-ui/index.js +5 -0
  379. package/dist/chat-ui/index.js.map +1 -1
  380. package/dist/chat-ui/mentions/mention-chip.cjs +10 -4
  381. package/dist/chat-ui/mentions/mention-chip.cjs.map +1 -1
  382. package/dist/chat-ui/mentions/mention-chip.js +11 -5
  383. package/dist/chat-ui/mentions/mention-chip.js.map +1 -1
  384. package/dist/chat-ui/mentions/mention-extension.cjs +8 -1
  385. package/dist/chat-ui/mentions/mention-extension.cjs.map +1 -1
  386. package/dist/chat-ui/mentions/mention-extension.js +8 -1
  387. package/dist/chat-ui/mentions/mention-extension.js.map +1 -1
  388. package/dist/chat-ui/mentions/suggestions/components/get-scope-name.cjs +1 -0
  389. package/dist/chat-ui/mentions/suggestions/components/get-scope-name.cjs.map +1 -1
  390. package/dist/chat-ui/mentions/suggestions/components/get-scope-name.js +1 -0
  391. package/dist/chat-ui/mentions/suggestions/components/get-scope-name.js.map +1 -1
  392. package/dist/chat-ui/mentions/suggestions/components/mention-icon.cjs +20 -2
  393. package/dist/chat-ui/mentions/suggestions/components/mention-icon.cjs.map +1 -1
  394. package/dist/chat-ui/mentions/suggestions/components/mention-icon.d.ts +10 -1
  395. package/dist/chat-ui/mentions/suggestions/components/mention-icon.js +22 -4
  396. package/dist/chat-ui/mentions/suggestions/components/mention-icon.js.map +1 -1
  397. package/dist/chat-ui/mentions/suggestions/components/menu-item.cjs +1 -1
  398. package/dist/chat-ui/mentions/suggestions/components/menu-item.cjs.map +1 -1
  399. package/dist/chat-ui/mentions/suggestions/components/menu-item.js +1 -1
  400. package/dist/chat-ui/mentions/suggestions/components/menu-item.js.map +1 -1
  401. package/dist/chat-ui/mentions/suggestions/data/api-client.cjs +45 -0
  402. package/dist/chat-ui/mentions/suggestions/data/api-client.cjs.map +1 -1
  403. package/dist/chat-ui/mentions/suggestions/data/api-client.d.ts +48 -0
  404. package/dist/chat-ui/mentions/suggestions/data/api-client.js +45 -0
  405. package/dist/chat-ui/mentions/suggestions/data/api-client.js.map +1 -1
  406. package/dist/chat-ui/mentions/suggestions/data/sources/asset-type-icon-names.generated.cjs +89 -0
  407. package/dist/chat-ui/mentions/suggestions/data/sources/asset-type-icon-names.generated.cjs.map +1 -0
  408. package/dist/chat-ui/mentions/suggestions/data/sources/asset-type-icon-names.generated.d.ts +8 -0
  409. package/dist/chat-ui/mentions/suggestions/data/sources/asset-type-icon-names.generated.js +89 -0
  410. package/dist/chat-ui/mentions/suggestions/data/sources/asset-type-icon-names.generated.js.map +1 -0
  411. package/dist/chat-ui/mentions/suggestions/data/sources/asset-type-icons.cjs +140 -116
  412. package/dist/chat-ui/mentions/suggestions/data/sources/asset-type-icons.cjs.map +1 -1
  413. package/dist/chat-ui/mentions/suggestions/data/sources/asset-type-icons.d.ts +46 -12
  414. package/dist/chat-ui/mentions/suggestions/data/sources/asset-type-icons.js +141 -117
  415. package/dist/chat-ui/mentions/suggestions/data/sources/asset-type-icons.js.map +1 -1
  416. package/dist/chat-ui/mentions/suggestions/data/sources/index.cjs +272 -25
  417. package/dist/chat-ui/mentions/suggestions/data/sources/index.cjs.map +1 -1
  418. package/dist/chat-ui/mentions/suggestions/data/sources/index.d.ts +88 -10
  419. package/dist/chat-ui/mentions/suggestions/data/sources/index.js +274 -27
  420. package/dist/chat-ui/mentions/suggestions/data/sources/index.js.map +1 -1
  421. package/dist/chat-ui/mentions/suggestions/data/types.cjs.map +1 -1
  422. package/dist/chat-ui/mentions/suggestions/data/types.d.ts +27 -1
  423. package/dist/chat-ui/mentions/suggestions/data/types.js.map +1 -1
  424. package/dist/chat-ui/mentions/suggestions/data/use-mention-suggestions.cjs +56 -5
  425. package/dist/chat-ui/mentions/suggestions/data/use-mention-suggestions.cjs.map +1 -1
  426. package/dist/chat-ui/mentions/suggestions/data/use-mention-suggestions.d.ts +26 -6
  427. package/dist/chat-ui/mentions/suggestions/data/use-mention-suggestions.js +57 -6
  428. package/dist/chat-ui/mentions/suggestions/data/use-mention-suggestions.js.map +1 -1
  429. package/dist/chat-ui/mentions/suggestions/mention-suggestions.extension.cjs +34 -17
  430. package/dist/chat-ui/mentions/suggestions/mention-suggestions.extension.cjs.map +1 -1
  431. package/dist/chat-ui/mentions/suggestions/mention-suggestions.extension.d.ts +19 -1
  432. package/dist/chat-ui/mentions/suggestions/mention-suggestions.extension.js +35 -18
  433. package/dist/chat-ui/mentions/suggestions/mention-suggestions.extension.js.map +1 -1
  434. package/dist/chat-ui/mentions/use-asset-icon-app-url.cjs +12 -0
  435. package/dist/chat-ui/mentions/use-asset-icon-app-url.cjs.map +1 -0
  436. package/dist/chat-ui/mentions/use-asset-icon-app-url.d.ts +8 -0
  437. package/dist/chat-ui/mentions/use-asset-icon-app-url.js +12 -0
  438. package/dist/chat-ui/mentions/use-asset-icon-app-url.js.map +1 -0
  439. package/dist/chat-ui/statewire.d.ts +1 -1
  440. package/dist/chat-ui/thread/statewire-history-edge.cjs +15 -0
  441. package/dist/chat-ui/thread/statewire-history-edge.cjs.map +1 -1
  442. package/dist/chat-ui/thread/statewire-history-edge.d.ts +4 -1
  443. package/dist/chat-ui/thread/statewire-history-edge.js +15 -0
  444. package/dist/chat-ui/thread/statewire-history-edge.js.map +1 -1
  445. package/dist/collab/client.cjs +41 -6
  446. package/dist/collab/client.cjs.map +1 -1
  447. package/dist/collab/client.d.ts +38 -7
  448. package/dist/collab/client.js +41 -6
  449. package/dist/collab/client.js.map +1 -1
  450. package/dist/composer/ComposerAttachedReferences.cjs +119 -0
  451. package/dist/composer/ComposerAttachedReferences.cjs.map +1 -0
  452. package/dist/composer/ComposerAttachedReferences.d.ts +26 -0
  453. package/dist/composer/ComposerAttachedReferences.js +119 -0
  454. package/dist/composer/ComposerAttachedReferences.js.map +1 -0
  455. package/dist/composer/ComposerNamedAgents.cjs +63 -0
  456. package/dist/composer/ComposerNamedAgents.cjs.map +1 -0
  457. package/dist/composer/ComposerNamedAgents.d.ts +16 -0
  458. package/dist/composer/ComposerNamedAgents.js +63 -0
  459. package/dist/composer/ComposerNamedAgents.js.map +1 -0
  460. package/dist/composer/attached-references.cjs +159 -0
  461. package/dist/composer/attached-references.cjs.map +1 -0
  462. package/dist/composer/attached-references.d.ts +86 -0
  463. package/dist/composer/attached-references.js +159 -0
  464. package/dist/composer/attached-references.js.map +1 -0
  465. package/dist/composer/build-composed-message.cjs +14 -7
  466. package/dist/composer/build-composed-message.cjs.map +1 -1
  467. package/dist/composer/build-composed-message.d.ts +6 -1
  468. package/dist/composer/build-composed-message.js +14 -7
  469. package/dist/composer/build-composed-message.js.map +1 -1
  470. package/dist/composer/composer-handoff.cjs +6 -2
  471. package/dist/composer/composer-handoff.cjs.map +1 -1
  472. package/dist/composer/composer-handoff.d.ts +7 -1
  473. package/dist/composer/composer-handoff.js +6 -2
  474. package/dist/composer/composer-handoff.js.map +1 -1
  475. package/dist/composer/folder-upload.cjs +149 -0
  476. package/dist/composer/folder-upload.cjs.map +1 -0
  477. package/dist/composer/folder-upload.d.ts +79 -0
  478. package/dist/composer/folder-upload.js +149 -0
  479. package/dist/composer/folder-upload.js.map +1 -0
  480. package/dist/composer/index.d.ts +1 -1
  481. package/dist/composer/staged-message-metadata.cjs +12 -0
  482. package/dist/composer/staged-message-metadata.cjs.map +1 -0
  483. package/dist/composer/staged-message-metadata.d.ts +15 -0
  484. package/dist/composer/staged-message-metadata.js +12 -0
  485. package/dist/composer/staged-message-metadata.js.map +1 -0
  486. package/dist/composer/useAttachToChat.cjs +35 -0
  487. package/dist/composer/useAttachToChat.cjs.map +1 -0
  488. package/dist/composer/useAttachToChat.d.ts +54 -0
  489. package/dist/composer/useAttachToChat.js +35 -0
  490. package/dist/composer/useAttachToChat.js.map +1 -0
  491. package/dist/composer/useAttachedReferencesComposerProps.cjs +19 -0
  492. package/dist/composer/useAttachedReferencesComposerProps.cjs.map +1 -0
  493. package/dist/composer/useAttachedReferencesComposerProps.d.ts +12 -0
  494. package/dist/composer/useAttachedReferencesComposerProps.js +19 -0
  495. package/dist/composer/useAttachedReferencesComposerProps.js.map +1 -0
  496. package/dist/composer/useFileUpload.cjs +95 -7
  497. package/dist/composer/useFileUpload.cjs.map +1 -1
  498. package/dist/composer/useFileUpload.d.ts +21 -2
  499. package/dist/composer/useFileUpload.js +95 -7
  500. package/dist/composer/useFileUpload.js.map +1 -1
  501. package/dist/data/athena-api-error.cjs +125 -0
  502. package/dist/data/athena-api-error.cjs.map +1 -0
  503. package/dist/data/athena-api-error.d.ts +96 -0
  504. package/dist/data/athena-api-error.js +125 -0
  505. package/dist/data/athena-api-error.js.map +1 -0
  506. package/dist/data/athena-data-client.cjs +106 -0
  507. package/dist/data/athena-data-client.cjs.map +1 -0
  508. package/dist/data/athena-data-client.d.ts +74 -0
  509. package/dist/data/athena-data-client.js +106 -0
  510. package/dist/data/athena-data-client.js.map +1 -0
  511. package/dist/data/athena-member.cjs +93 -0
  512. package/dist/data/athena-member.cjs.map +1 -0
  513. package/dist/data/athena-member.d.ts +125 -0
  514. package/dist/data/athena-member.js +93 -0
  515. package/dist/data/athena-member.js.map +1 -0
  516. package/dist/data/athena-request.cjs +460 -0
  517. package/dist/data/athena-request.cjs.map +1 -0
  518. package/dist/data/athena-request.d.ts +120 -0
  519. package/dist/data/athena-request.js +460 -0
  520. package/dist/data/athena-request.js.map +1 -0
  521. package/dist/data/use-athena-fetch.cjs +14 -0
  522. package/dist/data/use-athena-fetch.cjs.map +1 -0
  523. package/dist/data/use-athena-fetch.d.ts +19 -0
  524. package/dist/data/use-athena-fetch.js +14 -0
  525. package/dist/data/use-athena-fetch.js.map +1 -0
  526. package/dist/data/use-athena-graphql.cjs +66 -0
  527. package/dist/data/use-athena-graphql.cjs.map +1 -0
  528. package/dist/data/use-athena-graphql.d.ts +56 -0
  529. package/dist/data/use-athena-graphql.js +66 -0
  530. package/dist/data/use-athena-graphql.js.map +1 -0
  531. package/dist/data/use-athena-rest.cjs +33 -0
  532. package/dist/data/use-athena-rest.cjs.map +1 -0
  533. package/dist/data/use-athena-rest.d.ts +21 -0
  534. package/dist/data/use-athena-rest.js +33 -0
  535. package/dist/data/use-athena-rest.js.map +1 -0
  536. package/dist/data/use-semantic-query.cjs +44 -0
  537. package/dist/data/use-semantic-query.cjs.map +1 -0
  538. package/dist/data/use-semantic-query.d.ts +92 -0
  539. package/dist/data/use-semantic-query.js +44 -0
  540. package/dist/data/use-semantic-query.js.map +1 -0
  541. package/dist/diagnostics/athena-diagnostics.cjs.map +1 -1
  542. package/dist/diagnostics/athena-diagnostics.d.ts +5 -1
  543. package/dist/diagnostics/athena-diagnostics.js.map +1 -1
  544. package/dist/diagnostics/errors.cjs +7 -0
  545. package/dist/diagnostics/errors.cjs.map +1 -1
  546. package/dist/diagnostics/errors.d.ts +7 -0
  547. package/dist/diagnostics/errors.js +7 -0
  548. package/dist/diagnostics/errors.js.map +1 -1
  549. package/dist/index.cjs +155 -11
  550. package/dist/index.cjs.map +1 -1
  551. package/dist/index.d.ts +72 -13
  552. package/dist/index.js +148 -4
  553. package/dist/index.js.map +1 -1
  554. package/dist/keryx-http/src/initial-sync.cjs +64 -16
  555. package/dist/keryx-http/src/initial-sync.cjs.map +1 -1
  556. package/dist/keryx-http/src/initial-sync.d.ts +31 -1
  557. package/dist/keryx-http/src/initial-sync.js +64 -16
  558. package/dist/keryx-http/src/initial-sync.js.map +1 -1
  559. package/dist/keryx-http/src/own-awareness.cjs +20 -0
  560. package/dist/keryx-http/src/own-awareness.cjs.map +1 -0
  561. package/dist/keryx-http/src/own-awareness.d.ts +50 -0
  562. package/dist/keryx-http/src/own-awareness.js +20 -0
  563. package/dist/keryx-http/src/own-awareness.js.map +1 -0
  564. package/dist/keryx-http/src/update-attributions.cjs +26 -1
  565. package/dist/keryx-http/src/update-attributions.cjs.map +1 -1
  566. package/dist/keryx-http/src/update-attributions.d.ts +10 -1
  567. package/dist/keryx-http/src/update-attributions.js +26 -1
  568. package/dist/keryx-http/src/update-attributions.js.map +1 -1
  569. package/dist/offline/chat-outbox.cjs +262 -26
  570. package/dist/offline/chat-outbox.cjs.map +1 -1
  571. package/dist/offline/chat-outbox.d.ts +90 -12
  572. package/dist/offline/chat-outbox.js +263 -27
  573. package/dist/offline/chat-outbox.js.map +1 -1
  574. package/dist/provider/AthenaProvider.cjs +60 -22
  575. package/dist/provider/AthenaProvider.cjs.map +1 -1
  576. package/dist/provider/AthenaProvider.d.ts +24 -8
  577. package/dist/provider/AthenaProvider.js +61 -23
  578. package/dist/provider/AthenaProvider.js.map +1 -1
  579. package/dist/react/package.json.cjs +1 -1
  580. package/dist/react/package.json.js +1 -1
  581. package/dist/references/src/anchors/parse.cjs +11 -1
  582. package/dist/references/src/anchors/parse.cjs.map +1 -1
  583. package/dist/references/src/anchors/parse.js +11 -1
  584. package/dist/references/src/anchors/parse.js.map +1 -1
  585. package/dist/references/src/anchors/schemas.d.ts +1 -0
  586. package/dist/references/src/anchors/serialize.cjs +1 -0
  587. package/dist/references/src/anchors/serialize.cjs.map +1 -1
  588. package/dist/references/src/anchors/serialize.js +1 -0
  589. package/dist/references/src/anchors/serialize.js.map +1 -1
  590. package/dist/references/src/anchors/types.cjs +5 -0
  591. package/dist/references/src/anchors/types.cjs.map +1 -1
  592. package/dist/references/src/anchors/types.d.ts +9 -0
  593. package/dist/references/src/anchors/types.js +5 -0
  594. package/dist/references/src/anchors/types.js.map +1 -1
  595. package/dist/references/src/attachable.cjs +149 -0
  596. package/dist/references/src/attachable.cjs.map +1 -0
  597. package/dist/references/src/attachable.d.ts +87 -0
  598. package/dist/references/src/attachable.js +149 -0
  599. package/dist/references/src/attachable.js.map +1 -0
  600. package/dist/references/src/schemas.d.ts +2 -0
  601. package/dist/runtime/StatewirePlanModeLaneSync.cjs +93 -0
  602. package/dist/runtime/StatewirePlanModeLaneSync.cjs.map +1 -0
  603. package/dist/runtime/StatewirePlanModeLaneSync.d.ts +34 -0
  604. package/dist/runtime/StatewirePlanModeLaneSync.js +93 -0
  605. package/dist/runtime/StatewirePlanModeLaneSync.js.map +1 -0
  606. package/dist/runtime/StatewireThreadConfigLaneSync.cjs +2 -0
  607. package/dist/runtime/StatewireThreadConfigLaneSync.cjs.map +1 -1
  608. package/dist/runtime/StatewireThreadConfigLaneSync.d.ts +4 -0
  609. package/dist/runtime/StatewireThreadConfigLaneSync.js +2 -0
  610. package/dist/runtime/StatewireThreadConfigLaneSync.js.map +1 -1
  611. package/dist/runtime/statewire-plan-mode.cjs +71 -0
  612. package/dist/runtime/statewire-plan-mode.cjs.map +1 -0
  613. package/dist/runtime/statewire-plan-mode.d.ts +88 -0
  614. package/dist/runtime/statewire-plan-mode.js +71 -0
  615. package/dist/runtime/statewire-plan-mode.js.map +1 -0
  616. package/dist/runtime/statewire-run-config.cjs +3 -1
  617. package/dist/runtime/statewire-run-config.cjs.map +1 -1
  618. package/dist/runtime/statewire-run-config.d.ts +7 -0
  619. package/dist/runtime/statewire-run-config.js +3 -1
  620. package/dist/runtime/statewire-run-config.js.map +1 -1
  621. package/dist/runtime/statewire-session-key.cjs +11 -5
  622. package/dist/runtime/statewire-session-key.cjs.map +1 -1
  623. package/dist/runtime/statewire-session-key.d.ts +22 -10
  624. package/dist/runtime/statewire-session-key.js +11 -5
  625. package/dist/runtime/statewire-session-key.js.map +1 -1
  626. package/dist/runtime/useAthenaStatewireRuntime.cjs +64 -9
  627. package/dist/runtime/useAthenaStatewireRuntime.cjs.map +1 -1
  628. package/dist/runtime/useAthenaStatewireRuntime.d.ts +26 -10
  629. package/dist/runtime/useAthenaStatewireRuntime.js +66 -11
  630. package/dist/runtime/useAthenaStatewireRuntime.js.map +1 -1
  631. package/dist/search/useAthenaAssets.cjs +394 -0
  632. package/dist/search/useAthenaAssets.cjs.map +1 -0
  633. package/dist/search/useAthenaAssets.d.ts +186 -0
  634. package/dist/search/useAthenaAssets.js +394 -0
  635. package/dist/search/useAthenaAssets.js.map +1 -0
  636. package/dist/sheet-range/index.cjs +4 -0
  637. package/dist/sheet-range/index.cjs.map +1 -1
  638. package/dist/sheet-range/index.d.ts +4 -2
  639. package/dist/sheet-range/index.js +4 -0
  640. package/dist/sheet-range/index.js.map +1 -1
  641. package/dist/sheet-range/query-range.cjs +102 -0
  642. package/dist/sheet-range/query-range.cjs.map +1 -0
  643. package/dist/sheet-range/query-range.d.ts +46 -0
  644. package/dist/sheet-range/query-range.js +102 -0
  645. package/dist/sheet-range/query-range.js.map +1 -0
  646. package/dist/styles.css +1 -1
  647. package/dist/subagents/index.cjs +49 -0
  648. package/dist/subagents/index.cjs.map +1 -0
  649. package/dist/subagents/index.d.ts +16 -0
  650. package/dist/subagents/index.js +49 -0
  651. package/dist/subagents/index.js.map +1 -0
  652. package/dist/subagents/lane-follow.cjs +19 -0
  653. package/dist/subagents/lane-follow.cjs.map +1 -0
  654. package/dist/subagents/lane-follow.d.ts +9 -0
  655. package/dist/subagents/lane-follow.js +19 -0
  656. package/dist/subagents/lane-follow.js.map +1 -0
  657. package/dist/subagents/lane-model.cjs +178 -0
  658. package/dist/subagents/lane-model.cjs.map +1 -0
  659. package/dist/subagents/lane-model.d.ts +140 -0
  660. package/dist/subagents/lane-model.js +178 -0
  661. package/dist/subagents/lane-model.js.map +1 -0
  662. package/dist/subagents/lane-parts.cjs +517 -0
  663. package/dist/subagents/lane-parts.cjs.map +1 -0
  664. package/dist/subagents/lane-parts.d.ts +130 -0
  665. package/dist/subagents/lane-parts.js +517 -0
  666. package/dist/subagents/lane-parts.js.map +1 -0
  667. package/dist/subagents/subagent-lane-group.cjs +215 -0
  668. package/dist/subagents/subagent-lane-group.cjs.map +1 -0
  669. package/dist/subagents/subagent-lane-group.d.ts +67 -0
  670. package/dist/subagents/subagent-lane-group.js +215 -0
  671. package/dist/subagents/subagent-lane-group.js.map +1 -0
  672. package/dist/subagents/subagent-transcript-drawer.cjs +431 -0
  673. package/dist/subagents/subagent-transcript-drawer.cjs.map +1 -0
  674. package/dist/subagents/subagent-transcript-drawer.d.ts +78 -0
  675. package/dist/subagents/subagent-transcript-drawer.js +431 -0
  676. package/dist/subagents/subagent-transcript-drawer.js.map +1 -0
  677. package/dist/subagents/task-subagent-group.cjs +115 -0
  678. package/dist/subagents/task-subagent-group.cjs.map +1 -0
  679. package/dist/subagents/task-subagent-group.d.ts +36 -0
  680. package/dist/subagents/task-subagent-group.js +115 -0
  681. package/dist/subagents/task-subagent-group.js.map +1 -0
  682. package/dist/subagents/use-omitted-images-in-view.cjs +68 -0
  683. package/dist/subagents/use-omitted-images-in-view.cjs.map +1 -0
  684. package/dist/subagents/use-omitted-images-in-view.d.ts +21 -0
  685. package/dist/subagents/use-omitted-images-in-view.js +68 -0
  686. package/dist/subagents/use-omitted-images-in-view.js.map +1 -0
  687. package/dist/threads/Inbox.cjs +2 -2
  688. package/dist/threads/Inbox.cjs.map +1 -1
  689. package/dist/threads/SessionList.cjs +6 -6
  690. package/dist/threads/SessionList.cjs.map +1 -1
  691. package/dist/threads/SessionsPage.cjs +13 -7
  692. package/dist/threads/SessionsPage.cjs.map +1 -1
  693. package/dist/threads/SessionsPage.d.ts +10 -1
  694. package/dist/threads/SessionsPage.js +9 -3
  695. package/dist/threads/SessionsPage.js.map +1 -1
  696. package/dist/threads/session-list-model.cjs.map +1 -1
  697. package/dist/threads/session-list-model.d.ts +2 -1
  698. package/dist/threads/session-list-model.js.map +1 -1
  699. package/dist/threads/session-row-parts.cjs +3 -3
  700. package/dist/threads/session-row-parts.cjs.map +1 -1
  701. package/dist/threads/sessions-page-model.cjs +13 -5
  702. package/dist/threads/sessions-page-model.cjs.map +1 -1
  703. package/dist/threads/sessions-page-model.d.ts +7 -0
  704. package/dist/threads/sessions-page-model.js +11 -3
  705. package/dist/threads/sessions-page-model.js.map +1 -1
  706. package/dist/threads/sessions-page-storage.cjs +8 -8
  707. package/dist/threads/sessions-page-storage.cjs.map +1 -1
  708. package/dist/threads/sessions-page-storage.d.ts +5 -1
  709. package/dist/threads/sessions-page-storage.js +8 -8
  710. package/dist/threads/sessions-page-storage.js.map +1 -1
  711. package/dist/threads/statewire-thread-list.cjs +14 -2
  712. package/dist/threads/statewire-thread-list.cjs.map +1 -1
  713. package/dist/threads/statewire-thread-list.d.ts +11 -2
  714. package/dist/threads/statewire-thread-list.js +14 -2
  715. package/dist/threads/statewire-thread-list.js.map +1 -1
  716. package/dist/threads/use-athena-sessions.cjs +1 -0
  717. package/dist/threads/use-athena-sessions.cjs.map +1 -1
  718. package/dist/threads/use-athena-sessions.d.ts +7 -0
  719. package/dist/threads/use-athena-sessions.js +1 -0
  720. package/dist/threads/use-athena-sessions.js.map +1 -1
  721. package/dist/threads/use-athena-thread-agent.cjs +31 -0
  722. package/dist/threads/use-athena-thread-agent.cjs.map +1 -0
  723. package/dist/threads/use-athena-thread-agent.d.ts +38 -0
  724. package/dist/threads/use-athena-thread-agent.js +31 -0
  725. package/dist/threads/use-athena-thread-agent.js.map +1 -0
  726. package/dist/threads/use-athena-thread-plan-mode.cjs +18 -0
  727. package/dist/threads/use-athena-thread-plan-mode.cjs.map +1 -0
  728. package/dist/threads/use-athena-thread-plan-mode.d.ts +18 -0
  729. package/dist/threads/use-athena-thread-plan-mode.js +18 -0
  730. package/dist/threads/use-athena-thread-plan-mode.js.map +1 -0
  731. package/dist/threads/use-rest-conversation-history.d.ts +1 -0
  732. package/dist/tools/agent-creations.cjs +97 -0
  733. package/dist/tools/agent-creations.cjs.map +1 -0
  734. package/dist/tools/agent-creations.d.ts +38 -0
  735. package/dist/tools/agent-creations.js +97 -0
  736. package/dist/tools/agent-creations.js.map +1 -0
  737. package/dist/tools/agent-highlights.cjs +100 -0
  738. package/dist/tools/agent-highlights.cjs.map +1 -0
  739. package/dist/tools/agent-highlights.d.ts +57 -0
  740. package/dist/tools/agent-highlights.js +100 -0
  741. package/dist/tools/agent-highlights.js.map +1 -0
  742. package/dist/tools/append-document-tool-ui.cjs +1 -0
  743. package/dist/tools/append-document-tool-ui.cjs.map +1 -1
  744. package/dist/tools/append-document-tool-ui.d.ts +7 -0
  745. package/dist/tools/append-document-tool-ui.js +2 -1
  746. package/dist/tools/append-document-tool-ui.js.map +1 -1
  747. package/dist/tools/auto-open-tools.cjs +144 -71
  748. package/dist/tools/auto-open-tools.cjs.map +1 -1
  749. package/dist/tools/auto-open-tools.d.ts +131 -1
  750. package/dist/tools/auto-open-tools.js +145 -72
  751. package/dist/tools/auto-open-tools.js.map +1 -1
  752. package/dist/tools/browser-tool-uis.cjs +594 -0
  753. package/dist/tools/browser-tool-uis.cjs.map +1 -0
  754. package/dist/tools/browser-tool-uis.d.ts +8 -0
  755. package/dist/tools/browser-tool-uis.js +594 -0
  756. package/dist/tools/browser-tool-uis.js.map +1 -0
  757. package/dist/tools/computer-asset-tool-uis.cjs +313 -0
  758. package/dist/tools/computer-asset-tool-uis.cjs.map +1 -0
  759. package/dist/tools/computer-asset-tool-uis.d.ts +5 -0
  760. package/dist/tools/computer-asset-tool-uis.js +313 -0
  761. package/dist/tools/computer-asset-tool-uis.js.map +1 -0
  762. package/dist/tools/document-edit-tool-uis.cjs +218 -0
  763. package/dist/tools/document-edit-tool-uis.cjs.map +1 -0
  764. package/dist/tools/document-edit-tool-uis.d.ts +40 -0
  765. package/dist/tools/document-edit-tool-uis.js +218 -0
  766. package/dist/tools/document-edit-tool-uis.js.map +1 -0
  767. package/dist/tools/drive-tool-uis.cjs +429 -0
  768. package/dist/tools/drive-tool-uis.cjs.map +1 -0
  769. package/dist/tools/drive-tool-uis.d.ts +121 -0
  770. package/dist/tools/drive-tool-uis.js +429 -0
  771. package/dist/tools/drive-tool-uis.js.map +1 -0
  772. package/dist/tools/email-calendar-tool-uis.cjs +789 -0
  773. package/dist/tools/email-calendar-tool-uis.cjs.map +1 -0
  774. package/dist/tools/email-calendar-tool-uis.d.ts +129 -0
  775. package/dist/tools/email-calendar-tool-uis.js +789 -0
  776. package/dist/tools/email-calendar-tool-uis.js.map +1 -0
  777. package/dist/tools/ontology-tool-uis.cjs +83 -0
  778. package/dist/tools/ontology-tool-uis.cjs.map +1 -0
  779. package/dist/tools/ontology-tool-uis.d.ts +9 -0
  780. package/dist/tools/ontology-tool-uis.js +83 -0
  781. package/dist/tools/ontology-tool-uis.js.map +1 -0
  782. package/dist/tools/orchestration-tool-uis.cjs +586 -0
  783. package/dist/tools/orchestration-tool-uis.cjs.map +1 -0
  784. package/dist/tools/orchestration-tool-uis.d.ts +141 -0
  785. package/dist/tools/orchestration-tool-uis.js +586 -0
  786. package/dist/tools/orchestration-tool-uis.js.map +1 -0
  787. package/dist/tools/presentation-edit-tool-uis.cjs +516 -0
  788. package/dist/tools/presentation-edit-tool-uis.cjs.map +1 -0
  789. package/dist/tools/presentation-edit-tool-uis.d.ts +73 -0
  790. package/dist/tools/presentation-edit-tool-uis.js +516 -0
  791. package/dist/tools/presentation-edit-tool-uis.js.map +1 -0
  792. package/dist/tools/project-tool-uis.cjs +213 -0
  793. package/dist/tools/project-tool-uis.cjs.map +1 -0
  794. package/dist/tools/project-tool-uis.d.ts +14 -0
  795. package/dist/tools/project-tool-uis.js +213 -0
  796. package/dist/tools/project-tool-uis.js.map +1 -0
  797. package/dist/tools/sandbox-tool-uis.cjs +491 -0
  798. package/dist/tools/sandbox-tool-uis.cjs.map +1 -0
  799. package/dist/tools/sandbox-tool-uis.d.ts +116 -0
  800. package/dist/tools/sandbox-tool-uis.js +491 -0
  801. package/dist/tools/sandbox-tool-uis.js.map +1 -0
  802. package/dist/tools/sheet-query-tool-ui.cjs +138 -0
  803. package/dist/tools/sheet-query-tool-ui.cjs.map +1 -0
  804. package/dist/tools/sheet-query-tool-ui.d.ts +15 -0
  805. package/dist/tools/sheet-query-tool-ui.js +138 -0
  806. package/dist/tools/sheet-query-tool-ui.js.map +1 -0
  807. package/dist/tools/studio-screenshot-tool-uis.cjs +262 -0
  808. package/dist/tools/studio-screenshot-tool-uis.cjs.map +1 -0
  809. package/dist/tools/studio-screenshot-tool-uis.d.ts +52 -0
  810. package/dist/tools/studio-screenshot-tool-uis.js +262 -0
  811. package/dist/tools/studio-screenshot-tool-uis.js.map +1 -0
  812. package/dist/tools/subagent-task-tool-ui.cjs +24 -475
  813. package/dist/tools/subagent-task-tool-ui.cjs.map +1 -1
  814. package/dist/tools/subagent-task-tool-ui.d.ts +19 -103
  815. package/dist/tools/subagent-task-tool-ui.js +28 -479
  816. package/dist/tools/subagent-task-tool-ui.js.map +1 -1
  817. package/dist/tools/tool-summary.cjs +36 -0
  818. package/dist/tools/tool-summary.cjs.map +1 -1
  819. package/dist/tools/tool-summary.js +36 -0
  820. package/dist/tools/tool-summary.js.map +1 -1
  821. package/dist/tools/tool-uis.cjs +181 -53
  822. package/dist/tools/tool-uis.cjs.map +1 -1
  823. package/dist/tools/tool-uis.d.ts +40 -0
  824. package/dist/tools/tool-uis.js +183 -55
  825. package/dist/tools/tool-uis.js.map +1 -1
  826. package/dist/typed-interrupts/index.cjs +15 -0
  827. package/dist/typed-interrupts/index.cjs.map +1 -0
  828. package/dist/typed-interrupts/index.d.ts +20 -0
  829. package/dist/typed-interrupts/index.js +15 -0
  830. package/dist/typed-interrupts/index.js.map +1 -0
  831. package/dist/version.cjs +4 -0
  832. package/dist/version.cjs.map +1 -1
  833. package/dist/version.d.ts +9 -0
  834. package/dist/version.js +4 -0
  835. package/dist/version.js.map +1 -1
  836. package/dist/workbench/live-desktop-api.cjs +2 -1
  837. package/dist/workbench/live-desktop-api.cjs.map +1 -1
  838. package/dist/workbench/live-desktop-api.js +2 -1
  839. package/dist/workbench/live-desktop-api.js.map +1 -1
  840. package/dist/workbench/session-workbench-panes.cjs +6 -6
  841. package/dist/workbench/session-workbench-panes.cjs.map +1 -1
  842. package/dist/workbench/session-workspace-api.cjs +7 -2
  843. package/dist/workbench/session-workspace-api.cjs.map +1 -1
  844. package/dist/workbench/session-workspace-api.d.ts +10 -0
  845. package/dist/workbench/session-workspace-api.js +7 -2
  846. package/dist/workbench/session-workspace-api.js.map +1 -1
  847. package/package.json +28 -6
  848. package/dist/agent-runtime/src/chat-outbox-store.cjs +0 -510
  849. package/dist/agent-runtime/src/chat-outbox-store.cjs.map +0 -1
  850. package/dist/agent-runtime/src/chat-outbox-store.d.ts +0 -210
  851. package/dist/agent-runtime/src/chat-outbox-store.js +0 -510
  852. package/dist/agent-runtime/src/chat-outbox-store.js.map +0 -1
@@ -1 +1 @@
1
- {"version":3,"file":"StatewireApprovalCard.js","sources":["../../src/chat/StatewireApprovalCard.tsx"],"sourcesContent":["import { useAuiState } from '@assistant-ui/react';\nimport { type StatewireThread, useStatewireState } from '@assistant-ui/react-statewire';\nimport {\n actionRequestToolCallIds,\n asHitlApproval,\n fanLaneDecision,\n HITL_PENDING_RESUME_GRACE_MS,\n type HitlActionDecision,\n type HitlApprovalPayload,\n hasStatewireThreadExtras,\n hitlResumeActionDecisions,\n hitlResumeApprove,\n hitlResumeApproveForSession,\n hitlResumeReject,\n interruptResumeDecline,\n interruptMirrorPayload,\n laneInterruptIds,\n type PendingActionRequest,\n type PendingApprovalContext,\n type PendingApprovalTitle,\n pendingApprovalTitle,\n readInterruptMessage,\n readInterruptMirror,\n type ResumeExtras,\n resumeValueApproves,\n sessionApprovalLabel,\n sessionApprovalOffer,\n statewireRejectionDetailMessage,\n} from '@athenaintel/agent-runtime';\nimport {\n CheckCheckIcon,\n CheckIcon,\n ChevronDownIcon,\n ShieldAlertIcon,\n XIcon,\n} from 'lucide-react';\nimport {\n type FC,\n type ReactNode,\n useCallback,\n useEffect,\n useMemo,\n useRef,\n useState,\n} from 'react';\nimport { cn } from '../lib/utils';\nimport { Button } from '../ui/button';\nimport {\n type StatewireInterruptPredicate,\n useStatewireApprovalRequest,\n} from './use-statewire-approval-request';\n\n/**\n * Human-in-the-loop approval card for the statewire transport — the one\n * approval UI every Athena chat surface mounts (the SDK's `AthenaChat`, the\n * Chrome side panel, the Office task pane, Olympus).\n *\n * When the deep-agent runtime hits an approval-gated tool call, the backend\n * parks the run on an `interrupt` input request. This card reads that request\n * through `useStatewireApprovalRequest` and answers it with\n * `{ type: 'run/input', requestId, response: { type: 'resume', value } }` —\n * the exact command the backend's resume path consumes. Without an answer the\n * run stays parked forever, so this card must be mounted on every statewire\n * chat surface. On legacy (non-statewire) threads it renders nothing.\n *\n * A gated call raised inside a delegated subagent parks only its lane: the\n * host mirrors that interrupt while the sibling lanes keep streaming, before\n * any input request exists. The card renders the mirrored payload the same\n * way and answers it with `run/lane-input` keyed by the lane's langgraph\n * interrupt id (`laneInterruptIds`); the host queues the decision and applies\n * it the moment the run parks, so the approver never waits on the siblings.\n * Once parked, a payload whose calls all carry interrupt ids resumes as a\n * `lane_decisions` map too — one positional `run/input` can only answer the\n * first of several parked lanes.\n *\n * Recovery of a queued decision the host never applies is ordered host\n * first: the host's answerer resumes the park or drops (and flushes) the\n * queue within `QUEUED_LANE_ANSWER_BUDGET_SECONDS` of the park, and this\n * card's grace (`HITL_PENDING_RESUME_GRACE_MS`, longer than that budget)\n * fires only when the host stayed silent. When it fires, the card that sent\n * the queued decision asks the host to replay it (`run/lane-replay` — the\n * host resumes as the approver, under the meta it recorded, and refuses any\n * other caller); every other card, and a replay the host refuses, hands the\n * decision back to a person by unlocking the actions. A queued decision is\n * never re-sent as a `run/input` of the viewing client's own: that would run\n * the approver's decision under the viewer's identity and configuration.\n *\n * A lone gated call whose resolved envelope (`approval_context`) carries a\n * headline is titled by it in the card's own review: the headline replaces\n * \"`tool` requires approval before it runs\", the summary sits under it, and\n * the default details name the tool instead. A batch keeps the generic copy,\n * since one decision answers every call. So does a host review\n * (`renderDetails`, or an editor from `renderEditor`): it shows the envelope\n * itself, headline included, so the header must not say it again. Display-only:\n * the decision row and what it sends do not change.\n *\n * Host-specific review UIs (subagent cards, email summaries) slot in through\n * `renderDetails`; a host composer that must also OWN the decision (an\n * editable email whose edits have to reach the backend) takes over the\n * details and the decision row through `renderEditor`; requests another\n * surface answers (typed interrupt families, per-lane subagent approvals)\n * stand down through `isHandledElsewhere`; viewers without edit rights see\n * `readOnlyNotice`.\n */\n\n/**\n * The answer a passkey decision check confirms before the card sends it\n * (identity 0b.9): a `run/input` resume of the parked request, or the lane\n * decisions of a `run/lane-input` sent while sibling lanes still stream.\n */\nexport type StatewireDecisionAnswer =\n | {\n readonly kind: 'input';\n readonly requestId: string;\n readonly value: StatewireThread.InputResponse;\n }\n | {\n readonly kind: 'lanes';\n readonly laneDecisions: Readonly<Record<string, StatewireThread.InputResponse>>;\n };\n\n/**\n * Runs the host's passkey check for an approving answer and resolves its\n * token, or `undefined` to send the answer without one. While checks are\n * report-only, an answer goes ahead without a check (no passkey yet, a\n * cancelled prompt); the host decides what to tell the person. Never called\n * for an answer that only rejects.\n */\nexport type StatewireDecisionConfirmer = (\n answer: StatewireDecisionAnswer,\n) => Promise<string | undefined>;\n\nfunction answerApproves(answer: StatewireDecisionAnswer): boolean {\n if (answer.kind === 'input') return resumeValueApproves(answer.value);\n const lanes = Object.values(answer.laneDecisions);\n return lanes.length === 0 || lanes.some(resumeValueApproves);\n}\n\n/** What the card reads in place of the host's queued lanes once it has given up on them. */\nconst NO_HOST_QUEUED_LANE_DECISIONS: Readonly<Record<string, unknown>> = Object.freeze({});\n\n/** The pending request a host slot renders or judges. */\nexport interface StatewireApprovalRequestContext {\n /** The parked input request — `undefined` while the run still streams (a live lane approval). */\n request: StatewireThread.CustomInputRequest | undefined;\n /** The payload narrowed to the Athena HITL approval shape, or `null` for a generic park. */\n hitl: HitlApprovalPayload | null;\n /** Every gated call the approval covers, in decision order (empty for non-HITL parks). */\n actionRequests: PendingActionRequest[];\n /**\n * The approval's title (`pendingApprovalTitle`): a lone call's envelope\n * headline and summary. Absent for a batch, a non-HITL park and a call\n * without one. The default header shows it only above the card's own\n * details; under a host review the host shows the envelope, and may lead\n * with this.\n */\n title?: PendingApprovalTitle;\n}\n\n/** The request a host editor renders, plus the decisions it may send for it. */\nexport interface StatewireApprovalEditorContext extends StatewireApprovalRequestContext {\n /** A decision is in flight (or a live lane already answered); the editor must not send another. */\n locked: boolean;\n /** Whether a session-wide approval may be offered for this batch. */\n sessionApprovalOffered: boolean;\n /**\n * What the session option's button says, naming exactly what the answer\n * covers (`sessionApprovalLabel`): \"Approve all for this session\" for\n * tools, or \"Approve for this session: only kyle@… and sam@…\" for sends\n * scoped to their recipients. Meaningful only when `sessionApprovalOffered`.\n */\n sessionApprovalLabel: string;\n approve: () => void;\n approveForSession: () => void;\n reject: (reason?: string) => void;\n /**\n * Answer each gated call on its own — the only way an EDITED call reaches\n * the backend. `decision` is asked once per call, in order, so the answer\n * always names exactly the parked calls (a partial map is refused\n * server-side and nothing runs). `null` when the batch cannot take\n * per-action answers: a call without a `tool_call_id`, or a live / multi-\n * lane approval, which resumes per lane and carries no edit.\n */\n decideEach: ((decision: (request: PendingActionRequest) => HitlActionDecision) => void) | null;\n}\n\nexport interface StatewireApprovalCardProps {\n /** Surface-styling overrides merged onto the default classes. */\n classNames?: {\n /** The approval card container. */\n root?: string;\n /** The \"approval was cancelled\" notice container. */\n abandoned?: string;\n /** The disclosed details block. */\n details?: string;\n /** The decision row. */\n actions?: string;\n };\n /** Copy shown when an interrupt payload carries no message. */\n fallbackMessage?: string;\n /**\n * Which pending interrupt this card answers. Defaults to\n * `isApprovalCardInterrupt` (client-tool parks excluded — keep it that way\n * unless the surface handles those itself).\n */\n interruptPredicate?: StatewireInterruptPredicate;\n /**\n * How long a clicked decision keeps the buttons locked when no resume run\n * ever starts (a `run/input` the host rejected before any run began).\n * Defaults to `HITL_PENDING_RESUME_GRACE_MS`.\n */\n pendingResumeGraceMs?: number;\n /**\n * Return true when another surface answers this request (a typed Athena\n * interrupt family, per-lane subagent approval cards). The card renders\n * nothing for it — two surfaces must never answer the same input request.\n */\n isHandledElsewhere?: (context: StatewireApprovalRequestContext) => boolean;\n /**\n * Replace the default argument disclosure (one JSON block per gated call)\n * with a host-specific review UI. Rendered inside the collapsible details\n * region; the decision buttons stay with the card.\n */\n renderDetails?: (context: StatewireApprovalRequestContext) => ReactNode;\n /** Replace the default approval icon and heading. Return null to keep it. */\n renderHeader?: (context: StatewireApprovalRequestContext) => ReactNode;\n /**\n * Replace BOTH the details region and the decision row with a host\n * composer that decides the request itself through the context's\n * callbacks (an editable email whose edits must be what runs). Return\n * `null`/`undefined` to keep the default card for this request. Not\n * consulted for read-only viewers or non-HITL parks.\n */\n renderEditor?: (context: StatewireApprovalEditorContext) => ReactNode;\n /**\n * The viewer may see the request (it explains why the run is parked) but\n * cannot decide it — answering steers the shared run. Renders\n * `readOnlyNotice` in place of the buttons.\n */\n readOnly?: boolean;\n readOnlyNotice?: ReactNode;\n /**\n * Copy for a park that is not a HITL approval — a typed Athena interrupt\n * this surface has no card for. The only honest action is to decline it\n * (`{ action: 'reject' }`, which every typed raiser treats as a clean user\n * decline); a generic \"Continue\" would be rejected by the raiser's resume\n * schema and surface as a tool error.\n */\n nonHitlNotice?: ReactNode;\n /**\n * The host refused a decision (or the transport lost it). The optimistic\n * fold has rolled back and the request is on screen again with its actions\n * re-enabled; this is where a host tells the user why (a toast, a log line).\n */\n onResumeRejected?: (error: unknown, requestId: string) => void;\n /**\n * The host's passkey decision check (identity 0b.9). An answer that lets\n * anything run is handed to it first and sent with the token it resolves\n * as `decisionCheck`; the decision buttons stay locked while it runs. An\n * answer that only rejects never is. Omit it and every answer is sent as\n * before, with no check.\n */\n confirmDecision?: StatewireDecisionConfirmer;\n}\n\nexport const StatewireApprovalCard: FC<StatewireApprovalCardProps> = (props) => {\n const extras = useAuiState((s) => s.thread.extras);\n if (!hasStatewireThreadExtras(extras)) return null;\n return <StatewireApprovalCardInner {...props} />;\n};\n\nconst StatewireApprovalCardInner: FC<StatewireApprovalCardProps> = ({\n classNames,\n fallbackMessage,\n interruptPredicate,\n pendingResumeGraceMs,\n isHandledElsewhere,\n renderDetails,\n renderHeader,\n renderEditor,\n readOnly = false,\n readOnlyNotice = 'Waiting for someone with edit access to respond.',\n nonHitlNotice = 'This request needs an answer this surface cannot collect.',\n onResumeRejected,\n confirmDecision,\n}) => {\n const approvalEpochRef = useRef(0);\n const [decisionFailure, setDecisionFailure] = useState<{\n requestId: string;\n message: string;\n epoch: number;\n }>();\n const reportResumeRejected = useCallback(\n (error: unknown, failedRequestId: string) => {\n setDecisionFailure({\n requestId: failedRequestId,\n message: statewireRejectionDetailMessage(error) ?? 'Your decision could not be sent. Try again.',\n epoch: approvalEpochRef.current,\n });\n onResumeRejected?.(error, failedRequestId);\n },\n [onResumeRejected],\n );\n const {\n request,\n requestId,\n hitl: parkedHitl,\n actionRequests: parkedActionRequests,\n liveHitl,\n liveActionRequests,\n queuedLaneDecisions,\n abandonedInterrupt,\n pending,\n resume,\n sendLaneDecisions,\n replayQueuedLanes,\n } = useStatewireApprovalRequest<StatewireThread.InputResponse>({\n interruptPredicate,\n pendingResumeGraceMs,\n onResumeRejected: reportResumeRejected,\n });\n // Read the host mirror: the optimistic resume fold can temporarily hide\n // `liveHitl` and the parked request without ending this approval.\n const mirroredApproval = useStatewireState(\n (state) => asHitlApproval(interruptMirrorPayload(readInterruptMirror(state))) !== null,\n );\n const approvalPresent = requestId !== undefined || mirroredApproval;\n const previousApprovalPresentRef = useRef(approvalPresent);\n if (previousApprovalPresentRef.current && !approvalPresent) approvalEpochRef.current += 1;\n previousApprovalPresentRef.current = approvalPresent;\n const [dismissedId, setDismissedId] = useState<string>();\n // The card shares the chat column with the thread. A lone gated call is\n // small enough to show inline, but a fan-out of a dozen calls would swallow\n // the conversation, so a batch starts collapsed until someone opens it.\n const [detailsOverride, setDetailsOverride] = useState<boolean>();\n // The live lanes a decision was sent for (joined ids); the buttons stay\n // locked until the host echoes them in `queuedLaneDecisions` or refuses.\n const [liveSentKey, setLiveSentKey] = useState<string>();\n // The parked request whose host-queued lanes outlived the grace window\n // (see `queuedLanesAwaitingHost` below): its queue is read as stale.\n const [staleQueuedRequestId, setStaleQueuedRequestId] = useState<string>();\n // The parked request whose queued lanes this card has asked the host to\n // replay (`run/lane-replay` in flight): locked until the host answers.\n const [replayingRequestId, setReplayingRequestId] = useState<string>();\n // The lanes THIS card decided live (its own `run/lane-input` the host\n // accepted). Only a queue this card recorded is replayed from here — the\n // host refuses any other caller, and a second editor's card must not even\n // ask. Pruned to the lanes on screen whenever a different view arrives, so\n // the record survives the live → parked transition of the same lanes (and\n // a fold that briefly shows nothing) and dies with a new request.\n const sentLaneIdsRef = useRef<Set<string>>(new Set());\n // The parked request already replayed once from here: a request is\n // replayed at most once, then the grace hands the decision back.\n const replayedRequestIdRef = useRef<string>(undefined);\n // A passkey check is running for the answer clicked here; the buttons stay\n // locked until it settles.\n const [confirming, setConfirming] = useState(false);\n // The parked request on screen now, read after a check settles: an answer\n // confirmed for a request that is no longer parked is never sent.\n const currentRequestIdRef = useRef(requestId);\n currentRequestIdRef.current = requestId;\n const confirmDecisionRef = useRef(confirmDecision);\n confirmDecisionRef.current = confirmDecision;\n\n const isLive = request === undefined && liveHitl !== null;\n const hitl = isLive ? liveHitl : parkedHitl;\n const actionRequests = isLive ? liveActionRequests : parkedActionRequests;\n const laneIds = laneInterruptIds(actionRequests);\n // The host answers the lanes it queued from its own settle path, within its\n // published budget of the park (`QUEUED_LANE_ANSWER_BUDGET_SECONDS`). A\n // parked request whose queued lanes are still unanswered past the grace\n // window has a silent answerer, and either this card asked the host to\n // replay them and was refused, or the queue is not this card's to replay —\n // so the queue no longer counts as a decision here: the actions re-enable\n // and the next click answers the parked request itself (a resume the host\n // accepts, and whose dispatch drops the stale queue).\n const hostQueuedLaneDecisions =\n requestId !== undefined && staleQueuedRequestId === requestId\n ? NO_HOST_QUEUED_LANE_DECISIONS\n : queuedLaneDecisions;\n const undecidedLaneIds =\n laneIds?.filter((id) => !(id in hostQueuedLaneDecisions)) ?? null;\n // A lone parked lane (or an unstamped batch) answers with one positional\n // `run/input`; that is the only resume the backend binds per-action answers\n // to, so it is the only place an edited call can go.\n const positional = laneIds === null || (!isLive && laneIds.length <= 1);\n const liveKey = isLive ? (laneIds?.join('|') ?? null) : null;\n const viewKey = requestId ?? liveKey ?? undefined;\n\n // A fresh approval gets the default for ITS batch size, not the disclosure\n // the previous one was left in. Reset during render via React's \"previous\n // value\" pattern.\n const prevViewKeyRef = useRef(viewKey);\n if (prevViewKeyRef.current !== viewKey) {\n prevViewKeyRef.current = viewKey;\n if (detailsOverride !== undefined) setDetailsOverride(undefined);\n if (liveSentKey !== undefined) setLiveSentKey(undefined);\n if (laneIds !== null) {\n for (const id of sentLaneIdsRef.current) {\n if (!laneIds.includes(id)) sentLaneIdsRef.current.delete(id);\n }\n }\n }\n // The per-request marks (stale queue, replayed once, replay in flight)\n // outlive the optimistic fold of a click's own `run/input`: the request\n // leaves and comes back under the SAME id when the host refuses it, and a\n // card that forgot its stale mark then would relock over the standing\n // queue for another grace, and could replay it a second time. They are\n // forgotten only for a genuinely different parked request.\n if (\n requestId !== undefined &&\n staleQueuedRequestId !== undefined &&\n requestId !== staleQueuedRequestId\n ) {\n setStaleQueuedRequestId(undefined);\n }\n if (\n requestId !== undefined &&\n replayingRequestId !== undefined &&\n requestId !== replayingRequestId\n ) {\n setReplayingRequestId(undefined);\n }\n if (\n requestId !== undefined &&\n replayedRequestIdRef.current !== undefined &&\n requestId !== replayedRequestIdRef.current\n ) {\n replayedRequestIdRef.current = undefined;\n }\n\n const title = pendingApprovalTitle({ hitl, actionRequests });\n const context: StatewireApprovalRequestContext = {\n request,\n hitl,\n actionRequests,\n ...(title ? { title } : {}),\n };\n const handledElsewhere = isHandledElsewhere?.(context) ?? false;\n const replaying = replayingRequestId !== undefined && replayingRequestId === requestId;\n\n // Parked, every lane the request covers already queued on the host, no\n // resume of our own in flight, and this card is the one that would decide\n // (not a viewer, not a request another surface owns): the host's answerer\n // is expected to resume the run within its budget. Start the clock on it,\n // longer than that budget. When it runs out the host has stayed silent: if\n // this card queued those lanes itself, it asks the host to replay them as\n // their approver (`run/lane-replay`); otherwise — and when the host refuses\n // the replay — the queue no longer counts as a decision here and the actions\n // re-enable, so a person decides. Never a `run/input` of this client's own\n // carrying someone else's recorded decision.\n const queuedLanesAwaitingHost =\n !isLive &&\n !readOnly &&\n !handledElsewhere &&\n requestId !== undefined &&\n undecidedLaneIds !== null &&\n undecidedLaneIds.length === 0 &&\n !pending &&\n !replaying;\n const queuedLaneGraceMs = pendingResumeGraceMs ?? HITL_PENDING_RESUME_GRACE_MS;\n const laneKey = laneIds?.join('|');\n const onResumeRejectedRef = useRef(reportResumeRejected);\n onResumeRejectedRef.current = reportResumeRejected;\n useEffect(() => {\n if (!queuedLanesAwaitingHost || requestId === undefined || laneKey === undefined) {\n return undefined;\n }\n const timer = setTimeout(() => {\n const ownQueue =\n laneKey.split('|').every((id) => sentLaneIdsRef.current.has(id)) &&\n replayedRequestIdRef.current !== requestId;\n if (!ownQueue) {\n setStaleQueuedRequestId(requestId);\n return;\n }\n replayedRequestIdRef.current = requestId;\n setReplayingRequestId(requestId);\n replayQueuedLanes(requestId).then(\n () => {\n setReplayingRequestId((current) => (current === requestId ? undefined : current));\n },\n (error: unknown) => {\n setReplayingRequestId((current) => (current === requestId ? undefined : current));\n setStaleQueuedRequestId(requestId);\n onResumeRejectedRef.current?.(error, requestId);\n },\n );\n }, queuedLaneGraceMs);\n return () => clearTimeout(timer);\n }, [queuedLanesAwaitingHost, requestId, laneKey, queuedLaneGraceMs, replayQueuedLanes]);\n\n /**\n * Send `answer` through `deliver`, with a passkey check first when it\n * approves and the host runs one. The check is the person's own act on\n * their device; while it is open the card is locked, and if the parked\n * request changed meanwhile the confirmed answer is dropped, never sent to\n * whatever parked next.\n */\n const withDecisionCheck = useCallback(\n (answer: StatewireDecisionAnswer, deliver: (extras?: ResumeExtras) => void) => {\n const confirmer = confirmDecisionRef.current;\n if (confirmer === undefined || !answerApproves(answer)) {\n deliver();\n return;\n }\n setConfirming(true);\n confirmer(answer)\n .catch(() => undefined)\n .then((token) => {\n setConfirming(false);\n if (answer.kind === 'input' && currentRequestIdRef.current !== answer.requestId) {\n return;\n }\n deliver(token ? { decisionCheck: token } : undefined);\n });\n },\n [],\n );\n\n // A live lane decision: the host queues it until the run parks, and holds\n // it for this card's caller, the only queue this card may ask it to replay.\n const sendLiveLanes = useCallback(\n ({\n key,\n lanes,\n epoch,\n extras,\n }: {\n key: string;\n lanes: Readonly<Record<string, StatewireThread.InputResponse>>;\n epoch: number;\n extras?: ResumeExtras;\n }) => {\n const sentLaneIds = key.split('|');\n setLiveSentKey(key);\n Promise.resolve(sendLaneDecisions(lanes, extras)).then(\n () => {\n if (epoch !== approvalEpochRef.current) return;\n for (const id of sentLaneIds) sentLaneIdsRef.current.add(id);\n },\n (error: unknown) => {\n if (epoch !== approvalEpochRef.current) return;\n setLiveSentKey((current) => (current === key ? undefined : current));\n reportResumeRejected(error, sentLaneIds[0] ?? '');\n },\n );\n },\n [sendLaneDecisions, reportResumeRejected],\n );\n\n const decide = useCallback(\n (value: Record<string, string>) => {\n setDecisionFailure(undefined);\n const epoch = approvalEpochRef.current;\n // Several parked lanes (or a live one) answer by interrupt id: a\n // positional `run/input` would resume only the first and re-park the\n // rest. A lone parked lane keeps the positional resume every host\n // already speaks.\n if (positional || undecidedLaneIds === null) {\n if (requestId === undefined) return;\n withDecisionCheck({ kind: 'input', requestId, value }, (extras) => {\n resume(value, extras);\n });\n return;\n }\n const lanes = fanLaneDecision({ interruptIds: undecidedLaneIds, decision: value });\n if (!isLive) {\n if (requestId === undefined) return;\n withDecisionCheck(\n { kind: 'input', requestId, value: { lane_decisions: lanes } },\n (extras) => {\n sendLaneDecisions(lanes, extras);\n },\n );\n return;\n }\n const key = undecidedLaneIds.join('|');\n withDecisionCheck({ kind: 'lanes', laneDecisions: lanes }, (extras) =>\n sendLiveLanes({ key, lanes, epoch, extras }),\n );\n },\n [\n positional,\n undecidedLaneIds,\n isLive,\n requestId,\n resume,\n sendLaneDecisions,\n sendLiveLanes,\n withDecisionCheck,\n ],\n );\n\n const decideEach = useMemo<StatewireApprovalEditorContext['decideEach']>(() => {\n if (actionRequestToolCallIds(actionRequests) === null || !positional) return null;\n return (decision) => {\n setDecisionFailure(undefined);\n const decisions: Record<string, HitlActionDecision> = {};\n for (const request of actionRequests) {\n if (request.toolCallId !== undefined) decisions[request.toolCallId] = decision(request);\n }\n // The edited argument set comes from the wire as JSON; the resume value\n // is that JSON going back.\n const value = hitlResumeActionDecisions(decisions) as StatewireThread.InputResponse;\n if (requestId === undefined) return;\n withDecisionCheck({ kind: 'input', requestId, value }, (extras) => {\n resume(value, extras);\n });\n };\n }, [actionRequests, positional, requestId, resume, withDecisionCheck]);\n\n if (!request && !isLive) {\n if (!abandonedInterrupt || abandonedInterrupt.id === dismissedId) return null;\n return (\n <div\n className={cn(\n 'aui-approval-abandoned flex w-full items-center justify-between gap-3 rounded-xl border border-border bg-muted/40 px-3 py-2 text-muted-foreground text-xs',\n classNames?.abandoned,\n )}\n >\n <p>Approval was cancelled — the run moved on.</p>\n <button\n type=\"button\"\n aria-label=\"Dismiss cancelled approval\"\n onClick={() => setDismissedId(abandonedInterrupt.id)}\n className=\"shrink-0 rounded-md p-1 transition-colors hover:bg-muted hover:text-foreground\"\n >\n <XIcon className=\"size-3.5\" />\n </button>\n </div>\n );\n }\n\n if (handledElsewhere) return null;\n // A live mirror without lane stamps cannot be answered before the run\n // parks; the parked request renders it then.\n if (isLive && laneIds === null) return null;\n\n const message = readInterruptMessage(request ? request.payload : liveHitl, fallbackMessage);\n const toolName = hitl?.context?.tool_name ?? hitl?.context?.tool_id;\n const pendingCount = hitl?.context?.pending_action_count ?? 1;\n const hasDetails = hitl !== null && actionRequests.length > 0;\n const showDetails = hasDetails && (detailsOverride ?? actionRequests.length <= 1);\n const sessionOffer = hitl !== null ? sessionApprovalOffer(actionRequests) : undefined;\n const sessionApprovalOffered = sessionOffer !== undefined;\n const sessionLabel = sessionOffer ? sessionApprovalLabel(sessionOffer) : '';\n const laneDecided =\n undecidedLaneIds !== null &&\n laneIds !== null &&\n (undecidedLaneIds.length === 0 || liveSentKey === undecidedLaneIds.join('|'));\n const locked = pending || laneDecided || replaying || confirming;\n\n const editor =\n !readOnly && hitl !== null && renderEditor\n ? renderEditor({\n ...context,\n locked,\n sessionApprovalOffered,\n sessionApprovalLabel: sessionLabel,\n approve: () => decide(hitlResumeApprove()),\n approveForSession: () => decide(hitlResumeApproveForSession()),\n reject: (reason) => decide(hitlResumeReject(reason)),\n decideEach,\n })\n : undefined;\n const customHeader = renderHeader?.(context);\n // Only the card's own review leads with the title: a host's details or\n // editor show the envelope themselves, headline included.\n const headerTitle = renderDetails === undefined && editor == null ? title : undefined;\n\n return (\n <section\n aria-label={hitl ? 'Approval required' : 'Input required'}\n className={cn(\n 'aui-approval-card w-full rounded-2xl border border-border bg-card px-4 py-3 text-foreground shadow-xs',\n classNames?.root,\n )}\n >\n <div className=\"flex items-start gap-3\">\n {customHeader != null ? (\n <div className=\"min-w-0 flex-1\">{customHeader}</div>\n ) : (\n <>\n <ShieldAlertIcon className=\"mt-0.5 size-4 shrink-0 text-muted-foreground\" />\n <div className=\"min-w-0 flex-1\">\n <p className=\"flex items-center gap-2 font-semibold text-sm\">\n <span>{hitl ? 'Approval required' : 'Waiting for input'}</span>\n {hitl && pendingCount > 1 ? (\n <span className=\"shrink-0 rounded-full border border-border bg-muted px-1.5 py-px font-normal text-[11px] text-muted-foreground\">\n {pendingCount} tool calls\n </span>\n ) : null}\n </p>\n {headerTitle ? (\n <>\n <p\n className=\"break-words pt-1 font-medium text-foreground text-sm leading-snug\"\n data-testid=\"statewire-approval-headline\"\n >\n {headerTitle.headline}\n </p>\n {headerTitle.summary ? (\n <p\n className=\"break-words pt-1 text-muted-foreground text-sm leading-snug\"\n data-testid=\"statewire-approval-summary\"\n >\n {headerTitle.summary}\n </p>\n ) : null}\n </>\n ) : (\n <p className=\"pt-1 text-muted-foreground text-sm leading-snug\">\n {hitl && pendingCount === 1 && toolName ? (\n <>\n <span className=\"font-mono text-foreground\">{toolName}</span> requires approval before it runs.\n </>\n ) : (\n message\n )}\n </p>\n )}\n </div>\n </>\n )}\n </div>\n {decisionFailure && decisionFailure.epoch === approvalEpochRef.current &&\n (decisionFailure.requestId === requestId || laneIds?.includes(decisionFailure.requestId)) ? (\n <p role=\"alert\" data-testid=\"statewire-approval-error\">{decisionFailure.message}</p>\n ) : null}\n {isLive ? (\n <p className=\"pt-1 text-muted-foreground text-xs\" data-testid=\"statewire-approval-live\">\n {laneDecided\n ? 'Decision sent — it applies as soon as this step pauses.'\n : 'Other work keeps running while you decide.'}\n </p>\n ) : null}\n {hasDetails && editor == null ? (\n <button\n type=\"button\"\n onClick={() => setDetailsOverride(!showDetails)}\n aria-expanded={showDetails}\n className=\"mt-2 flex items-center gap-1 rounded px-1 py-0.5 text-muted-foreground text-xs transition-colors hover:text-foreground\"\n >\n <ChevronDownIcon\n className={cn('size-3 transition-transform', showDetails && 'rotate-180')}\n />\n {showDetails ? 'Hide details' : 'Review details'}\n </button>\n ) : null}\n {/* EVERY pending gated call renders, in order — one decision\n authorizes the whole batch, so nothing may hide behind a host's\n richer cards. All read-only: this runtime resumes through\n `hitl_response_to_decisions`, which has no `tool_args` channel —\n an editable composer would let someone rewrite an email and then\n watch the original go out — unless the host takes over the\n decision too (`renderEditor`), which sends the edit per call. */}\n {editor != null ? (\n <div className={cn('mt-3 flex flex-col gap-2', classNames?.details)}>{editor}</div>\n ) : showDetails ? (\n <div className={cn('mt-2 flex flex-col gap-2', classNames?.details)}>\n {renderDetails ? (\n renderDetails(context)\n ) : (\n // A titled card no longer names its tool in the header, so its\n // details do, as a batch's do.\n <DefaultApprovalDetails\n actionRequests={actionRequests}\n showNames={actionRequests.length > 1 || headerTitle !== undefined}\n />\n )}\n </div>\n ) : null}\n {editor != null ? null : (\n <div className={cn('flex flex-wrap items-center gap-2 pt-3', classNames?.actions)}>\n {readOnly ? (\n <p className=\"text-muted-foreground text-sm\" data-testid=\"statewire-approval-read-only\">\n {readOnlyNotice}\n </p>\n ) : hitl ? (\n <>\n <Button\n size=\"sm\"\n disabled={locked}\n onClick={() => decide(hitlResumeApprove())}\n >\n <CheckIcon />\n Approve\n </Button>\n {sessionApprovalOffered ? (\n <Button\n size=\"sm\"\n variant=\"outline\"\n disabled={locked}\n onClick={() => decide(hitlResumeApproveForSession())}\n data-testid=\"statewire-approval-approve-session\"\n className=\"h-auto min-h-8 whitespace-normal py-1.5 text-left\"\n >\n <CheckCheckIcon />\n <span className=\"min-w-0 break-words\">{sessionLabel}</span>\n </Button>\n ) : null}\n <Button\n size=\"sm\"\n variant=\"outline\"\n disabled={locked}\n onClick={() => decide(hitlResumeReject())}\n >\n <XIcon />\n Reject\n </Button>\n </>\n ) : (\n <>\n <p className=\"text-muted-foreground text-sm\" data-testid=\"statewire-approval-non-hitl\">\n {nonHitlNotice}\n </p>\n <Button\n size=\"sm\"\n variant=\"outline\"\n disabled={pending}\n onClick={() => resume(interruptResumeDecline())}\n >\n <XIcon />\n Decline\n </Button>\n </>\n )}\n </div>\n )}\n </section>\n );\n};\n\n/**\n * What the backend resolved about a call before asking (where a Slack write\n * goes and as whom, Slack Connect warnings), above its raw arguments. Its\n * headline and summary title the card instead; with nothing else, nothing\n * renders here.\n */\nconst ApprovalContextFacts: FC<{ context: PendingApprovalContext }> = ({ context }) =>\n context.facts.length === 0 && context.warnings.length === 0 ? null : (\n <div className=\"mt-1 space-y-0.5\" data-testid=\"statewire-approval-context\">\n {context.facts.map((fact) => (\n <p key={fact.label}>\n <span className=\"font-semibold\">{fact.label}:</span> {fact.value}\n </p>\n ))}\n {context.warnings.map((warning) => (\n <p\n key={warning.message}\n className={warning.severity === 'info' ? undefined : 'font-semibold'}\n >\n {warning.message}\n </p>\n ))}\n </div>\n );\n\n/**\n * One block per gated call: its name (a batch's, or a titled call's), its\n * resolved facts, and its arguments as JSON.\n */\nconst DefaultApprovalDetails: FC<{ actionRequests: PendingActionRequest[]; showNames: boolean }> = ({\n actionRequests,\n showNames,\n}) => (\n <>\n {actionRequests.map((action, index) => (\n <div\n key={`${action.name}-${index}`}\n className=\"rounded-lg border border-border/60 bg-muted/40 p-2 text-foreground text-xs leading-relaxed\"\n >\n {showNames ? <p className=\"font-mono font-semibold\">{action.name}</p> : null}\n {action.approvalContext ? <ApprovalContextFacts context={action.approvalContext} /> : null}\n {Object.keys(action.args).length > 0 ? (\n <pre className=\"mt-1 max-h-32 overflow-auto whitespace-pre-wrap break-words rounded bg-background p-1.5 font-mono text-[11px]\">\n {JSON.stringify(action.args, null, 2)}\n </pre>\n ) : (\n <p className=\"text-muted-foreground\">No arguments.</p>\n )}\n </div>\n ))}\n </>\n);\n"],"names":["_a","request"],"mappings":"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"}
1
+ {"version":3,"file":"StatewireApprovalCard.js","sources":["../../src/chat/StatewireApprovalCard.tsx"],"sourcesContent":["import { useAuiState } from '@assistant-ui/react';\nimport {\n type StatewireThread,\n useStatewireRuns,\n useStatewireState,\n} from '@assistant-ui/react-statewire';\nimport {\n actionRequestToolCallIds,\n asHitlApproval,\n fanLaneDecision,\n HITL_PENDING_RESUME_GRACE_MS,\n type HitlActionDecision,\n type HitlApprovalPayload,\n hasStatewireThreadExtras,\n hitlResumeActionDecisions,\n hitlResumeApprove,\n hitlResumeApproveForSession,\n hitlResumeReject,\n interruptResumeDecline,\n interruptMirrorPayload,\n isApprovalCardInterrupt,\n laneInterruptIds,\n type PendingActionRequest,\n type PendingApprovalContext,\n type PendingApprovalTitle,\n pendingApprovalTitle,\n readInterruptMessage,\n readInterruptMirror,\n type ResumeExtras,\n resumeValueApproves,\n sessionApprovalLabel,\n sessionApprovalOffer,\n statewireRejectionDetailMessage,\n} from '@athenaintel/agent-runtime';\nimport {\n CheckCheckIcon,\n CheckIcon,\n ChevronDownIcon,\n ShieldAlertIcon,\n XIcon,\n} from 'lucide-react';\nimport {\n type FC,\n type ReactNode,\n useCallback,\n useEffect,\n useMemo,\n useRef,\n useState,\n} from 'react';\nimport { cn } from '../lib/utils';\nimport { Button } from '../ui/button';\nimport {\n type StatewireInterruptPredicate,\n useStatewireApprovalRequest,\n} from './use-statewire-approval-request';\n\n/**\n * Human-in-the-loop approval card for the statewire transport — the one\n * approval UI every Athena chat surface mounts (the SDK's `AthenaChat`, the\n * Chrome side panel, the Office task pane, Olympus).\n *\n * When the deep-agent runtime hits an approval-gated tool call, the backend\n * parks the run on an `interrupt` input request. This card reads that request\n * through `useStatewireApprovalRequest` and answers it with\n * `{ type: 'run/input', requestId, response: { type: 'resume', value } }` —\n * the exact command the backend's resume path consumes. Without an answer the\n * run stays parked forever, so this card must be mounted on every statewire\n * chat surface. On legacy (non-statewire) threads it renders nothing.\n *\n * A gated call raised inside a delegated subagent parks only its lane: the\n * host mirrors that interrupt while the sibling lanes keep streaming, before\n * any input request exists. The card renders the mirrored payload the same\n * way and answers it with `run/lane-input` keyed by the lane's langgraph\n * interrupt id (`laneInterruptIds`); the host queues the decision and applies\n * it the moment the run parks, so the approver never waits on the siblings.\n * Once parked, a payload whose calls all carry interrupt ids resumes as a\n * `lane_decisions` map too — one positional `run/input` can only answer the\n * first of several parked lanes.\n *\n * Recovery of a queued decision the host never applies is ordered host\n * first: the host's answerer resumes the park or drops (and flushes) the\n * queue within `QUEUED_LANE_ANSWER_BUDGET_SECONDS` of the park, and this\n * card's grace (`HITL_PENDING_RESUME_GRACE_MS`, longer than that budget)\n * fires only when the host stayed silent. When it fires, the card that sent\n * the queued decision asks the host to replay it (`run/lane-replay` — the\n * host resumes as the approver, under the meta it recorded, and refuses any\n * other caller); every other card, and a replay the host refuses, hands the\n * decision back to a person by unlocking the actions. A queued decision is\n * never re-sent as a `run/input` of the viewing client's own: that would run\n * the approver's decision under the viewer's identity and configuration.\n *\n * A lone gated call whose resolved envelope (`approval_context`) carries a\n * headline is titled by it in the card's own review: the headline replaces\n * \"`tool` requires approval before it runs\", the summary sits under it, and\n * the default details name the tool instead. A batch keeps the generic copy,\n * since one decision answers every call. So does a host review\n * (`renderDetails`, or an editor from `renderEditor`): it shows the envelope\n * itself, headline included, so the header must not say it again. Display-only:\n * the decision row and what it sends do not change.\n *\n * Host-specific review UIs (subagent cards, email summaries) slot in through\n * `renderDetails`; a host composer that must also OWN the decision (an\n * editable email whose edits have to reach the backend) takes over the\n * details and the decision row through `renderEditor`; requests another\n * surface answers (typed interrupt families, per-lane subagent approvals)\n * stand down through `isHandledElsewhere`; viewers without edit rights see\n * `readOnlyNotice`.\n *\n * A run parked on a typed Athena interrupt (the `ask` tool's questions, a\n * file request, a form, toolkits to turn on, a saved login, a schedule, a\n * wait, a tool-raised approval) gets that kind's own card when the host hands\n * one in as `typedInterrupts` (`statewireTypedInterrupts` from\n * `@athenaintel/react/typed-interrupts`, which `AthenaChat` passes): the card\n * answers with the resume shape the raiser validates, under the same props\n * (`isHandledElsewhere` and `readOnly` apply to it, an approve goes through\n * `confirmDecision`, a refusal reaches `onResumeRejected`). Without it, as on\n * a host whose own cards answer typed parks (Olympus), a typed park is\n * answered only with `nonHitlNotice`'s decline, as is any park that is\n * neither.\n */\n\n/**\n * The answer a passkey decision check confirms before the card sends it\n * (identity 0b.9): a `run/input` resume of the parked request, or the lane\n * decisions of a `run/lane-input` sent while sibling lanes still stream.\n */\nexport type StatewireDecisionAnswer =\n | {\n readonly kind: 'input';\n readonly requestId: string;\n readonly value: StatewireThread.InputResponse;\n }\n | {\n readonly kind: 'lanes';\n readonly laneDecisions: Readonly<Record<string, StatewireThread.InputResponse>>;\n };\n\n/**\n * Runs the host's passkey check for an approving answer and resolves its\n * token, or `undefined` to send the answer without one. While checks are\n * report-only, an answer goes ahead without a check (no passkey yet, a\n * cancelled prompt); the host decides what to tell the person. Never called\n * for an answer that only rejects.\n */\nexport type StatewireDecisionConfirmer = (\n answer: StatewireDecisionAnswer,\n) => Promise<string | undefined>;\n\nfunction answerApproves(answer: StatewireDecisionAnswer): boolean {\n if (answer.kind === 'input') return resumeValueApproves(answer.value);\n const lanes = Object.values(answer.laneDecisions);\n return lanes.length === 0 || lanes.some(resumeValueApproves);\n}\n\n/** What the card reads in place of the host's queued lanes once it has given up on them. */\nconst NO_HOST_QUEUED_LANE_DECISIONS: Readonly<Record<string, unknown>> = Object.freeze({});\n\n/** The pending request a host slot renders or judges. */\nexport interface StatewireApprovalRequestContext {\n /** The parked input request — `undefined` while the run still streams (a live lane approval). */\n request: StatewireThread.CustomInputRequest | undefined;\n /** The payload narrowed to the Athena HITL approval shape, or `null` for a generic park. */\n hitl: HitlApprovalPayload | null;\n /** Every gated call the approval covers, in decision order (empty for non-HITL parks). */\n actionRequests: PendingActionRequest[];\n /**\n * The approval's title (`pendingApprovalTitle`): a lone call's envelope\n * headline and summary. Absent for a batch, a non-HITL park and a call\n * without one. The default header shows it only above the card's own\n * details; under a host review the host shows the envelope, and may lead\n * with this.\n */\n title?: PendingApprovalTitle;\n}\n\n/** The request a host editor renders, plus the decisions it may send for it. */\nexport interface StatewireApprovalEditorContext extends StatewireApprovalRequestContext {\n /** A decision is in flight (or a live lane already answered); the editor must not send another. */\n locked: boolean;\n /** Whether a session-wide approval may be offered for this batch. */\n sessionApprovalOffered: boolean;\n /**\n * What the session option's button says, naming exactly what the answer\n * covers (`sessionApprovalLabel`): \"Approve all for this session\" for\n * tools, or \"Approve for this session: only kyle@… and sam@…\" for sends\n * scoped to their recipients. Meaningful only when `sessionApprovalOffered`.\n */\n sessionApprovalLabel: string;\n approve: () => void;\n approveForSession: () => void;\n reject: (reason?: string) => void;\n /**\n * Answer each gated call on its own — the only way an EDITED call reaches\n * the backend. `decision` is asked once per call, in order, so the answer\n * always names exactly the parked calls (a partial map is refused\n * server-side and nothing runs). `null` when the batch cannot take\n * per-action answers: a call without a `tool_call_id`, or a live / multi-\n * lane approval, which resumes per lane and carries no edit.\n */\n decideEach: ((decision: (request: PendingActionRequest) => HitlActionDecision) => void) | null;\n}\n\n/** The approval card's own props it hands the typed card (`StatewireTypedInterruptSeam.render`). */\nexport interface StatewireTypedInterruptCardProps {\n /** Surface-styling override for the card's container. */\n classNames?: { root?: string };\n /** A viewer without edit rights: the park's message and `readOnlyNotice`, no controls. */\n readOnly?: boolean;\n readOnlyNotice?: ReactNode;\n /**\n * Return true when another surface answers this request: the card renders\n * nothing for it, since two surfaces must never answer one request.\n */\n isHandledElsewhere?: (context: StatewireApprovalRequestContext) => boolean;\n /** The host's passkey decision check, for an answer that approves a typed approval. */\n confirmDecision?: StatewireDecisionConfirmer;\n /** The host refused an answer; the card is back with its controls and says why. */\n onResumeRejected?: (error: unknown, requestId: string) => void;\n pendingResumeGraceMs?: number;\n}\n\n/**\n * A card for typed Athena interrupts, handed to `StatewireApprovalCard` as\n * `typedInterrupts`: which parks it answers, and the card. The SDK's is\n * `statewireTypedInterrupts` from `@athenaintel/react/typed-interrupts`.\n */\nexport interface StatewireTypedInterruptSeam {\n /** The parks the typed card answers; the approval card leaves them to it. */\n isTypedRequest: StatewireInterruptPredicate;\n /** The typed card, given the approval card's own props. */\n render: (props: StatewireTypedInterruptCardProps) => ReactNode;\n}\n\nexport interface StatewireApprovalCardProps {\n /** Surface-styling overrides merged onto the default classes. */\n classNames?: {\n /** The approval card container. */\n root?: string;\n /** The \"approval was cancelled\" notice container. */\n abandoned?: string;\n /** The disclosed details block. */\n details?: string;\n /** The decision row. */\n actions?: string;\n };\n /** Copy shown when an interrupt payload carries no message. */\n fallbackMessage?: string;\n /**\n * Which pending interrupt this card answers. Defaults to\n * `isApprovalCardInterrupt` (client-tool parks excluded — keep it that way\n * unless the surface handles those itself).\n */\n interruptPredicate?: StatewireInterruptPredicate;\n /**\n * How long a clicked decision keeps the buttons locked when no resume run\n * ever starts (a `run/input` the host rejected before any run began).\n * Defaults to `HITL_PENDING_RESUME_GRACE_MS`.\n */\n pendingResumeGraceMs?: number;\n /**\n * Return true when another surface answers this request (a typed Athena\n * interrupt family, per-lane subagent approval cards). The card renders\n * nothing for it — two surfaces must never answer the same input request.\n */\n isHandledElsewhere?: (context: StatewireApprovalRequestContext) => boolean;\n /**\n * Replace the default argument disclosure (one JSON block per gated call)\n * with a host-specific review UI. Rendered inside the collapsible details\n * region; the decision buttons stay with the card.\n */\n renderDetails?: (context: StatewireApprovalRequestContext) => ReactNode;\n /** Replace the default approval icon and heading. Return null to keep it. */\n renderHeader?: (context: StatewireApprovalRequestContext) => ReactNode;\n /**\n * Replace BOTH the details region and the decision row with a host\n * composer that decides the request itself through the context's\n * callbacks (an editable email whose edits must be what runs). Return\n * `null`/`undefined` to keep the default card for this request. Not\n * consulted for read-only viewers or non-HITL parks.\n */\n renderEditor?: (context: StatewireApprovalEditorContext) => ReactNode;\n /**\n * The viewer may see the request (it explains why the run is parked) but\n * cannot decide it — answering steers the shared run. Renders\n * `readOnlyNotice` in place of the buttons.\n */\n readOnly?: boolean;\n readOnlyNotice?: ReactNode;\n /**\n * Copy for a park that is not a HITL approval and that no typed card\n * (`typedInterrupts`) answers. The only honest action is to decline it\n * (`{ action: 'reject' }`, which every typed raiser treats as a clean user\n * decline); a generic \"Continue\" would be rejected by the raiser's resume\n * schema and surface as a tool error.\n */\n nonHitlNotice?: ReactNode;\n /**\n * The host refused a decision (or the transport lost it). The optimistic\n * fold has rolled back and the request is on screen again with its actions\n * re-enabled; this is where a host tells the user why (a toast, a log line).\n */\n onResumeRejected?: (error: unknown, requestId: string) => void;\n /**\n * The host's passkey decision check (identity 0b.9). An answer that lets\n * anything run is handed to it first and sent with the token it resolves\n * as `decisionCheck`; the decision buttons stay locked while it runs. An\n * answer that only rejects never is. Omit it and every answer is sent as\n * before, with no check.\n */\n confirmDecision?: StatewireDecisionConfirmer;\n /**\n * The card for typed Athena interrupts and the parks it answers:\n * `statewireTypedInterrupts` from `@athenaintel/react/typed-interrupts`, as\n * `AthenaChat` passes it. With it, this card leaves typed parks to that one\n * and hands it its own props; without it, a typed park gets\n * `nonHitlNotice` and a decline. A seam rather than a built-in, so a host\n * whose own cards answer typed parks (Olympus) bundles neither the SDK's\n * cards nor its selector.\n */\n typedInterrupts?: StatewireTypedInterruptSeam;\n}\n\nexport const StatewireApprovalCard: FC<StatewireApprovalCardProps> = (props) => {\n const extras = useAuiState((s) => s.thread.extras);\n if (!hasStatewireThreadExtras(extras)) return null;\n const { typedInterrupts } = props;\n if (!typedInterrupts) return <StatewireApprovalCardInner {...props} />;\n const {\n classNames,\n readOnly,\n readOnlyNotice,\n isHandledElsewhere,\n confirmDecision,\n onResumeRejected,\n pendingResumeGraceMs,\n } = props;\n return (\n <>\n <StatewireApprovalCardInner {...props} />\n {typedInterrupts.render({\n ...(classNames?.root ? { classNames: { root: classNames.root } } : {}),\n readOnly,\n readOnlyNotice,\n isHandledElsewhere,\n confirmDecision,\n onResumeRejected,\n pendingResumeGraceMs,\n })}\n </>\n );\n};\n\nconst StatewireApprovalCardInner: FC<StatewireApprovalCardProps> = ({\n classNames,\n fallbackMessage,\n interruptPredicate,\n pendingResumeGraceMs,\n isHandledElsewhere,\n renderDetails,\n renderHeader,\n renderEditor,\n readOnly = false,\n readOnlyNotice = 'Waiting for someone with edit access to respond.',\n nonHitlNotice = 'This request needs an answer this surface cannot collect.',\n onResumeRejected,\n confirmDecision,\n typedInterrupts,\n}) => {\n const isTypedRequest = typedInterrupts?.isTypedRequest;\n // With a typed card beside it, this card's own selection is every pending\n // approval-card interrupt but a typed one.\n const selectRequest = useMemo<StatewireInterruptPredicate | undefined>(() => {\n if (interruptPredicate || !isTypedRequest) return interruptPredicate;\n return (request): request is StatewireThread.CustomInputRequest =>\n isApprovalCardInterrupt(request) && !isTypedRequest(request);\n }, [interruptPredicate, isTypedRequest]);\n const approvalEpochRef = useRef(0);\n const [decisionFailure, setDecisionFailure] = useState<{\n requestId: string;\n message: string;\n epoch: number;\n }>();\n const reportResumeRejected = useCallback(\n (error: unknown, failedRequestId: string) => {\n setDecisionFailure({\n requestId: failedRequestId,\n message: statewireRejectionDetailMessage(error) ?? 'Your decision could not be sent. Try again.',\n epoch: approvalEpochRef.current,\n });\n onResumeRejected?.(error, failedRequestId);\n },\n [onResumeRejected],\n );\n const {\n request,\n requestId,\n hitl: parkedHitl,\n actionRequests: parkedActionRequests,\n liveHitl,\n liveActionRequests,\n queuedLaneDecisions,\n abandonedInterrupt,\n pending,\n resume,\n sendLaneDecisions,\n replayQueuedLanes,\n } = useStatewireApprovalRequest<StatewireThread.InputResponse>({\n interruptPredicate: selectRequest,\n pendingResumeGraceMs,\n onResumeRejected: reportResumeRejected,\n });\n // Read the host mirror: the optimistic resume fold can temporarily hide\n // `liveHitl` and the parked request without ending this approval.\n const mirroredApproval = useStatewireState(\n (state) => asHitlApproval(interruptMirrorPayload(readInterruptMirror(state))) !== null,\n );\n const approvalPresent = requestId !== undefined || mirroredApproval;\n // A typed park the typed card answers beside this one: an older cancelled\n // approval's notice waits until nothing is parked, as it did before.\n const inputRequests = useStatewireRuns().inputRequests;\n const typedParkPending =\n isTypedRequest !== undefined && (inputRequests?.some((pendingRequest) => isTypedRequest(pendingRequest)) ?? false);\n const previousApprovalPresentRef = useRef(approvalPresent);\n if (previousApprovalPresentRef.current && !approvalPresent) approvalEpochRef.current += 1;\n previousApprovalPresentRef.current = approvalPresent;\n const [dismissedId, setDismissedId] = useState<string>();\n // The card shares the chat column with the thread. A lone gated call is\n // small enough to show inline, but a fan-out of a dozen calls would swallow\n // the conversation, so a batch starts collapsed until someone opens it.\n const [detailsOverride, setDetailsOverride] = useState<boolean>();\n // The live lanes a decision was sent for (joined ids); the buttons stay\n // locked until the host echoes them in `queuedLaneDecisions` or refuses.\n const [liveSentKey, setLiveSentKey] = useState<string>();\n // The parked request whose host-queued lanes outlived the grace window\n // (see `queuedLanesAwaitingHost` below): its queue is read as stale.\n const [staleQueuedRequestId, setStaleQueuedRequestId] = useState<string>();\n // The parked request whose queued lanes this card has asked the host to\n // replay (`run/lane-replay` in flight): locked until the host answers.\n const [replayingRequestId, setReplayingRequestId] = useState<string>();\n // The lanes THIS card decided live (its own `run/lane-input` the host\n // accepted). Only a queue this card recorded is replayed from here — the\n // host refuses any other caller, and a second editor's card must not even\n // ask. Pruned to the lanes on screen whenever a different view arrives, so\n // the record survives the live → parked transition of the same lanes (and\n // a fold that briefly shows nothing) and dies with a new request.\n const sentLaneIdsRef = useRef<Set<string>>(new Set());\n // The parked request already replayed once from here: a request is\n // replayed at most once, then the grace hands the decision back.\n const replayedRequestIdRef = useRef<string>(undefined);\n // A passkey check is running for the answer clicked here; the buttons stay\n // locked until it settles.\n const [confirming, setConfirming] = useState(false);\n // The parked request on screen now, read after a check settles: an answer\n // confirmed for a request that is no longer parked is never sent.\n const currentRequestIdRef = useRef(requestId);\n currentRequestIdRef.current = requestId;\n const confirmDecisionRef = useRef(confirmDecision);\n confirmDecisionRef.current = confirmDecision;\n\n const isLive = request === undefined && liveHitl !== null;\n const hitl = isLive ? liveHitl : parkedHitl;\n const actionRequests = isLive ? liveActionRequests : parkedActionRequests;\n const laneIds = laneInterruptIds(actionRequests);\n // The host answers the lanes it queued from its own settle path, within its\n // published budget of the park (`QUEUED_LANE_ANSWER_BUDGET_SECONDS`). A\n // parked request whose queued lanes are still unanswered past the grace\n // window has a silent answerer, and either this card asked the host to\n // replay them and was refused, or the queue is not this card's to replay —\n // so the queue no longer counts as a decision here: the actions re-enable\n // and the next click answers the parked request itself (a resume the host\n // accepts, and whose dispatch drops the stale queue).\n const hostQueuedLaneDecisions =\n requestId !== undefined && staleQueuedRequestId === requestId\n ? NO_HOST_QUEUED_LANE_DECISIONS\n : queuedLaneDecisions;\n const undecidedLaneIds =\n laneIds?.filter((id) => !(id in hostQueuedLaneDecisions)) ?? null;\n // A lone parked lane (or an unstamped batch) answers with one positional\n // `run/input`; that is the only resume the backend binds per-action answers\n // to, so it is the only place an edited call can go.\n const positional = laneIds === null || (!isLive && laneIds.length <= 1);\n const liveKey = isLive ? (laneIds?.join('|') ?? null) : null;\n const viewKey = requestId ?? liveKey ?? undefined;\n\n // A fresh approval gets the default for ITS batch size, not the disclosure\n // the previous one was left in. Reset during render via React's \"previous\n // value\" pattern.\n const prevViewKeyRef = useRef(viewKey);\n if (prevViewKeyRef.current !== viewKey) {\n prevViewKeyRef.current = viewKey;\n if (detailsOverride !== undefined) setDetailsOverride(undefined);\n if (liveSentKey !== undefined) setLiveSentKey(undefined);\n if (laneIds !== null) {\n for (const id of sentLaneIdsRef.current) {\n if (!laneIds.includes(id)) sentLaneIdsRef.current.delete(id);\n }\n }\n }\n // The per-request marks (stale queue, replayed once, replay in flight)\n // outlive the optimistic fold of a click's own `run/input`: the request\n // leaves and comes back under the SAME id when the host refuses it, and a\n // card that forgot its stale mark then would relock over the standing\n // queue for another grace, and could replay it a second time. They are\n // forgotten only for a genuinely different parked request.\n if (\n requestId !== undefined &&\n staleQueuedRequestId !== undefined &&\n requestId !== staleQueuedRequestId\n ) {\n setStaleQueuedRequestId(undefined);\n }\n if (\n requestId !== undefined &&\n replayingRequestId !== undefined &&\n requestId !== replayingRequestId\n ) {\n setReplayingRequestId(undefined);\n }\n if (\n requestId !== undefined &&\n replayedRequestIdRef.current !== undefined &&\n requestId !== replayedRequestIdRef.current\n ) {\n replayedRequestIdRef.current = undefined;\n }\n\n const title = pendingApprovalTitle({ hitl, actionRequests });\n const context: StatewireApprovalRequestContext = {\n request,\n hitl,\n actionRequests,\n ...(title ? { title } : {}),\n };\n const handledElsewhere = isHandledElsewhere?.(context) ?? false;\n const replaying = replayingRequestId !== undefined && replayingRequestId === requestId;\n\n // Parked, every lane the request covers already queued on the host, no\n // resume of our own in flight, and this card is the one that would decide\n // (not a viewer, not a request another surface owns): the host's answerer\n // is expected to resume the run within its budget. Start the clock on it,\n // longer than that budget. When it runs out the host has stayed silent: if\n // this card queued those lanes itself, it asks the host to replay them as\n // their approver (`run/lane-replay`); otherwise — and when the host refuses\n // the replay — the queue no longer counts as a decision here and the actions\n // re-enable, so a person decides. Never a `run/input` of this client's own\n // carrying someone else's recorded decision.\n const queuedLanesAwaitingHost =\n !isLive &&\n !readOnly &&\n !handledElsewhere &&\n requestId !== undefined &&\n undecidedLaneIds !== null &&\n undecidedLaneIds.length === 0 &&\n !pending &&\n !replaying;\n const queuedLaneGraceMs = pendingResumeGraceMs ?? HITL_PENDING_RESUME_GRACE_MS;\n const laneKey = laneIds?.join('|');\n const onResumeRejectedRef = useRef(reportResumeRejected);\n onResumeRejectedRef.current = reportResumeRejected;\n useEffect(() => {\n if (!queuedLanesAwaitingHost || requestId === undefined || laneKey === undefined) {\n return undefined;\n }\n const timer = setTimeout(() => {\n const ownQueue =\n laneKey.split('|').every((id) => sentLaneIdsRef.current.has(id)) &&\n replayedRequestIdRef.current !== requestId;\n if (!ownQueue) {\n setStaleQueuedRequestId(requestId);\n return;\n }\n replayedRequestIdRef.current = requestId;\n setReplayingRequestId(requestId);\n replayQueuedLanes(requestId).then(\n () => {\n setReplayingRequestId((current) => (current === requestId ? undefined : current));\n },\n (error: unknown) => {\n setReplayingRequestId((current) => (current === requestId ? undefined : current));\n setStaleQueuedRequestId(requestId);\n onResumeRejectedRef.current?.(error, requestId);\n },\n );\n }, queuedLaneGraceMs);\n return () => clearTimeout(timer);\n }, [queuedLanesAwaitingHost, requestId, laneKey, queuedLaneGraceMs, replayQueuedLanes]);\n\n /**\n * Send `answer` through `deliver`, with a passkey check first when it\n * approves and the host runs one. The check is the person's own act on\n * their device; while it is open the card is locked, and if the parked\n * request changed meanwhile the confirmed answer is dropped, never sent to\n * whatever parked next.\n */\n const withDecisionCheck = useCallback(\n (answer: StatewireDecisionAnswer, deliver: (extras?: ResumeExtras) => void) => {\n const confirmer = confirmDecisionRef.current;\n if (confirmer === undefined || !answerApproves(answer)) {\n deliver();\n return;\n }\n setConfirming(true);\n confirmer(answer)\n .catch(() => undefined)\n .then((token) => {\n setConfirming(false);\n if (answer.kind === 'input' && currentRequestIdRef.current !== answer.requestId) {\n return;\n }\n deliver(token ? { decisionCheck: token } : undefined);\n });\n },\n [],\n );\n\n // A live lane decision: the host queues it until the run parks, and holds\n // it for this card's caller, the only queue this card may ask it to replay.\n const sendLiveLanes = useCallback(\n ({\n key,\n lanes,\n epoch,\n extras,\n }: {\n key: string;\n lanes: Readonly<Record<string, StatewireThread.InputResponse>>;\n epoch: number;\n extras?: ResumeExtras;\n }) => {\n const sentLaneIds = key.split('|');\n setLiveSentKey(key);\n Promise.resolve(sendLaneDecisions(lanes, extras)).then(\n () => {\n if (epoch !== approvalEpochRef.current) return;\n for (const id of sentLaneIds) sentLaneIdsRef.current.add(id);\n },\n (error: unknown) => {\n if (epoch !== approvalEpochRef.current) return;\n setLiveSentKey((current) => (current === key ? undefined : current));\n reportResumeRejected(error, sentLaneIds[0] ?? '');\n },\n );\n },\n [sendLaneDecisions, reportResumeRejected],\n );\n\n const decide = useCallback(\n (value: Record<string, string>) => {\n setDecisionFailure(undefined);\n const epoch = approvalEpochRef.current;\n // Several parked lanes (or a live one) answer by interrupt id: a\n // positional `run/input` would resume only the first and re-park the\n // rest. A lone parked lane keeps the positional resume every host\n // already speaks.\n if (positional || undecidedLaneIds === null) {\n if (requestId === undefined) return;\n withDecisionCheck({ kind: 'input', requestId, value }, (extras) => {\n resume(value, extras);\n });\n return;\n }\n const lanes = fanLaneDecision({ interruptIds: undecidedLaneIds, decision: value });\n if (!isLive) {\n if (requestId === undefined) return;\n withDecisionCheck(\n { kind: 'input', requestId, value: { lane_decisions: lanes } },\n (extras) => {\n sendLaneDecisions(lanes, extras);\n },\n );\n return;\n }\n const key = undecidedLaneIds.join('|');\n withDecisionCheck({ kind: 'lanes', laneDecisions: lanes }, (extras) =>\n sendLiveLanes({ key, lanes, epoch, extras }),\n );\n },\n [\n positional,\n undecidedLaneIds,\n isLive,\n requestId,\n resume,\n sendLaneDecisions,\n sendLiveLanes,\n withDecisionCheck,\n ],\n );\n\n const decideEach = useMemo<StatewireApprovalEditorContext['decideEach']>(() => {\n if (actionRequestToolCallIds(actionRequests) === null || !positional) return null;\n return (decision) => {\n setDecisionFailure(undefined);\n const decisions: Record<string, HitlActionDecision> = {};\n for (const request of actionRequests) {\n if (request.toolCallId !== undefined) decisions[request.toolCallId] = decision(request);\n }\n // The edited argument set comes from the wire as JSON; the resume value\n // is that JSON going back.\n const value = hitlResumeActionDecisions(decisions) as StatewireThread.InputResponse;\n if (requestId === undefined) return;\n withDecisionCheck({ kind: 'input', requestId, value }, (extras) => {\n resume(value, extras);\n });\n };\n }, [actionRequests, positional, requestId, resume, withDecisionCheck]);\n\n if (!request && !isLive) {\n if (!abandonedInterrupt || abandonedInterrupt.id === dismissedId || typedParkPending) return null;\n return (\n <div\n className={cn(\n 'aui-approval-abandoned flex w-full items-center justify-between gap-3 rounded-xl border border-border bg-muted/40 px-3 py-2 text-muted-foreground text-xs',\n classNames?.abandoned,\n )}\n >\n <p>Approval was cancelled — the run moved on.</p>\n <button\n type=\"button\"\n aria-label=\"Dismiss cancelled approval\"\n onClick={() => setDismissedId(abandonedInterrupt.id)}\n className=\"shrink-0 rounded-md p-1 transition-colors hover:bg-muted hover:text-foreground\"\n >\n <XIcon className=\"size-3.5\" />\n </button>\n </div>\n );\n }\n\n if (handledElsewhere) return null;\n // A live mirror without lane stamps cannot be answered before the run\n // parks; the parked request renders it then.\n if (isLive && laneIds === null) return null;\n\n const message = readInterruptMessage(request ? request.payload : liveHitl, fallbackMessage);\n const toolName = hitl?.context?.tool_name ?? hitl?.context?.tool_id;\n const pendingCount = hitl?.context?.pending_action_count ?? 1;\n const hasDetails = hitl !== null && actionRequests.length > 0;\n const showDetails = hasDetails && (detailsOverride ?? actionRequests.length <= 1);\n const sessionOffer = hitl !== null ? sessionApprovalOffer(actionRequests) : undefined;\n const sessionApprovalOffered = sessionOffer !== undefined;\n const sessionLabel = sessionOffer ? sessionApprovalLabel(sessionOffer) : '';\n const laneDecided =\n undecidedLaneIds !== null &&\n laneIds !== null &&\n (undecidedLaneIds.length === 0 || liveSentKey === undecidedLaneIds.join('|'));\n const locked = pending || laneDecided || replaying || confirming;\n\n const editor =\n !readOnly && hitl !== null && renderEditor\n ? renderEditor({\n ...context,\n locked,\n sessionApprovalOffered,\n sessionApprovalLabel: sessionLabel,\n approve: () => decide(hitlResumeApprove()),\n approveForSession: () => decide(hitlResumeApproveForSession()),\n reject: (reason) => decide(hitlResumeReject(reason)),\n decideEach,\n })\n : undefined;\n const customHeader = renderHeader?.(context);\n // Only the card's own review leads with the title: a host's details or\n // editor show the envelope themselves, headline included.\n const headerTitle = renderDetails === undefined && editor == null ? title : undefined;\n\n return (\n <section\n aria-label={hitl ? 'Approval required' : 'Input required'}\n className={cn(\n 'aui-approval-card w-full rounded-2xl border border-border bg-card px-4 py-3 text-foreground shadow-xs',\n classNames?.root,\n )}\n >\n <div className=\"flex items-start gap-3\">\n {customHeader != null ? (\n <div className=\"min-w-0 flex-1\">{customHeader}</div>\n ) : (\n <>\n <ShieldAlertIcon className=\"mt-0.5 size-4 shrink-0 text-muted-foreground\" />\n <div className=\"min-w-0 flex-1\">\n <p className=\"flex items-center gap-2 font-semibold text-sm\">\n <span>{hitl ? 'Approval required' : 'Waiting for input'}</span>\n {hitl && pendingCount > 1 ? (\n <span className=\"shrink-0 rounded-full border border-border bg-muted px-1.5 py-px font-normal text-[11px] text-muted-foreground\">\n {pendingCount} tool calls\n </span>\n ) : null}\n </p>\n {headerTitle ? (\n <>\n <p\n className=\"break-words pt-1 font-medium text-foreground text-sm leading-snug\"\n data-testid=\"statewire-approval-headline\"\n >\n {headerTitle.headline}\n </p>\n {headerTitle.summary ? (\n <p\n className=\"break-words pt-1 text-muted-foreground text-sm leading-snug\"\n data-testid=\"statewire-approval-summary\"\n >\n {headerTitle.summary}\n </p>\n ) : null}\n </>\n ) : (\n <p className=\"pt-1 text-muted-foreground text-sm leading-snug\">\n {hitl && pendingCount === 1 && toolName ? (\n <>\n <span className=\"font-mono text-foreground\">{toolName}</span> requires approval before it runs.\n </>\n ) : (\n message\n )}\n </p>\n )}\n </div>\n </>\n )}\n </div>\n {decisionFailure && decisionFailure.epoch === approvalEpochRef.current &&\n (decisionFailure.requestId === requestId || laneIds?.includes(decisionFailure.requestId)) ? (\n <p role=\"alert\" data-testid=\"statewire-approval-error\">{decisionFailure.message}</p>\n ) : null}\n {isLive ? (\n <p className=\"pt-1 text-muted-foreground text-xs\" data-testid=\"statewire-approval-live\">\n {laneDecided\n ? 'Decision sent — it applies as soon as this step pauses.'\n : 'Other work keeps running while you decide.'}\n </p>\n ) : null}\n {hasDetails && editor == null ? (\n <button\n type=\"button\"\n onClick={() => setDetailsOverride(!showDetails)}\n aria-expanded={showDetails}\n className=\"mt-2 flex items-center gap-1 rounded px-1 py-0.5 text-muted-foreground text-xs transition-colors hover:text-foreground\"\n >\n <ChevronDownIcon\n className={cn('size-3 transition-transform', showDetails && 'rotate-180')}\n />\n {showDetails ? 'Hide details' : 'Review details'}\n </button>\n ) : null}\n {/* EVERY pending gated call renders, in order — one decision\n authorizes the whole batch, so nothing may hide behind a host's\n richer cards. All read-only: this runtime resumes through\n `hitl_response_to_decisions`, which has no `tool_args` channel —\n an editable composer would let someone rewrite an email and then\n watch the original go out — unless the host takes over the\n decision too (`renderEditor`), which sends the edit per call. */}\n {editor != null ? (\n <div className={cn('mt-3 flex flex-col gap-2', classNames?.details)}>{editor}</div>\n ) : showDetails ? (\n <div className={cn('mt-2 flex flex-col gap-2', classNames?.details)}>\n {renderDetails ? (\n renderDetails(context)\n ) : (\n // A titled card no longer names its tool in the header, so its\n // details do, as a batch's do.\n <DefaultApprovalDetails\n actionRequests={actionRequests}\n showNames={actionRequests.length > 1 || headerTitle !== undefined}\n />\n )}\n </div>\n ) : null}\n {editor != null ? null : (\n <div className={cn('flex flex-wrap items-center gap-2 pt-3', classNames?.actions)}>\n {readOnly ? (\n <p className=\"text-muted-foreground text-sm\" data-testid=\"statewire-approval-read-only\">\n {readOnlyNotice}\n </p>\n ) : hitl ? (\n <>\n <Button\n size=\"sm\"\n disabled={locked}\n onClick={() => decide(hitlResumeApprove())}\n >\n <CheckIcon />\n Approve\n </Button>\n {sessionApprovalOffered ? (\n <Button\n size=\"sm\"\n variant=\"outline\"\n disabled={locked}\n onClick={() => decide(hitlResumeApproveForSession())}\n data-testid=\"statewire-approval-approve-session\"\n className=\"h-auto min-h-8 whitespace-normal py-1.5 text-left\"\n >\n <CheckCheckIcon />\n <span className=\"min-w-0 break-words\">{sessionLabel}</span>\n </Button>\n ) : null}\n <Button\n size=\"sm\"\n variant=\"outline\"\n disabled={locked}\n onClick={() => decide(hitlResumeReject())}\n >\n <XIcon />\n Reject\n </Button>\n </>\n ) : (\n <>\n <p className=\"text-muted-foreground text-sm\" data-testid=\"statewire-approval-non-hitl\">\n {nonHitlNotice}\n </p>\n <Button\n size=\"sm\"\n variant=\"outline\"\n disabled={pending}\n onClick={() => resume(interruptResumeDecline())}\n >\n <XIcon />\n Decline\n </Button>\n </>\n )}\n </div>\n )}\n </section>\n );\n};\n\n/**\n * What the backend resolved about a call before asking (where a Slack write\n * goes and as whom, Slack Connect warnings), above its raw arguments. Its\n * headline and summary title the card instead; with nothing else, nothing\n * renders here.\n */\nconst ApprovalContextFacts: FC<{ context: PendingApprovalContext }> = ({ context }) =>\n context.facts.length === 0 && context.warnings.length === 0 ? null : (\n <div className=\"mt-1 space-y-0.5\" data-testid=\"statewire-approval-context\">\n {context.facts.map((fact) => (\n <p key={fact.label}>\n <span className=\"font-semibold\">{fact.label}:</span> {fact.value}\n </p>\n ))}\n {context.warnings.map((warning) => (\n <p\n key={warning.message}\n className={warning.severity === 'info' ? undefined : 'font-semibold'}\n >\n {warning.message}\n </p>\n ))}\n </div>\n );\n\n/**\n * One block per gated call: its name (a batch's, or a titled call's), its\n * resolved facts, and its arguments as JSON.\n */\nconst DefaultApprovalDetails: FC<{ actionRequests: PendingActionRequest[]; showNames: boolean }> = ({\n actionRequests,\n showNames,\n}) => (\n <>\n {actionRequests.map((action, index) => (\n <div\n key={`${action.name}-${index}`}\n className=\"rounded-lg border border-border/60 bg-muted/40 p-2 text-foreground text-xs leading-relaxed\"\n >\n {showNames ? <p className=\"font-mono font-semibold\">{action.name}</p> : null}\n {action.approvalContext ? <ApprovalContextFacts context={action.approvalContext} /> : null}\n {Object.keys(action.args).length > 0 ? (\n <pre className=\"mt-1 max-h-32 overflow-auto whitespace-pre-wrap break-words rounded bg-background p-1.5 font-mono text-[11px]\">\n {JSON.stringify(action.args, null, 2)}\n </pre>\n ) : (\n <p className=\"text-muted-foreground\">No arguments.</p>\n )}\n </div>\n ))}\n </>\n);\n"],"names":["request","_a"],"mappings":"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"}
@@ -13,9 +13,11 @@ const threadStatus = require("../agent-runtime/src/thread-status.cjs");
13
13
  const useDeepAgentChatOutbox = require("../agent-runtime/src/use-deep-agent-chat-outbox.cjs");
14
14
  const queue = require("../agent-runtime/src/queue.cjs");
15
15
  const errors = require("../agent-runtime/src/errors.cjs");
16
+ const runSend = require("../agent-runtime/src/run-send.cjs");
16
17
  const messages = require("../agent-runtime/src/messages.cjs");
17
18
  const cnfast = require("cnfast");
18
19
  const MAX_RETRY_HOLDS = 10;
20
+ const NO_FAILED_SENDS = [];
19
21
  function isThenable(value) {
20
22
  return typeof value === "object" && value !== null && typeof value.then === "function";
21
23
  }
@@ -37,7 +39,6 @@ const StatewireQueuedMessagesInner = ({
37
39
  var _a;
38
40
  const runs = reactStatewire.useStatewireRuns();
39
41
  const { queue: queue$1, steerQueue, runId, epoch } = runs;
40
- const failed = runs.failed ?? [];
41
42
  const status = threadStatus.useDeepAgentThreadStatus();
42
43
  const { isRunning, isContinuable } = queue.queueLaneFlags(status);
43
44
  const aui = react.useAui();
@@ -61,6 +62,7 @@ const StatewireQueuedMessagesInner = ({
61
62
  }, []);
62
63
  const outbox = useDeepAgentChatOutbox.useDeepAgentChatOutboxContext();
63
64
  const outboxSnapshot = useDeepAgentChatOutbox.useChatOutboxSnapshot(outbox);
65
+ const failed = outbox === null ? threadExtras.readStatewireFailedSends({ runs }) : NO_FAILED_SENDS;
64
66
  const rows = queue.buildStatewireQueueRows({ queue: queue$1, steerQueue, isContinuable });
65
67
  const queueHeadId = ((_a = queue$1[0]) == null ? void 0 : _a.id) ?? null;
66
68
  const continuationRef = require$$0.useRef({ aui, threadId, runId, epoch, queueHeadId, isContinuable });
@@ -232,6 +234,14 @@ const StatewireQueuedMessagesInner = ({
232
234
  "data-testid": "statewire-queued-message-sending",
233
235
  children: "Sending…"
234
236
  }
237
+ ) : lane === "queue" && isRunning && runSend.wasSentAsAuto(item.id) ? /* @__PURE__ */ jsxRuntime.jsx(
238
+ "span",
239
+ {
240
+ className: "px-1 text-[10px] text-muted-foreground",
241
+ "data-testid": "statewire-queued-message-downgraded",
242
+ title: "Athena queued this message to run after the current response.",
243
+ children: "queued"
244
+ }
235
245
  ) : null,
236
246
  showSteer ? /* @__PURE__ */ jsxRuntime.jsxs(
237
247
  "button",
@@ -241,7 +251,12 @@ const StatewireQueuedMessagesInner = ({
241
251
  title: "Steer the current response: folded into the running turn at its next step, without stopping it.",
242
252
  onClick: () => {
243
253
  if (runId === null) return;
244
- sendCommand({ type: "run/steer-live", runId, messageId: item.id });
254
+ sendCommand({
255
+ type: "run/send",
256
+ runId,
257
+ messageId: item.id,
258
+ behavior: "steer"
259
+ });
245
260
  },
246
261
  className: "inline-flex items-center gap-1 rounded-full border border-border px-2 py-1 font-medium text-[10px] text-foreground/80 hover:bg-background hover:text-foreground",
247
262
  children: [
@@ -1 +1 @@
1
- {"version":3,"file":"StatewireQueuedMessages.cjs","sources":["../../src/chat/StatewireQueuedMessages.tsx"],"sourcesContent":["import { useAui, useAuiState } from '@assistant-ui/react';\nimport type { StatewireThread } from '@assistant-ui/react-statewire';\nimport {\n useStatewireRuns,\n useStatewireSendCommand,\n useStatewireState,\n} from '@assistant-ui/react-statewire';\nimport {\n buildQueueEditCommand,\n buildStatewireQueueRows,\n type DeepAgentThreadStatus,\n describeQueueSendFailure,\n hasStatewireThreadExtras,\n isFailedSendEntryRace,\n isQueueEntryUnsettled,\n isServerUpdateStopSource,\n QUEUE_AUTO_CONTINUE_DELAY_MS,\n queueEntryText,\n queueLaneFlags,\n readDeepAgentStreamValues,\n readRetryableRunRefusal,\n readRunMarkerFromSourceMessages,\n readStatewireFailedSendLane,\n requireStatewireFailedActions,\n type StatewireFailedActions,\n showQueueRowSteer,\n useChatOutboxSnapshot,\n useDeepAgentChatOutboxContext,\n useDeepAgentThreadStatus,\n userStopBlocksQueueAutoContinue,\n} from '@athenaintel/agent-runtime';\nimport {\n AlertCircleIcon,\n CheckIcon,\n ChevronDownIcon,\n ChevronRightIcon,\n CircleIcon,\n Loader2Icon,\n PencilIcon,\n RotateCcwIcon,\n ShipWheelIcon,\n Trash2Icon,\n XIcon,\n} from 'lucide-react';\nimport {\n type FC,\n type KeyboardEvent,\n type MutableRefObject,\n type ReactNode,\n useEffect,\n useId,\n useLayoutEffect,\n useMemo,\n useRef,\n useState,\n} from 'react';\nimport { mentionsToPlainText, parseMentionsInText } from '../chat-ui/mentions/mention-chip';\nimport { ContinuePill } from '../chat-ui/messages/continue-pill';\nimport { cn } from '../lib/utils';\nimport { ChatOutboxRows } from './chat-outbox-rows';\n\ndeclare module '@assistant-ui/core' {\n namespace Assistant {\n interface Commands {\n /**\n * The ⚡ on a queued row (`DeepAgentThread.run_prioritize`). With\n * `priority: true` the host moves the entry to the head of the queue\n * lane (behind entries prioritized before it), records it durably, and\n * the live run ends at its next model-call boundary — after the\n * in-flight tool chain, never mid-tool — so the settle delivers the\n * entry on top of the finished tool results instead of after the whole\n * turn. `priority: false` withdraws the request and leaves the entry\n * where it is.\n */\n runPrioritize: {\n type: 'run/prioritize';\n runId: string;\n messageId: string;\n priority: boolean;\n };\n /**\n * \"Steer\" on a queued row (`DeepAgentThread.run_steer_live`) — what\n * ChatGPT and Codex call Steer, versus Queue. The host moves the entry\n * to the steer lane and records it as a live steer, so the running\n * turn is NOT cancelled: at its next model call — after the in-flight\n * tool chain, never mid-tool — the run drains the entry into its own\n * context as a user turn and continues. Everything the run produces\n * from then on lands after the steered message. Mirrors `run/steer`'s\n * params (exactly one of `message` or `messageId`).\n */\n runSteerLive: {\n type: 'run/steer-live';\n runId: string;\n messageId: string;\n };\n }\n }\n}\n\n/**\n * The one queued-messages tray for the server-owned statewire queue and steer\n * lanes, mounted by the SDK's `AthenaChat`, the Chrome side panel, the Office\n * task pane, and Olympus.\n *\n * A message sent before the live run has produced any output is a double\n * text: the host folds it into the run's turn (`run/enqueue` steers it and\n * the run redispatches with both messages), so it never lists here. A\n * message sent once the run is answering queues behind it. Rows offer\n * \"Steer\" (`run/steer-live` — the host parks the entry on the steer lane as a\n * live steer and the running turn drains it into its own context at its next\n * model call, so the run continues with it; ChatGPT's Steer versus Queue),\n * inline edit (re-sent under the entry's own id on its own lane, which the\n * host folds as an in-place content update), and remove (`run/dequeue`).\n * While the thread rests stopped/errored, stranded steer-lane entries list\n * ahead of the queue (they dispatch first, as one batch) and a Continue pill\n * steer-promotes the queue head — a steer entry moved onto its own lane is a\n * no-op, so a steer-only rest state gets no dead button.\n *\n * A row whose send has not settled yet (`isQueueEntryUnsettled` — this\n * client's optimistic fold, not a host-admitted lane entry) renders as\n * \"Sending…\" with no acting affordances: admission is server-side and can\n * still refuse the message. Failed run sends (`runs.failed`) list after the\n * lanes with Retry (`retryFailed`) and Discard (`discardFailed`).\n *\n * With `autoContinue`, an ordinary stranded settle promotes the queue head\n * once after `QUEUE_AUTO_CONTINUE_DELAY_MS`. User stops remain manual;\n * infrastructure pauses and retryable dispatch refusals recover on the server.\n *\n * Renders nothing on the legacy transport or when every lane is empty.\n */\n\nexport type StatewireQueueEvent =\n | {\n type: 'auto-continued';\n threadId: string | null;\n status: DeepAgentThreadStatus;\n headEntryId: string;\n }\n | {\n type: 'failed-send-action-raced';\n threadId: string | null;\n messageId: string;\n action: 'retry' | 'discard';\n error: string;\n };\n\nexport interface StatewireQueueRowContentContext {\n text: string;\n index: number;\n item: StatewireThread.RunsQueueEntry;\n}\n\nexport interface StatewireQueueRowMarkerContext {\n item: StatewireThread.RunsQueueEntry;\n lane: 'queue' | 'steer';\n index: number;\n /** This client's optimistic fold, not yet admitted by the host (renders \"Sending…\"). */\n isUnsettled: boolean;\n}\n\nexport interface StatewireQueueEditorContext {\n value: string;\n /** The entry being edited, for an editor that reads its metadata (e.g. the composer markdown it was sent from). */\n item: StatewireThread.RunsQueueEntry;\n onChange: (value: string) => void;\n /**\n * Save the edit; a blank or unchanged message sends nothing but closes the\n * editor. `metadata`, when given, replaces the entry's message metadata.\n */\n onSave: (text: string, options?: { metadata?: Record<string, unknown> }) => void;\n onCancel: () => void;\n}\n\nexport interface StatewireQueuedMessagesProps {\n /** Surface-styling overrides merged onto the default classes. */\n classNames?: {\n /** The tray container. */\n root?: string;\n /** The row list. */\n list?: string;\n };\n /**\n * Steer-promote a stranded queue head automatically after a settle (see the\n * component docs). Off by default: a host opts in to dispatching runs on the\n * user's behalf. Pass `{ delayMs }` to tune the grace before the promotion\n * (defaults to `QUEUE_AUTO_CONTINUE_DELAY_MS`).\n */\n autoContinue?: boolean | { delayMs?: number };\n /** Identifies the thread for once-per-entry auto-continue attempts and events. */\n threadId?: string | null;\n /** Telemetry sink for the tray's notable moments. */\n onEvent?: (event: StatewireQueueEvent) => void;\n /** Replace the plain-text row body (e.g. a mention-aware renderer). */\n renderContent?: (context: StatewireQueueRowContentContext) => ReactNode;\n /** Replace the plain textarea inline editor (e.g. the host's composer editor). */\n renderEditor?: (context: StatewireQueueEditorContext) => ReactNode;\n /**\n * Replace a lane row's leading marker (the bullet, or the spinner while the\n * send is unsettled) — e.g. the submitter's avatar on a shared thread.\n * Returning `null`/`undefined` keeps the default marker for that row.\n */\n renderRowMarker?: (context: StatewireQueueRowMarkerContext) => ReactNode;\n /**\n * Called right before a failed message is sent again (its Retry), with its\n * id, so the host can put back the per-send context that message was sent\n * with (e.g. the agents it named) before its command leaves. A promise holds\n * the Retry until it settles, then the host is asked again, unless the\n * message was sent or discarded meanwhile: it can't put that context back\n * while a send with another one is still on its way (every send of a\n * conversation rides one ambient context). A held Retry is held once (a\n * second click does nothing); after {@link MAX_RETRY_HOLDS} holds the message\n * goes regardless, and a hook that throws never holds it back. A function\n * returned is called when the message does not go after all (it left the\n * failed lane first), so the host lets go of what it put back.\n */\n onBeforeRetry?: (messageId: string) => void | PromiseLike<void> | (() => void);\n}\n\n/** How many times a host may hold one Retry (`onBeforeRetry`'s promise) before it goes regardless. */\nconst MAX_RETRY_HOLDS = 10;\n\nfunction isThenable(value: unknown): value is PromiseLike<unknown> {\n return (\n typeof value === 'object' &&\n value !== null &&\n typeof (value as { then?: unknown }).then === 'function'\n );\n}\n\nexport const StatewireQueuedMessages: FC<StatewireQueuedMessagesProps> = (props) => {\n const extras = useAuiState((s) => s.thread.extras);\n if (!hasStatewireThreadExtras(extras)) return null;\n return <StatewireQueuedMessagesInner {...props} />;\n};\n\nconst StatewireQueuedMessagesInner: FC<StatewireQueuedMessagesProps> = ({\n classNames,\n autoContinue = false,\n threadId = null,\n onEvent,\n renderContent,\n renderEditor,\n renderRowMarker,\n onBeforeRetry,\n}) => {\n // The QUEUE lane only: composer.queue prepends the steer lane, whose entries\n // already render in the message list. A non-empty queue implies a live run\n // entry (the host retires runId only once both lanes drain), so the row\n // controls can always send.\n const runs = useStatewireRuns();\n const { queue, steerQueue, runId, epoch } = runs;\n // `failed` joined the runs projection in react-statewire 0.24; a projection\n // without it (an older lib, a stubbed runs read) must not crash the tray.\n const failed = runs.failed ?? [];\n const status = useDeepAgentThreadStatus();\n const { isRunning, isContinuable } = queueLaneFlags(status);\n const aui = useAui();\n const sendCommand = useStatewireSendCommand();\n const listId = useId();\n const [expanded, setExpanded] = useState(true);\n const [editingId, setEditingId] = useState<string | null>(null);\n const [editingText, setEditingText] = useState('');\n // Head entries already auto-promoted once on this mount: an attempt whose\n // continue run dies and re-strands the SAME entry must not loop — the manual\n // Continue pill is the fallback for a repeatedly failing dispatch. Kept on\n // the tray (not the auto-continue child) so it survives the empty-lane\n // renders between a promotion and its outcome.\n const autoContinuedRef = useRef<Set<string>>(new Set());\n const onEventRef = useRef(onEvent);\n onEventRef.current = onEvent;\n const onBeforeRetryRef = useRef(onBeforeRetry);\n onBeforeRetryRef.current = onBeforeRetry;\n // The messages whose Retry the host is holding (`onBeforeRetry`'s promise).\n const heldRetriesRef = useRef<Set<string>>(new Set());\n // A Retry the host held goes on only while the tray is still there.\n const mountedRef = useRef(true);\n useEffect(() => {\n mountedRef.current = true;\n return () => {\n mountedRef.current = false;\n };\n }, []);\n // Messages typed while Athena couldn't be reached (the host's chat outbox), shown above the\n // lanes until they are sent, cancelled or discarded.\n const outbox = useDeepAgentChatOutboxContext();\n const outboxSnapshot = useChatOutboxSnapshot(outbox);\n\n const rows = buildStatewireQueueRows({ queue, steerQueue, isContinuable });\n // Continue promotes the QUEUE head only: a queue→steer move dispatches the\n // stranded steer lane plus this entry, while a steer entry moved onto its\n // own lane is a no-op.\n const queueHeadId = queue[0]?.id ?? null;\n const continuationRef = useRef({ aui, threadId, runId, epoch, queueHeadId, isContinuable });\n useLayoutEffect(() => {\n continuationRef.current = { aui, threadId, runId, epoch, queueHeadId, isContinuable };\n }, [aui, threadId, runId, epoch, queueHeadId, isContinuable]);\n\n const continueQueue = (): void => {\n const current = continuationRef.current;\n // Draft recovery may remove the old head during the pill's exit animation.\n // Continue the surviving queue only within the clicked runtime/dispatch.\n if (\n current.aui !== aui || current.threadId !== threadId ||\n current.runId !== runId || current.epoch !== epoch ||\n !current.isContinuable || current.queueHeadId === null\n ) return;\n aui.composer.queueItem({ id: current.queueHeadId }).move({ lane: 'steer' });\n };\n const retryableRefusal = readRetryableRunRefusal(runs.error) !== null;\n const autoContinueOptions = autoContinue === true ? {} : autoContinue || null;\n\n /**\n * Re-send the entry under its own id on its own lane: the host replaces the\n * queued message's content in place, leaving its queue position and lane\n * untouched (a same-id send never dispatches).\n */\n const saveEdit = (\n item: StatewireThread.RunsQueueEntry,\n lane: 'queue' | 'steer',\n text: string,\n metadata?: Record<string, unknown>,\n ): void => {\n setEditingId(null);\n setEditingText('');\n const command = buildQueueEditCommand({ item, lane, runId, text, metadata });\n if (command !== null) sendCommand(command);\n };\n\n /**\n * Retry/Discard act on a rendered lane snapshot that can trail the session\n * record; acting on an entry statewire already dropped throws. Nothing is\n * lost in that race, so it is recorded instead of crashing the click.\n * Returns whether the action went.\n */\n const runFailedSendAction = ({\n action,\n messageId,\n run,\n }: {\n action: 'retry' | 'discard';\n messageId: string;\n run: (actions: StatewireFailedActions) => void;\n }): boolean => {\n try {\n run(requireStatewireFailedActions(aui.thread().getState().extras));\n return true;\n } catch (error) {\n if (!(error instanceof Error) || !isFailedSendEntryRace(error)) throw error;\n onEvent?.({\n type: 'failed-send-action-raced',\n threadId,\n messageId,\n action,\n error: error.message,\n });\n return false;\n }\n };\n\n /**\n * A failed message's Retry: the host puts its per-send context back first\n * (`onBeforeRetry`), synchronously with the re-send. A host that holds it (a\n * promise: a send with another context is still on its way) is asked again\n * once that settles, while the message is still in the failed lane; a click\n * meanwhile does nothing, and a tray gone meanwhile leaves the row as it was.\n */\n const retryFailedSend = (messageId: string, held = 0): void => {\n const heldRetries = heldRetriesRef.current;\n if (held === 0 && heldRetries.has(messageId)) return;\n heldRetries.delete(messageId);\n if (!mountedRef.current) return;\n if (\n held > 0 &&\n !readStatewireFailedSendLane(aui.thread().getState().extras)?.failed.some(\n (entry) => entry.id === messageId,\n )\n ) {\n return;\n }\n let before: ReturnType<NonNullable<typeof onBeforeRetry>> | undefined;\n try {\n before = onBeforeRetryRef.current?.(messageId);\n } catch {\n // A host's own context step failing never holds the Retry back.\n before = undefined;\n }\n if (isThenable(before) && held < MAX_RETRY_HOLDS) {\n heldRetries.add(messageId);\n const again = (): void => retryFailedSend(messageId, held + 1);\n before.then(again, again);\n return;\n }\n let sent = false;\n try {\n sent = runFailedSendAction({\n action: 'retry',\n messageId,\n run: (actions) => actions.retryFailed(messageId),\n });\n } finally {\n // It did not go after all: the host lets go of what it put back for it.\n try {\n if (!sent && typeof before === 'function') before();\n } catch {\n // The host's own step failing changes nothing here.\n }\n }\n };\n\n const hasOutboxRows =\n outbox !== null && (outboxSnapshot.rows.length > 0 || outboxSnapshot.elsewhere.length > 0);\n const hasLaneRows = rows.length > 0 || failed.length > 0;\n if (!hasLaneRows && !hasOutboxRows) return null;\n\n const renderRowContent = (context: StatewireQueueRowContentContext): ReactNode =>\n renderContent ? renderContent(context) : <QueueRowText text={context.text} />;\n\n return (\n <section\n aria-label=\"Queued messages\"\n className={cn(\n 'aui-statewire-queue w-full rounded-xl border border-border/70 bg-muted/30 px-2 py-1.5',\n classNames?.root,\n )}\n >\n {hasOutboxRows ? (\n <ChatOutboxRows outbox={outbox} snapshot={outboxSnapshot} renderContent={renderRowContent} />\n ) : null}\n {autoContinueOptions ? (\n <QueueAutoContinue\n delayMs={autoContinueOptions.delayMs ?? QUEUE_AUTO_CONTINUE_DELAY_MS}\n queueHeadId={queueHeadId}\n retryableRefusal={retryableRefusal}\n isContinuable={isContinuable}\n status={status}\n threadId={threadId}\n editing={editingId !== null}\n continuedRef={autoContinuedRef}\n onEventRef={onEventRef}\n />\n ) : null}\n {hasLaneRows ? (\n <div className=\"flex items-center gap-1.5\">\n <button\n type=\"button\"\n onClick={() => setExpanded((value) => !value)}\n aria-expanded={expanded}\n aria-controls={listId}\n className=\"flex items-center gap-1 rounded px-1 py-1 font-medium text-muted-foreground text-xs hover:text-foreground\"\n >\n {expanded ? (\n <ChevronDownIcon className=\"size-3.5\" />\n ) : (\n <ChevronRightIcon className=\"size-3.5\" />\n )}\n {rows.length + failed.length} queued\n </button>\n {isContinuable && queueHeadId !== null ? (\n <ContinuePill\n ariaLabel=\"Continue with queued messages\"\n onClick={continueQueue}\n />\n ) : null}\n </div>\n ) : null}\n {expanded && hasLaneRows ? (\n <ul\n id={listId}\n className={cn('max-h-40 overflow-y-auto', classNames?.list)}\n data-testid=\"athena-statewire-queue\"\n >\n {rows.map(({ item, lane }, index) => {\n const text = queueEntryText(item.parts);\n const isUnsettled = isQueueEntryUnsettled(item);\n const isEditing = editingId === item.id;\n const showSteer =\n !isUnsettled && runId !== null && showQueueRowSteer({ lane, isRunning });\n const marker = renderRowMarker?.({ item, lane, index, isUnsettled });\n const editorContext: StatewireQueueEditorContext = {\n value: editingText,\n item,\n onChange: setEditingText,\n onSave: (next, options) => saveEdit(item, lane, next, options?.metadata),\n onCancel: () => {\n setEditingId(null);\n setEditingText('');\n },\n };\n return (\n <li\n key={item.id}\n className=\"group flex items-start gap-2 rounded-md px-1 py-1.5 hover:bg-background\"\n >\n {marker != null ? (\n marker\n ) : isUnsettled ? (\n <Loader2Icon className=\"mt-0.5 size-3.5 shrink-0 animate-spin text-muted-foreground/60\" />\n ) : (\n <CircleIcon className=\"mt-0.5 size-3.5 shrink-0 text-muted-foreground/40\" />\n )}\n {isEditing ? (\n renderEditor ? (\n renderEditor(editorContext)\n ) : (\n <DefaultQueueEditor {...editorContext} />\n )\n ) : (\n renderRowContent({ text, index, item })\n )}\n <div\n className={cn('flex shrink-0 items-center gap-1', isEditing && 'hidden')}\n data-testid=\"statewire-queue-row-actions\"\n >\n {isUnsettled ? (\n <span\n className=\"px-1 text-[10px] text-muted-foreground\"\n data-testid=\"statewire-queued-message-sending\"\n >\n Sending…\n </span>\n ) : null}\n {showSteer ? (\n <button\n type=\"button\"\n aria-label=\"Steer\"\n title=\"Steer the current response: folded into the running turn at its next step, without stopping it.\"\n onClick={() => {\n if (runId === null) return;\n sendCommand({ type: 'run/steer-live', runId, messageId: item.id });\n }}\n className=\"inline-flex items-center gap-1 rounded-full border border-border px-2 py-1 font-medium text-[10px] text-foreground/80 hover:bg-background hover:text-foreground\"\n >\n <ShipWheelIcon className=\"size-2.5\" />\n Steer\n </button>\n ) : null}\n {!isUnsettled ? (\n <button\n type=\"button\"\n aria-label=\"Edit queued message\"\n onClick={() => {\n setEditingId(item.id);\n setEditingText(text);\n }}\n className=\"rounded p-1 text-muted-foreground transition-colors hover:text-primary\"\n >\n <PencilIcon className=\"size-3\" />\n </button>\n ) : null}\n <button\n type=\"button\"\n aria-label=\"Remove queued message\"\n onClick={() => aui.composer.queueItem({ id: item.id }).remove()}\n className={cn(\n 'rounded p-1 text-muted-foreground transition-colors hover:bg-destructive/10 hover:text-destructive',\n !showSteer &&\n 'opacity-0 focus-visible:opacity-100 group-hover:opacity-100',\n )}\n >\n <Trash2Icon className=\"size-3\" />\n </button>\n </div>\n </li>\n );\n })}\n {failed.map((item, index) => (\n <li\n key={item.id}\n className=\"group flex items-start gap-2 rounded-md px-1 py-1.5 hover:bg-background\"\n >\n <AlertCircleIcon className=\"mt-0.5 size-3.5 shrink-0 text-destructive\" />\n {renderRowContent({\n text: queueEntryText(item.parts),\n index: rows.length + index,\n item,\n })}\n <div\n className=\"flex shrink-0 items-center gap-1\"\n data-testid=\"statewire-queue-row-actions\"\n >\n <span\n className=\"px-1 text-[10px] text-destructive\"\n title={describeQueueSendFailure(item.sendFailure)}\n >\n Failed to send\n </span>\n <button\n type=\"button\"\n aria-label=\"Retry failed message\"\n onClick={() => retryFailedSend(item.id)}\n className=\"inline-flex items-center gap-1 rounded-full border border-primary/30 px-2 py-1 font-medium text-[10px] text-primary hover:bg-primary/5\"\n >\n <RotateCcwIcon className=\"size-2.5\" />\n Retry\n </button>\n <button\n type=\"button\"\n aria-label=\"Discard failed message\"\n onClick={() =>\n runFailedSendAction({\n action: 'discard',\n messageId: item.id,\n run: (actions) => actions.discardFailed(item.id),\n })\n }\n className=\"rounded p-1 text-muted-foreground transition-colors hover:bg-destructive/10 hover:text-destructive\"\n >\n <Trash2Icon className=\"size-3\" />\n </button>\n </div>\n </li>\n ))}\n </ul>\n ) : null}\n </section>\n );\n};\n\n/** Promotes ordinary stranded queue heads once; infrastructure recovery stays server-owned. */\nconst QueueAutoContinue: FC<{\n delayMs: number;\n queueHeadId: string | null;\n retryableRefusal: boolean;\n isContinuable: boolean;\n status: DeepAgentThreadStatus;\n threadId: string | null;\n editing: boolean;\n continuedRef: MutableRefObject<Set<string>>;\n onEventRef: MutableRefObject<((event: StatewireQueueEvent) => void) | undefined>;\n}> = ({\n delayMs,\n queueHeadId,\n retryableRefusal,\n isContinuable,\n status,\n threadId,\n editing,\n continuedRef,\n onEventRef,\n}) => {\n const aui = useAui();\n // The settle that stranded the queue is described by the LAST message's run\n // marker (a marker deeper in history was superseded by a later send). The\n // selectors return primitives so the subscriptions stay shallow-stable.\n const lastMessageMarker = useAuiState((s) => {\n const last = s.thread.messages.at(-1);\n return last ? readRunMarkerFromSourceMessages(last)?.marker : undefined;\n });\n const lastMessageMarkerSource = useAuiState((s) => {\n const last = s.thread.messages.at(-1);\n return last ? readRunMarkerFromSourceMessages(last)?.source : undefined;\n });\n const userStopBlocks = userStopBlocksQueueAutoContinue({\n marker: lastMessageMarker,\n source: lastMessageMarkerSource,\n });\n\n useEffect(() => {\n if (\n !isContinuable ||\n userStopBlocks ||\n retryableRefusal ||\n isServerUpdateStopSource(lastMessageMarkerSource)\n ) return;\n // An open inline edit means the user is mid-revision on some row —\n // dispatching underneath them could send text they are about to change.\n if (editing) return;\n if (queueHeadId === null) return;\n const attemptKey = `${threadId ?? 'unknown'}:${queueHeadId}`;\n if (continuedRef.current.has(attemptKey)) return;\n const timeoutId = setTimeout(() => {\n continuedRef.current.add(attemptKey);\n onEventRef.current?.({ type: 'auto-continued', threadId, status, headEntryId: queueHeadId });\n aui.composer.queueItem({ id: queueHeadId }).move({ lane: 'steer' });\n }, delayMs);\n return () => clearTimeout(timeoutId);\n }, [\n continuedRef,\n aui,\n delayMs,\n editing,\n isContinuable,\n onEventRef,\n queueHeadId,\n retryableRefusal,\n lastMessageMarkerSource,\n status,\n threadId,\n userStopBlocks,\n ]);\n\n return null;\n};\n\n/**\n * The default row body: `[@name](…)` mentions render as chips, not raw\n * markdown links, and the body clamps to two lines. Show more / Show less\n * appears only when the rendered text overflows those two lines, so a short\n * message that wraps in a narrow tray is still caught and a short one gets no\n * dead control.\n */\nconst QueueRowText: FC<{ text: string }> = ({ text }) => {\n const bodyRef = useRef<HTMLParagraphElement>(null);\n const [expanded, setExpanded] = useState(false);\n const [overflows, setOverflows] = useState(false);\n\n useLayoutEffect(() => {\n const body = bodyRef.current;\n // Expanded text has no clamp to overflow; the toggle stays up to collapse it.\n if (!body || expanded) return;\n const measure = (): void => setOverflows(body.scrollHeight > body.clientHeight + 1);\n measure();\n if (typeof ResizeObserver === 'undefined') return;\n const observer = new ResizeObserver(measure);\n observer.observe(body);\n return () => observer.disconnect();\n }, [text, expanded]);\n\n if (!text) {\n return <p className=\"min-w-0 flex-1 text-foreground text-xs\">Queued attachment</p>;\n }\n return (\n <div className=\"min-w-0 flex-1\">\n <p\n ref={bodyRef}\n className={cn(\n 'whitespace-pre-wrap break-words text-foreground text-xs leading-relaxed',\n !expanded && 'line-clamp-2',\n )}\n title={overflows && !expanded ? mentionsToPlainText(text) : undefined}\n >\n {parseMentionsInText(text)}\n </p>\n {overflows || expanded ? (\n <button\n type=\"button\"\n aria-expanded={expanded}\n onClick={() => setExpanded((value) => !value)}\n className=\"mt-0.5 font-medium text-[10px] text-muted-foreground hover:text-foreground\"\n >\n {expanded ? 'Show less' : 'Show more'}\n </button>\n ) : null}\n </div>\n );\n};\n\n/** Plain textarea editor: Enter saves, Shift+Enter breaks a line, Escape cancels. */\nconst DefaultQueueEditor: FC<StatewireQueueEditorContext> = ({\n value,\n onChange,\n onSave,\n onCancel,\n}) => {\n const canSave = value.trim().length > 0;\n const handleKeyDown = (event: KeyboardEvent<HTMLTextAreaElement>): void => {\n if (event.key === 'Enter' && !event.shiftKey) {\n event.preventDefault();\n if (canSave) onSave(value);\n } else if (event.key === 'Escape') {\n event.preventDefault();\n onCancel();\n }\n };\n return (\n <div className=\"flex min-w-0 flex-1 items-start gap-1\">\n <textarea\n autoFocus\n aria-label=\"Edit message\"\n value={value}\n onChange={(event) => onChange(event.target.value)}\n onKeyDown={handleKeyDown}\n rows={Math.min(6, Math.max(1, value.split('\\n').length))}\n className=\"min-w-0 flex-1 resize-none rounded-md border border-border bg-background px-2 py-1 text-foreground text-xs outline-none focus-visible:ring-2 focus-visible:ring-ring/50\"\n />\n <button\n type=\"button\"\n aria-label=\"Save edit\"\n disabled={!canSave}\n onClick={() => onSave(value)}\n className={cn(\n 'rounded p-1 text-primary transition-colors hover:bg-primary/10',\n !canSave && 'cursor-not-allowed opacity-40',\n )}\n >\n <CheckIcon className=\"size-3.5\" />\n </button>\n <button\n type=\"button\"\n aria-label=\"Cancel edit\"\n onClick={onCancel}\n className=\"rounded p-1 text-muted-foreground transition-colors hover:bg-muted\"\n >\n <XIcon className=\"size-3.5\" />\n </button>\n </div>\n );\n};\n"],"names":["useAuiState","hasStatewireThreadExtras","jsx","useStatewireRuns","queue","useDeepAgentThreadStatus","queueLaneFlags","useAui","useStatewireSendCommand","useId","useState","useRef","useEffect","useDeepAgentChatOutboxContext","useChatOutboxSnapshot","buildStatewireQueueRows","useLayoutEffect","readRetryableRunRefusal","buildQueueEditCommand","requireStatewireFailedActions","isFailedSendEntryRace","readStatewireFailedSendLane","jsxs","cn","ChatOutboxRows","QUEUE_AUTO_CONTINUE_DELAY_MS","ChevronDownIcon","ChevronRightIcon","ContinuePill","queueEntryText","isQueueEntryUnsettled","showQueueRowSteer","Loader2Icon","CircleIcon","ShipWheelIcon","PencilIcon","Trash2Icon","AlertCircleIcon","describeQueueSendFailure","RotateCcwIcon","readRunMarkerFromSourceMessages","userStopBlocksQueueAutoContinue","isServerUpdateStopSource","mentionsToPlainText","CheckIcon","XIcon"],"mappings":"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"}
1
+ {"version":3,"file":"StatewireQueuedMessages.cjs","sources":["../../src/chat/StatewireQueuedMessages.tsx"],"sourcesContent":["import { useAui, useAuiState } from '@assistant-ui/react';\nimport type { StatewireThread } from '@assistant-ui/react-statewire';\nimport {\n useStatewireRuns,\n useStatewireSendCommand,\n useStatewireState,\n} from '@assistant-ui/react-statewire';\nimport {\n buildQueueEditCommand,\n buildStatewireQueueRows,\n type DeepAgentThreadStatus,\n describeQueueSendFailure,\n hasStatewireThreadExtras,\n isFailedSendEntryRace,\n isQueueEntryUnsettled,\n isServerUpdateStopSource,\n QUEUE_AUTO_CONTINUE_DELAY_MS,\n queueEntryText,\n queueLaneFlags,\n readDeepAgentStreamValues,\n readRetryableRunRefusal,\n readRunMarkerFromSourceMessages,\n readStatewireFailedSendLane,\n readStatewireFailedSends,\n requireStatewireFailedActions,\n type StatewireFailedActions,\n showQueueRowSteer,\n useChatOutboxSnapshot,\n useDeepAgentChatOutboxContext,\n useDeepAgentThreadStatus,\n userStopBlocksQueueAutoContinue,\n wasSentAsAuto,\n} from '@athenaintel/agent-runtime';\nimport {\n AlertCircleIcon,\n CheckIcon,\n ChevronDownIcon,\n ChevronRightIcon,\n CircleIcon,\n Loader2Icon,\n PencilIcon,\n RotateCcwIcon,\n ShipWheelIcon,\n Trash2Icon,\n XIcon,\n} from 'lucide-react';\nimport {\n type FC,\n type KeyboardEvent,\n type MutableRefObject,\n type ReactNode,\n useEffect,\n useId,\n useLayoutEffect,\n useMemo,\n useRef,\n useState,\n} from 'react';\nimport { mentionsToPlainText, parseMentionsInText } from '../chat-ui/mentions/mention-chip';\nimport { ContinuePill } from '../chat-ui/messages/continue-pill';\nimport { cn } from '../lib/utils';\nimport { ChatOutboxRows } from './chat-outbox-rows';\n\n/**\n * The one queued-messages tray for the server-owned statewire queue and steer\n * lanes, mounted by the SDK's `AthenaChat`, the Chrome side panel, the Office\n * task pane, and Olympus.\n *\n * A message the composer sends while a run is live is an `auto` `run/send`:\n * the host's prioritizer folds it into the running turn (the steer lane, which\n * renders in the message list), stops the run for it, or queues it here. A row\n * this client sent as `auto` that the host queued carries a small \"queued\"\n * hint. Rows offer \"Steer\" (`run/send` `steer` — the entry moves to the steer\n * lane and the running turn folds it into its own context at its next safe\n * boundary, so the run continues with it; ChatGPT's Steer versus Queue),\n * inline edit (re-sent under the entry's own id on its own lane, which the\n * host folds as an in-place content update), and remove (`run/dequeue`).\n * While the thread rests stopped/errored, stranded steer-lane entries list\n * ahead of the queue (they dispatch first, as one batch) and a Continue pill\n * steer-promotes the queue head — a steer entry moved onto its own lane is a\n * no-op, so a steer-only rest state gets no dead button.\n *\n * A row whose send has not settled yet (`isQueueEntryUnsettled` — this\n * client's optimistic fold, not a host-admitted lane entry) renders as\n * \"Sending…\" with no acting affordances: admission is server-side and can\n * still refuse the message. Failed run sends (held, with `localMeta.error`) list after the\n * lanes with Retry (`retryFailed`) and Discard (`discardFailed`).\n *\n * With `autoContinue`, an ordinary stranded settle promotes the queue head\n * once after `QUEUE_AUTO_CONTINUE_DELAY_MS`. User stops remain manual;\n * infrastructure pauses and retryable dispatch refusals recover on the server.\n *\n * Renders nothing on the legacy transport or when every lane is empty.\n */\n\nexport type StatewireQueueEvent =\n | {\n type: 'auto-continued';\n threadId: string | null;\n status: DeepAgentThreadStatus;\n headEntryId: string;\n }\n | {\n type: 'failed-send-action-raced';\n threadId: string | null;\n messageId: string;\n action: 'retry' | 'discard';\n error: string;\n };\n\nexport interface StatewireQueueRowContentContext {\n text: string;\n index: number;\n item: StatewireThread.RunsQueueEntry;\n}\n\nexport interface StatewireQueueRowMarkerContext {\n item: StatewireThread.RunsQueueEntry;\n lane: 'queue' | 'steer';\n index: number;\n /** This client's optimistic fold, not yet admitted by the host (renders \"Sending…\"). */\n isUnsettled: boolean;\n}\n\nexport interface StatewireQueueEditorContext {\n value: string;\n /** The entry being edited, for an editor that reads its metadata (e.g. the composer markdown it was sent from). */\n item: StatewireThread.RunsQueueEntry;\n onChange: (value: string) => void;\n /**\n * Save the edit; a blank or unchanged message sends nothing but closes the\n * editor. `metadata`, when given, replaces the entry's message metadata.\n */\n onSave: (text: string, options?: { metadata?: Record<string, unknown> }) => void;\n onCancel: () => void;\n}\n\nexport interface StatewireQueuedMessagesProps {\n /** Surface-styling overrides merged onto the default classes. */\n classNames?: {\n /** The tray container. */\n root?: string;\n /** The row list. */\n list?: string;\n };\n /**\n * Steer-promote a stranded queue head automatically after a settle (see the\n * component docs). Off by default: a host opts in to dispatching runs on the\n * user's behalf. Pass `{ delayMs }` to tune the grace before the promotion\n * (defaults to `QUEUE_AUTO_CONTINUE_DELAY_MS`).\n */\n autoContinue?: boolean | { delayMs?: number };\n /** Identifies the thread for once-per-entry auto-continue attempts and events. */\n threadId?: string | null;\n /** Telemetry sink for the tray's notable moments. */\n onEvent?: (event: StatewireQueueEvent) => void;\n /** Replace the plain-text row body (e.g. a mention-aware renderer). */\n renderContent?: (context: StatewireQueueRowContentContext) => ReactNode;\n /** Replace the plain textarea inline editor (e.g. the host's composer editor). */\n renderEditor?: (context: StatewireQueueEditorContext) => ReactNode;\n /**\n * Replace a lane row's leading marker (the bullet, or the spinner while the\n * send is unsettled) — e.g. the submitter's avatar on a shared thread.\n * Returning `null`/`undefined` keeps the default marker for that row.\n */\n renderRowMarker?: (context: StatewireQueueRowMarkerContext) => ReactNode;\n /**\n * Called right before a failed message is sent again (its Retry), with its\n * id, so the host can put back the per-send context that message was sent\n * with (e.g. the agents it named) before its command leaves. A promise holds\n * the Retry until it settles, then the host is asked again, unless the\n * message was sent or discarded meanwhile: it can't put that context back\n * while a send with another one is still on its way (every send of a\n * conversation rides one ambient context). A held Retry is held once (a\n * second click does nothing); after {@link MAX_RETRY_HOLDS} holds the message\n * goes regardless, and a hook that throws never holds it back. A function\n * returned is called when the message does not go after all (it left the\n * failed lane first), so the host lets go of what it put back.\n */\n onBeforeRetry?: (messageId: string) => void | PromiseLike<void> | (() => void);\n}\n\n/** How many times a host may hold one Retry (`onBeforeRetry`'s promise) before it goes regardless. */\nconst MAX_RETRY_HOLDS = 10;\n\nconst NO_FAILED_SENDS: ReturnType<typeof readStatewireFailedSends> = [];\n\nfunction isThenable(value: unknown): value is PromiseLike<unknown> {\n return (\n typeof value === 'object' &&\n value !== null &&\n typeof (value as { then?: unknown }).then === 'function'\n );\n}\n\nexport const StatewireQueuedMessages: FC<StatewireQueuedMessagesProps> = (props) => {\n const extras = useAuiState((s) => s.thread.extras);\n if (!hasStatewireThreadExtras(extras)) return null;\n return <StatewireQueuedMessagesInner {...props} />;\n};\n\nconst StatewireQueuedMessagesInner: FC<StatewireQueuedMessagesProps> = ({\n classNames,\n autoContinue = false,\n threadId = null,\n onEvent,\n renderContent,\n renderEditor,\n renderRowMarker,\n onBeforeRetry,\n}) => {\n // The QUEUE lane only: composer.queue prepends the steer lane, whose entries\n // already render in the message list. A non-empty queue implies a live run\n // entry (the host retires runId only once both lanes drain), so the row\n // controls can always send.\n const runs = useStatewireRuns();\n const { queue, steerQueue, runId, epoch } = runs;\n const status = useDeepAgentThreadStatus();\n const { isRunning, isContinuable } = queueLaneFlags(status);\n const aui = useAui();\n const sendCommand = useStatewireSendCommand();\n const listId = useId();\n const [expanded, setExpanded] = useState(true);\n const [editingId, setEditingId] = useState<string | null>(null);\n const [editingText, setEditingText] = useState('');\n // Head entries already auto-promoted once on this mount: an attempt whose\n // continue run dies and re-strands the SAME entry must not loop — the manual\n // Continue pill is the fallback for a repeatedly failing dispatch. Kept on\n // the tray (not the auto-continue child) so it survives the empty-lane\n // renders between a promotion and its outcome.\n const autoContinuedRef = useRef<Set<string>>(new Set());\n const onEventRef = useRef(onEvent);\n onEventRef.current = onEvent;\n const onBeforeRetryRef = useRef(onBeforeRetry);\n onBeforeRetryRef.current = onBeforeRetry;\n // The messages whose Retry the host is holding (`onBeforeRetry`'s promise).\n const heldRetriesRef = useRef<Set<string>>(new Set());\n // A Retry the host held goes on only while the tray is still there.\n const mountedRef = useRef(true);\n useEffect(() => {\n mountedRef.current = true;\n return () => {\n mountedRef.current = false;\n };\n }, []);\n // Messages typed while Athena couldn't be reached (the host's chat outbox), shown above the\n // lanes until they are sent, cancelled or discarded.\n const outbox = useDeepAgentChatOutboxContext();\n const outboxSnapshot = useChatOutboxSnapshot(outbox);\n // Failed sends are held outbox entries carrying their failure (statewire 0.24); a projection\n // without `held` (a stubbed runs read) reads as none. With a chat outbox they are its rows\n // (Couldn't send) already, so they are not listed twice. A held send without a failure waits for\n // the outbox's countdown and is never shown as failed.\n const failed = outbox === null ? readStatewireFailedSends({ runs }) : NO_FAILED_SENDS;\n\n const rows = buildStatewireQueueRows({ queue, steerQueue, isContinuable });\n // Continue promotes the QUEUE head only: a queue→steer move dispatches the\n // stranded steer lane plus this entry, while a steer entry moved onto its\n // own lane is a no-op.\n const queueHeadId = queue[0]?.id ?? null;\n const continuationRef = useRef({ aui, threadId, runId, epoch, queueHeadId, isContinuable });\n useLayoutEffect(() => {\n continuationRef.current = { aui, threadId, runId, epoch, queueHeadId, isContinuable };\n }, [aui, threadId, runId, epoch, queueHeadId, isContinuable]);\n\n const continueQueue = (): void => {\n const current = continuationRef.current;\n // Draft recovery may remove the old head during the pill's exit animation.\n // Continue the surviving queue only within the clicked runtime/dispatch.\n if (\n current.aui !== aui || current.threadId !== threadId ||\n current.runId !== runId || current.epoch !== epoch ||\n !current.isContinuable || current.queueHeadId === null\n ) return;\n aui.composer.queueItem({ id: current.queueHeadId }).move({ lane: 'steer' });\n };\n const retryableRefusal = readRetryableRunRefusal(runs.error) !== null;\n const autoContinueOptions = autoContinue === true ? {} : autoContinue || null;\n\n /**\n * Re-send the entry under its own id on its own lane: the host replaces the\n * queued message's content in place, leaving its queue position and lane\n * untouched (a same-id send never dispatches).\n */\n const saveEdit = (\n item: StatewireThread.RunsQueueEntry,\n lane: 'queue' | 'steer',\n text: string,\n metadata?: Record<string, unknown>,\n ): void => {\n setEditingId(null);\n setEditingText('');\n const command = buildQueueEditCommand({ item, lane, runId, text, metadata });\n if (command !== null) sendCommand(command);\n };\n\n /**\n * Retry/Discard act on a rendered lane snapshot that can trail the session\n * record; acting on an entry statewire already dropped throws. Nothing is\n * lost in that race, so it is recorded instead of crashing the click.\n * Returns whether the action went.\n */\n const runFailedSendAction = ({\n action,\n messageId,\n run,\n }: {\n action: 'retry' | 'discard';\n messageId: string;\n run: (actions: StatewireFailedActions) => void;\n }): boolean => {\n try {\n run(requireStatewireFailedActions(aui.thread().getState().extras));\n return true;\n } catch (error) {\n if (!(error instanceof Error) || !isFailedSendEntryRace(error)) throw error;\n onEvent?.({\n type: 'failed-send-action-raced',\n threadId,\n messageId,\n action,\n error: error.message,\n });\n return false;\n }\n };\n\n /**\n * A failed message's Retry: the host puts its per-send context back first\n * (`onBeforeRetry`), synchronously with the re-send. A host that holds it (a\n * promise: a send with another context is still on its way) is asked again\n * once that settles, while the message is still in the failed lane; a click\n * meanwhile does nothing, and a tray gone meanwhile leaves the row as it was.\n */\n const retryFailedSend = (messageId: string, held = 0): void => {\n const heldRetries = heldRetriesRef.current;\n if (held === 0 && heldRetries.has(messageId)) return;\n heldRetries.delete(messageId);\n if (!mountedRef.current) return;\n if (\n held > 0 &&\n !readStatewireFailedSendLane(aui.thread().getState().extras)?.failed.some(\n (entry) => entry.id === messageId,\n )\n ) {\n return;\n }\n let before: ReturnType<NonNullable<typeof onBeforeRetry>> | undefined;\n try {\n before = onBeforeRetryRef.current?.(messageId);\n } catch {\n // A host's own context step failing never holds the Retry back.\n before = undefined;\n }\n if (isThenable(before) && held < MAX_RETRY_HOLDS) {\n heldRetries.add(messageId);\n const again = (): void => retryFailedSend(messageId, held + 1);\n before.then(again, again);\n return;\n }\n let sent = false;\n try {\n sent = runFailedSendAction({\n action: 'retry',\n messageId,\n run: (actions) => actions.retryFailed(messageId),\n });\n } finally {\n // It did not go after all: the host lets go of what it put back for it.\n try {\n if (!sent && typeof before === 'function') before();\n } catch {\n // The host's own step failing changes nothing here.\n }\n }\n };\n\n const hasOutboxRows =\n outbox !== null && (outboxSnapshot.rows.length > 0 || outboxSnapshot.elsewhere.length > 0);\n const hasLaneRows = rows.length > 0 || failed.length > 0;\n if (!hasLaneRows && !hasOutboxRows) return null;\n\n const renderRowContent = (context: StatewireQueueRowContentContext): ReactNode =>\n renderContent ? renderContent(context) : <QueueRowText text={context.text} />;\n\n return (\n <section\n aria-label=\"Queued messages\"\n className={cn(\n 'aui-statewire-queue w-full rounded-xl border border-border/70 bg-muted/30 px-2 py-1.5',\n classNames?.root,\n )}\n >\n {hasOutboxRows ? (\n <ChatOutboxRows outbox={outbox} snapshot={outboxSnapshot} renderContent={renderRowContent} />\n ) : null}\n {autoContinueOptions ? (\n <QueueAutoContinue\n delayMs={autoContinueOptions.delayMs ?? QUEUE_AUTO_CONTINUE_DELAY_MS}\n queueHeadId={queueHeadId}\n retryableRefusal={retryableRefusal}\n isContinuable={isContinuable}\n status={status}\n threadId={threadId}\n editing={editingId !== null}\n continuedRef={autoContinuedRef}\n onEventRef={onEventRef}\n />\n ) : null}\n {hasLaneRows ? (\n <div className=\"flex items-center gap-1.5\">\n <button\n type=\"button\"\n onClick={() => setExpanded((value) => !value)}\n aria-expanded={expanded}\n aria-controls={listId}\n className=\"flex items-center gap-1 rounded px-1 py-1 font-medium text-muted-foreground text-xs hover:text-foreground\"\n >\n {expanded ? (\n <ChevronDownIcon className=\"size-3.5\" />\n ) : (\n <ChevronRightIcon className=\"size-3.5\" />\n )}\n {rows.length + failed.length} queued\n </button>\n {isContinuable && queueHeadId !== null ? (\n <ContinuePill\n ariaLabel=\"Continue with queued messages\"\n onClick={continueQueue}\n />\n ) : null}\n </div>\n ) : null}\n {expanded && hasLaneRows ? (\n <ul\n id={listId}\n className={cn('max-h-40 overflow-y-auto', classNames?.list)}\n data-testid=\"athena-statewire-queue\"\n >\n {rows.map(({ item, lane }, index) => {\n const text = queueEntryText(item.parts);\n const isUnsettled = isQueueEntryUnsettled(item);\n const isEditing = editingId === item.id;\n const showSteer =\n !isUnsettled && runId !== null && showQueueRowSteer({ lane, isRunning });\n const marker = renderRowMarker?.({ item, lane, index, isUnsettled });\n const editorContext: StatewireQueueEditorContext = {\n value: editingText,\n item,\n onChange: setEditingText,\n onSave: (next, options) => saveEdit(item, lane, next, options?.metadata),\n onCancel: () => {\n setEditingId(null);\n setEditingText('');\n },\n };\n return (\n <li\n key={item.id}\n className=\"group flex items-start gap-2 rounded-md px-1 py-1.5 hover:bg-background\"\n >\n {marker != null ? (\n marker\n ) : isUnsettled ? (\n <Loader2Icon className=\"mt-0.5 size-3.5 shrink-0 animate-spin text-muted-foreground/60\" />\n ) : (\n <CircleIcon className=\"mt-0.5 size-3.5 shrink-0 text-muted-foreground/40\" />\n )}\n {isEditing ? (\n renderEditor ? (\n renderEditor(editorContext)\n ) : (\n <DefaultQueueEditor {...editorContext} />\n )\n ) : (\n renderRowContent({ text, index, item })\n )}\n <div\n className={cn('flex shrink-0 items-center gap-1', isEditing && 'hidden')}\n data-testid=\"statewire-queue-row-actions\"\n >\n {isUnsettled ? (\n <span\n className=\"px-1 text-[10px] text-muted-foreground\"\n data-testid=\"statewire-queued-message-sending\"\n >\n Sending…\n </span>\n ) : lane === 'queue' && isRunning && wasSentAsAuto(item.id) ? (\n <span\n className=\"px-1 text-[10px] text-muted-foreground\"\n data-testid=\"statewire-queued-message-downgraded\"\n title=\"Athena queued this message to run after the current response.\"\n >\n queued\n </span>\n ) : null}\n {showSteer ? (\n <button\n type=\"button\"\n aria-label=\"Steer\"\n title=\"Steer the current response: folded into the running turn at its next step, without stopping it.\"\n onClick={() => {\n if (runId === null) return;\n sendCommand({\n type: 'run/send',\n runId,\n messageId: item.id,\n behavior: 'steer',\n });\n }}\n className=\"inline-flex items-center gap-1 rounded-full border border-border px-2 py-1 font-medium text-[10px] text-foreground/80 hover:bg-background hover:text-foreground\"\n >\n <ShipWheelIcon className=\"size-2.5\" />\n Steer\n </button>\n ) : null}\n {!isUnsettled ? (\n <button\n type=\"button\"\n aria-label=\"Edit queued message\"\n onClick={() => {\n setEditingId(item.id);\n setEditingText(text);\n }}\n className=\"rounded p-1 text-muted-foreground transition-colors hover:text-primary\"\n >\n <PencilIcon className=\"size-3\" />\n </button>\n ) : null}\n <button\n type=\"button\"\n aria-label=\"Remove queued message\"\n onClick={() => aui.composer.queueItem({ id: item.id }).remove()}\n className={cn(\n 'rounded p-1 text-muted-foreground transition-colors hover:bg-destructive/10 hover:text-destructive',\n !showSteer &&\n 'opacity-0 focus-visible:opacity-100 group-hover:opacity-100',\n )}\n >\n <Trash2Icon className=\"size-3\" />\n </button>\n </div>\n </li>\n );\n })}\n {failed.map((item, index) => (\n <li\n key={item.id}\n className=\"group flex items-start gap-2 rounded-md px-1 py-1.5 hover:bg-background\"\n >\n <AlertCircleIcon className=\"mt-0.5 size-3.5 shrink-0 text-destructive\" />\n {renderRowContent({\n text: queueEntryText(item.parts),\n index: rows.length + index,\n item,\n })}\n <div\n className=\"flex shrink-0 items-center gap-1\"\n data-testid=\"statewire-queue-row-actions\"\n >\n <span\n className=\"px-1 text-[10px] text-destructive\"\n title={describeQueueSendFailure(item.sendFailure)}\n >\n Failed to send\n </span>\n <button\n type=\"button\"\n aria-label=\"Retry failed message\"\n onClick={() => retryFailedSend(item.id)}\n className=\"inline-flex items-center gap-1 rounded-full border border-primary/30 px-2 py-1 font-medium text-[10px] text-primary hover:bg-primary/5\"\n >\n <RotateCcwIcon className=\"size-2.5\" />\n Retry\n </button>\n <button\n type=\"button\"\n aria-label=\"Discard failed message\"\n onClick={() =>\n runFailedSendAction({\n action: 'discard',\n messageId: item.id,\n run: (actions) => actions.discardFailed(item.id),\n })\n }\n className=\"rounded p-1 text-muted-foreground transition-colors hover:bg-destructive/10 hover:text-destructive\"\n >\n <Trash2Icon className=\"size-3\" />\n </button>\n </div>\n </li>\n ))}\n </ul>\n ) : null}\n </section>\n );\n};\n\n/** Promotes ordinary stranded queue heads once; infrastructure recovery stays server-owned. */\nconst QueueAutoContinue: FC<{\n delayMs: number;\n queueHeadId: string | null;\n retryableRefusal: boolean;\n isContinuable: boolean;\n status: DeepAgentThreadStatus;\n threadId: string | null;\n editing: boolean;\n continuedRef: MutableRefObject<Set<string>>;\n onEventRef: MutableRefObject<((event: StatewireQueueEvent) => void) | undefined>;\n}> = ({\n delayMs,\n queueHeadId,\n retryableRefusal,\n isContinuable,\n status,\n threadId,\n editing,\n continuedRef,\n onEventRef,\n}) => {\n const aui = useAui();\n // The settle that stranded the queue is described by the LAST message's run\n // marker (a marker deeper in history was superseded by a later send). The\n // selectors return primitives so the subscriptions stay shallow-stable.\n const lastMessageMarker = useAuiState((s) => {\n const last = s.thread.messages.at(-1);\n return last ? readRunMarkerFromSourceMessages(last)?.marker : undefined;\n });\n const lastMessageMarkerSource = useAuiState((s) => {\n const last = s.thread.messages.at(-1);\n return last ? readRunMarkerFromSourceMessages(last)?.source : undefined;\n });\n const userStopBlocks = userStopBlocksQueueAutoContinue({\n marker: lastMessageMarker,\n source: lastMessageMarkerSource,\n });\n\n useEffect(() => {\n if (\n !isContinuable ||\n userStopBlocks ||\n retryableRefusal ||\n isServerUpdateStopSource(lastMessageMarkerSource)\n ) return;\n // An open inline edit means the user is mid-revision on some row —\n // dispatching underneath them could send text they are about to change.\n if (editing) return;\n if (queueHeadId === null) return;\n const attemptKey = `${threadId ?? 'unknown'}:${queueHeadId}`;\n if (continuedRef.current.has(attemptKey)) return;\n const timeoutId = setTimeout(() => {\n continuedRef.current.add(attemptKey);\n onEventRef.current?.({ type: 'auto-continued', threadId, status, headEntryId: queueHeadId });\n aui.composer.queueItem({ id: queueHeadId }).move({ lane: 'steer' });\n }, delayMs);\n return () => clearTimeout(timeoutId);\n }, [\n continuedRef,\n aui,\n delayMs,\n editing,\n isContinuable,\n onEventRef,\n queueHeadId,\n retryableRefusal,\n lastMessageMarkerSource,\n status,\n threadId,\n userStopBlocks,\n ]);\n\n return null;\n};\n\n/**\n * The default row body: `[@name](…)` mentions render as chips, not raw\n * markdown links, and the body clamps to two lines. Show more / Show less\n * appears only when the rendered text overflows those two lines, so a short\n * message that wraps in a narrow tray is still caught and a short one gets no\n * dead control.\n */\nconst QueueRowText: FC<{ text: string }> = ({ text }) => {\n const bodyRef = useRef<HTMLParagraphElement>(null);\n const [expanded, setExpanded] = useState(false);\n const [overflows, setOverflows] = useState(false);\n\n useLayoutEffect(() => {\n const body = bodyRef.current;\n // Expanded text has no clamp to overflow; the toggle stays up to collapse it.\n if (!body || expanded) return;\n const measure = (): void => setOverflows(body.scrollHeight > body.clientHeight + 1);\n measure();\n if (typeof ResizeObserver === 'undefined') return;\n const observer = new ResizeObserver(measure);\n observer.observe(body);\n return () => observer.disconnect();\n }, [text, expanded]);\n\n if (!text) {\n return <p className=\"min-w-0 flex-1 text-foreground text-xs\">Queued attachment</p>;\n }\n return (\n <div className=\"min-w-0 flex-1\">\n <p\n ref={bodyRef}\n className={cn(\n 'whitespace-pre-wrap break-words text-foreground text-xs leading-relaxed',\n !expanded && 'line-clamp-2',\n )}\n title={overflows && !expanded ? mentionsToPlainText(text) : undefined}\n >\n {parseMentionsInText(text)}\n </p>\n {overflows || expanded ? (\n <button\n type=\"button\"\n aria-expanded={expanded}\n onClick={() => setExpanded((value) => !value)}\n className=\"mt-0.5 font-medium text-[10px] text-muted-foreground hover:text-foreground\"\n >\n {expanded ? 'Show less' : 'Show more'}\n </button>\n ) : null}\n </div>\n );\n};\n\n/** Plain textarea editor: Enter saves, Shift+Enter breaks a line, Escape cancels. */\nconst DefaultQueueEditor: FC<StatewireQueueEditorContext> = ({\n value,\n onChange,\n onSave,\n onCancel,\n}) => {\n const canSave = value.trim().length > 0;\n const handleKeyDown = (event: KeyboardEvent<HTMLTextAreaElement>): void => {\n if (event.key === 'Enter' && !event.shiftKey) {\n event.preventDefault();\n if (canSave) onSave(value);\n } else if (event.key === 'Escape') {\n event.preventDefault();\n onCancel();\n }\n };\n return (\n <div className=\"flex min-w-0 flex-1 items-start gap-1\">\n <textarea\n autoFocus\n aria-label=\"Edit message\"\n value={value}\n onChange={(event) => onChange(event.target.value)}\n onKeyDown={handleKeyDown}\n rows={Math.min(6, Math.max(1, value.split('\\n').length))}\n className=\"min-w-0 flex-1 resize-none rounded-md border border-border bg-background px-2 py-1 text-foreground text-xs outline-none focus-visible:ring-2 focus-visible:ring-ring/50\"\n />\n <button\n type=\"button\"\n aria-label=\"Save edit\"\n disabled={!canSave}\n onClick={() => onSave(value)}\n className={cn(\n 'rounded p-1 text-primary transition-colors hover:bg-primary/10',\n !canSave && 'cursor-not-allowed opacity-40',\n )}\n >\n <CheckIcon className=\"size-3.5\" />\n </button>\n <button\n type=\"button\"\n aria-label=\"Cancel edit\"\n onClick={onCancel}\n className=\"rounded p-1 text-muted-foreground transition-colors hover:bg-muted\"\n >\n <XIcon className=\"size-3.5\" />\n </button>\n </div>\n );\n};\n"],"names":["useAuiState","hasStatewireThreadExtras","jsx","useStatewireRuns","queue","useDeepAgentThreadStatus","queueLaneFlags","useAui","useStatewireSendCommand","useId","useState","useRef","useEffect","useDeepAgentChatOutboxContext","useChatOutboxSnapshot","readStatewireFailedSends","buildStatewireQueueRows","useLayoutEffect","readRetryableRunRefusal","buildQueueEditCommand","requireStatewireFailedActions","isFailedSendEntryRace","readStatewireFailedSendLane","jsxs","cn","ChatOutboxRows","QUEUE_AUTO_CONTINUE_DELAY_MS","ChevronDownIcon","ChevronRightIcon","ContinuePill","queueEntryText","isQueueEntryUnsettled","showQueueRowSteer","Loader2Icon","CircleIcon","wasSentAsAuto","ShipWheelIcon","PencilIcon","Trash2Icon","AlertCircleIcon","describeQueueSendFailure","RotateCcwIcon","readRunMarkerFromSourceMessages","userStopBlocksQueueAutoContinue","isServerUpdateStopSource","mentionsToPlainText","CheckIcon","XIcon"],"mappings":";;;;;;;;;;;;;;;;;;AAuLA,MAAM,kBAAkB;AAExB,MAAM,kBAA+D,CAAA;AAErE,SAAS,WAAW,OAA+C;AACjE,SACE,OAAO,UAAU,YACjB,UAAU,QACV,OAAQ,MAA6B,SAAS;AAElD;AAEO,MAAM,0BAA4D,CAAC,UAAU;AAClF,QAAM,SAASA,MAAAA,YAAY,CAAC,MAAM,EAAE,OAAO,MAAM;AACjD,MAAI,CAACC,aAAAA,yBAAyB,MAAM,EAAG,QAAO;AAC9C,SAAOC,+BAAC,8BAAA,EAA8B,GAAG,MAAA,CAAO;AAClD;AAEA,MAAM,+BAAiE,CAAC;AAAA,EACtE;AAAA,EACA,eAAe;AAAA,EACf,WAAW;AAAA,EACX;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AACF,MAAM;;AAKJ,QAAM,OAAOC,eAAAA,iBAAA;AACb,QAAM,EAAA,OAAEC,SAAO,YAAY,OAAO,UAAU;AAC5C,QAAM,SAASC,aAAAA,yBAAA;AACf,QAAM,EAAE,WAAW,kBAAkBC,MAAAA,eAAe,MAAM;AAC1D,QAAM,MAAMC,MAAAA,OAAA;AACZ,QAAM,cAAcC,eAAAA,wBAAA;AACpB,QAAM,SAASC,WAAAA,MAAA;AACf,QAAM,CAAC,UAAU,WAAW,IAAIC,WAAAA,SAAS,IAAI;AAC7C,QAAM,CAAC,WAAW,YAAY,IAAIA,WAAAA,SAAwB,IAAI;AAC9D,QAAM,CAAC,aAAa,cAAc,IAAIA,WAAAA,SAAS,EAAE;AAMjD,QAAM,mBAAmBC,WAAAA,OAAoB,oBAAI,KAAK;AACtD,QAAM,aAAaA,WAAAA,OAAO,OAAO;AACjC,aAAW,UAAU;AACrB,QAAM,mBAAmBA,WAAAA,OAAO,aAAa;AAC7C,mBAAiB,UAAU;AAE3B,QAAM,iBAAiBA,WAAAA,OAAoB,oBAAI,KAAK;AAEpD,QAAM,aAAaA,WAAAA,OAAO,IAAI;AAC9BC,aAAAA,UAAU,MAAM;AACd,eAAW,UAAU;AACrB,WAAO,MAAM;AACX,iBAAW,UAAU;AAAA,IACvB;AAAA,EACF,GAAG,CAAA,CAAE;AAGL,QAAM,SAASC,uBAAAA,8BAAA;AACf,QAAM,iBAAiBC,uBAAAA,sBAAsB,MAAM;AAKnD,QAAM,SAAS,WAAW,OAAOC,aAAAA,yBAAyB,EAAE,KAAA,CAAM,IAAI;AAEtE,QAAM,OAAOC,MAAAA,wBAAwB,EAAA,OAAEZ,SAAO,YAAY,eAAe;AAIzE,QAAM,gBAAcA,aAAM,CAAC,MAAPA,mBAAU,OAAM;AACpC,QAAM,kBAAkBO,kBAAO,EAAE,KAAK,UAAU,OAAO,OAAO,aAAa,eAAe;AAC1FM,aAAAA,gBAAgB,MAAM;AACpB,oBAAgB,UAAU,EAAE,KAAK,UAAU,OAAO,OAAO,aAAa,cAAA;AAAA,EACxE,GAAG,CAAC,KAAK,UAAU,OAAO,OAAO,aAAa,aAAa,CAAC;AAE5D,QAAM,gBAAgB,MAAY;AAChC,UAAM,UAAU,gBAAgB;AAGhC,QACE,QAAQ,QAAQ,OAAO,QAAQ,aAAa,YAC5C,QAAQ,UAAU,SAAS,QAAQ,UAAU,SAC7C,CAAC,QAAQ,iBAAiB,QAAQ,gBAAgB,KAClD;AACF,QAAI,SAAS,UAAU,EAAE,IAAI,QAAQ,YAAA,CAAa,EAAE,KAAK,EAAE,MAAM,QAAA,CAAS;AAAA,EAC5E;AACA,QAAM,mBAAmBC,OAAAA,wBAAwB,KAAK,KAAK,MAAM;AACjE,QAAM,sBAAsB,iBAAiB,OAAO,CAAA,IAAK,gBAAgB;AAOzE,QAAM,WAAW,CACf,MACA,MACA,MACA,aACS;AACT,iBAAa,IAAI;AACjB,mBAAe,EAAE;AACjB,UAAM,UAAUC,MAAAA,sBAAsB,EAAE,MAAM,MAAM,OAAO,MAAM,UAAU;AAC3E,QAAI,YAAY,KAAM,aAAY,OAAO;AAAA,EAC3C;AAQA,QAAM,sBAAsB,CAAC;AAAA,IAC3B;AAAA,IACA;AAAA,IACA;AAAA,EAAA,MAKa;AACb,QAAI;AACF,UAAIC,aAAAA,8BAA8B,IAAI,OAAA,EAAS,SAAA,EAAW,MAAM,CAAC;AACjE,aAAO;AAAA,IACT,SAAS,OAAO;AACd,UAAI,EAAE,iBAAiB,UAAU,CAACC,MAAAA,sBAAsB,KAAK,EAAG,OAAM;AACtE,yCAAU;AAAA,QACR,MAAM;AAAA,QACN;AAAA,QACA;AAAA,QACA;AAAA,QACA,OAAO,MAAM;AAAA,MAAA;AAEf,aAAO;AAAA,IACT;AAAA,EACF;AASA,QAAM,kBAAkB,CAAC,WAAmB,OAAO,MAAY;;AAC7D,UAAM,cAAc,eAAe;AACnC,QAAI,SAAS,KAAK,YAAY,IAAI,SAAS,EAAG;AAC9C,gBAAY,OAAO,SAAS;AAC5B,QAAI,CAAC,WAAW,QAAS;AACzB,QACE,OAAO,KACP,GAACC,MAAAA,aAAAA,4BAA4B,IAAI,OAAA,EAAS,SAAA,EAAW,MAAM,MAA1DA,gBAAAA,IAA6D,OAAO;AAAA,MACnE,CAAC,UAAU,MAAM,OAAO;AAAA,QAE1B;AACA;AAAA,IACF;AACA,QAAI;AACJ,QAAI;AACF,gBAAS,sBAAiB,YAAjB,0CAA2B;AAAA,IACtC,QAAQ;AAEN,eAAS;AAAA,IACX;AACA,QAAI,WAAW,MAAM,KAAK,OAAO,iBAAiB;AAChD,kBAAY,IAAI,SAAS;AACzB,YAAM,QAAQ,MAAY,gBAAgB,WAAW,OAAO,CAAC;AAC7D,aAAO,KAAK,OAAO,KAAK;AACxB;AAAA,IACF;AACA,QAAI,OAAO;AACX,QAAI;AACF,aAAO,oBAAoB;AAAA,QACzB,QAAQ;AAAA,QACR;AAAA,QACA,KAAK,CAAC,YAAY,QAAQ,YAAY,SAAS;AAAA,MAAA,CAChD;AAAA,IACH,UAAA;AAEE,UAAI;AACF,YAAI,CAAC,QAAQ,OAAO,WAAW,WAAY,QAAA;AAAA,MAC7C,QAAQ;AAAA,MAER;AAAA,IACF;AAAA,EACF;AAEA,QAAM,gBACJ,WAAW,SAAS,eAAe,KAAK,SAAS,KAAK,eAAe,UAAU,SAAS;AAC1F,QAAM,cAAc,KAAK,SAAS,KAAK,OAAO,SAAS;AACvD,MAAI,CAAC,eAAe,CAAC,cAAe,QAAO;AAE3C,QAAM,mBAAmB,CAAC,YACxB,gBAAgB,cAAc,OAAO,IAAIpB,2BAAAA,IAAC,cAAA,EAAa,MAAM,QAAQ,KAAA,CAAM;AAE7E,SACEqB,2BAAAA;AAAAA,IAAC;AAAA,IAAA;AAAA,MACC,cAAW;AAAA,MACX,WAAWC,OAAAA;AAAAA,QACT;AAAA,QACA,yCAAY;AAAA,MAAA;AAAA,MAGb,UAAA;AAAA,QAAA,+CACEC,eAAAA,gBAAA,EAAe,QAAgB,UAAU,gBAAgB,eAAe,kBAAkB,IACzF;AAAA,QACH,sBACCvB,2BAAAA;AAAAA,UAAC;AAAA,UAAA;AAAA,YACC,SAAS,oBAAoB,WAAWwB,MAAAA;AAAAA,YACxC;AAAA,YACA;AAAA,YACA;AAAA,YACA;AAAA,YACA;AAAA,YACA,SAAS,cAAc;AAAA,YACvB,cAAc;AAAA,YACd;AAAA,UAAA;AAAA,QAAA,IAEA;AAAA,QACH,cACCH,2BAAAA,KAAC,OAAA,EAAI,WAAU,6BACb,UAAA;AAAA,UAAAA,2BAAAA;AAAAA,YAAC;AAAA,YAAA;AAAA,cACC,MAAK;AAAA,cACL,SAAS,MAAM,YAAY,CAAC,UAAU,CAAC,KAAK;AAAA,cAC5C,iBAAe;AAAA,cACf,iBAAe;AAAA,cACf,WAAU;AAAA,cAET,UAAA;AAAA,gBAAA,WACCrB,2BAAAA,IAACyB,+BAAgB,WAAU,WAAA,CAAW,IAEtCzB,2BAAAA,IAAC0B,YAAAA,kBAAA,EAAiB,WAAU,WAAA,CAAW;AAAA,gBAExC,KAAK,SAAS,OAAO;AAAA,gBAAO;AAAA,cAAA;AAAA,YAAA;AAAA,UAAA;AAAA,UAE9B,iBAAiB,gBAAgB,OAChC1B,2BAAAA;AAAAA,YAAC2B,aAAAA;AAAAA,YAAA;AAAA,cACC,WAAU;AAAA,cACV,SAAS;AAAA,YAAA;AAAA,UAAA,IAET;AAAA,QAAA,EAAA,CACN,IACE;AAAA,QACH,YAAY,cACXN,2BAAAA;AAAAA,UAAC;AAAA,UAAA;AAAA,YACC,IAAI;AAAA,YACJ,WAAWC,OAAAA,GAAG,4BAA4B,yCAAY,IAAI;AAAA,YAC1D,eAAY;AAAA,YAEX,UAAA;AAAA,cAAA,KAAK,IAAI,CAAC,EAAE,MAAM,KAAA,GAAQ,UAAU;AACnC,sBAAM,OAAOM,MAAAA,eAAe,KAAK,KAAK;AACtC,sBAAM,cAAcC,MAAAA,sBAAsB,IAAI;AAC9C,sBAAM,YAAY,cAAc,KAAK;AACrC,sBAAM,YACJ,CAAC,eAAe,UAAU,QAAQC,wBAAkB,EAAE,MAAM,WAAW;AACzE,sBAAM,SAAS,mDAAkB,EAAE,MAAM,MAAM,OAAO;AACtD,sBAAM,gBAA6C;AAAA,kBACjD,OAAO;AAAA,kBACP;AAAA,kBACA,UAAU;AAAA,kBACV,QAAQ,CAAC,MAAM,YAAY,SAAS,MAAM,MAAM,MAAM,mCAAS,QAAQ;AAAA,kBACvE,UAAU,MAAM;AACd,iCAAa,IAAI;AACjB,mCAAe,EAAE;AAAA,kBACnB;AAAA,gBAAA;AAEF,uBACET,2BAAAA;AAAAA,kBAAC;AAAA,kBAAA;AAAA,oBAEC,WAAU;AAAA,oBAET,UAAA;AAAA,sBAAA,UAAU,OACT,SACE,cACFrB,2BAAAA,IAAC+B,YAAAA,aAAA,EAAY,WAAU,iEAAA,CAAiE,IAExF/B,2BAAAA,IAACgC,YAAAA,YAAA,EAAW,WAAU,oDAAA,CAAoD;AAAA,sBAE3E,YACC,eACE,aAAa,aAAa,IAE1BhC,2BAAAA,IAAC,oBAAA,EAAoB,GAAG,cAAA,CAAe,IAGzC,iBAAiB,EAAE,MAAM,OAAO,MAAM;AAAA,sBAExCqB,2BAAAA;AAAAA,wBAAC;AAAA,wBAAA;AAAA,0BACC,WAAWC,OAAAA,GAAG,oCAAoC,aAAa,QAAQ;AAAA,0BACvE,eAAY;AAAA,0BAEX,UAAA;AAAA,4BAAA,cACCtB,2BAAAA;AAAAA,8BAAC;AAAA,8BAAA;AAAA,gCACC,WAAU;AAAA,gCACV,eAAY;AAAA,gCACb,UAAA;AAAA,8BAAA;AAAA,4BAAA,IAGC,SAAS,WAAW,aAAaiC,QAAAA,cAAc,KAAK,EAAE,IACxDjC,2BAAAA;AAAAA,8BAAC;AAAA,8BAAA;AAAA,gCACC,WAAU;AAAA,gCACV,eAAY;AAAA,gCACZ,OAAM;AAAA,gCACP,UAAA;AAAA,8BAAA;AAAA,4BAAA,IAGC;AAAA,4BACH,YACCqB,2BAAAA;AAAAA,8BAAC;AAAA,8BAAA;AAAA,gCACC,MAAK;AAAA,gCACL,cAAW;AAAA,gCACX,OAAM;AAAA,gCACN,SAAS,MAAM;AACb,sCAAI,UAAU,KAAM;AACpB,8CAAY;AAAA,oCACV,MAAM;AAAA,oCACN;AAAA,oCACA,WAAW,KAAK;AAAA,oCAChB,UAAU;AAAA,kCAAA,CACX;AAAA,gCACH;AAAA,gCACA,WAAU;AAAA,gCAEV,UAAA;AAAA,kCAAArB,2BAAAA,IAACkC,YAAAA,eAAA,EAAc,WAAU,WAAA,CAAW;AAAA,kCAAE;AAAA,gCAAA;AAAA,8BAAA;AAAA,4BAAA,IAGtC;AAAA,4BACH,CAAC,cACAlC,2BAAAA;AAAAA,8BAAC;AAAA,8BAAA;AAAA,gCACC,MAAK;AAAA,gCACL,cAAW;AAAA,gCACX,SAAS,MAAM;AACb,+CAAa,KAAK,EAAE;AACpB,iDAAe,IAAI;AAAA,gCACrB;AAAA,gCACA,WAAU;AAAA,gCAEV,UAAAA,2BAAAA,IAACmC,YAAAA,YAAA,EAAW,WAAU,SAAA,CAAS;AAAA,8BAAA;AAAA,4BAAA,IAE/B;AAAA,4BACJnC,2BAAAA;AAAAA,8BAAC;AAAA,8BAAA;AAAA,gCACC,MAAK;AAAA,gCACL,cAAW;AAAA,gCACX,SAAS,MAAM,IAAI,SAAS,UAAU,EAAE,IAAI,KAAK,IAAI,EAAE,OAAA;AAAA,gCACvD,WAAWsB,OAAAA;AAAAA,kCACT;AAAA,kCACA,CAAC,aACC;AAAA,gCAAA;AAAA,gCAGJ,UAAAtB,2BAAAA,IAACoC,YAAAA,YAAA,EAAW,WAAU,SAAA,CAAS;AAAA,8BAAA;AAAA,4BAAA;AAAA,0BACjC;AAAA,wBAAA;AAAA,sBAAA;AAAA,oBACF;AAAA,kBAAA;AAAA,kBApFK,KAAK;AAAA,gBAAA;AAAA,cAuFhB,CAAC;AAAA,cACA,OAAO,IAAI,CAAC,MAAM,UACjBf,2BAAAA;AAAAA,gBAAC;AAAA,gBAAA;AAAA,kBAEC,WAAU;AAAA,kBAEV,UAAA;AAAA,oBAAArB,2BAAAA,IAACqC,YAAAA,iBAAA,EAAgB,WAAU,4CAAA,CAA4C;AAAA,oBACtE,iBAAiB;AAAA,sBAChB,MAAMT,MAAAA,eAAe,KAAK,KAAK;AAAA,sBAC/B,OAAO,KAAK,SAAS;AAAA,sBACrB;AAAA,oBAAA,CACD;AAAA,oBACDP,2BAAAA;AAAAA,sBAAC;AAAA,sBAAA;AAAA,wBACC,WAAU;AAAA,wBACV,eAAY;AAAA,wBAEZ,UAAA;AAAA,0BAAArB,2BAAAA;AAAAA,4BAAC;AAAA,4BAAA;AAAA,8BACC,WAAU;AAAA,8BACV,OAAOsC,MAAAA,yBAAyB,KAAK,WAAW;AAAA,8BACjD,UAAA;AAAA,4BAAA;AAAA,0BAAA;AAAA,0BAGDjB,2BAAAA;AAAAA,4BAAC;AAAA,4BAAA;AAAA,8BACC,MAAK;AAAA,8BACL,cAAW;AAAA,8BACX,SAAS,MAAM,gBAAgB,KAAK,EAAE;AAAA,8BACtC,WAAU;AAAA,8BAEV,UAAA;AAAA,gCAAArB,2BAAAA,IAACuC,YAAAA,eAAA,EAAc,WAAU,WAAA,CAAW;AAAA,gCAAE;AAAA,8BAAA;AAAA,4BAAA;AAAA,0BAAA;AAAA,0BAGxCvC,2BAAAA;AAAAA,4BAAC;AAAA,4BAAA;AAAA,8BACC,MAAK;AAAA,8BACL,cAAW;AAAA,8BACX,SAAS,MACP,oBAAoB;AAAA,gCAClB,QAAQ;AAAA,gCACR,WAAW,KAAK;AAAA,gCAChB,KAAK,CAAC,YAAY,QAAQ,cAAc,KAAK,EAAE;AAAA,8BAAA,CAChD;AAAA,8BAEH,WAAU;AAAA,8BAEV,UAAAA,2BAAAA,IAACoC,YAAAA,YAAA,EAAW,WAAU,SAAA,CAAS;AAAA,4BAAA;AAAA,0BAAA;AAAA,wBACjC;AAAA,sBAAA;AAAA,oBAAA;AAAA,kBACF;AAAA,gBAAA;AAAA,gBA1CK,KAAK;AAAA,cAAA,CA4Cb;AAAA,YAAA;AAAA,UAAA;AAAA,QAAA,IAED;AAAA,MAAA;AAAA,IAAA;AAAA,EAAA;AAGV;AAGA,MAAM,oBAUD,CAAC;AAAA,EACJ;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AACF,MAAM;AACJ,QAAM,MAAM/B,MAAAA,OAAA;AAIZ,QAAM,oBAAoBP,kBAAY,CAAC,MAAM;;AAC3C,UAAM,OAAO,EAAE,OAAO,SAAS,GAAG,EAAE;AACpC,WAAO,QAAO0C,cAAAA,gCAAgC,IAAI,MAApCA,mBAAuC,SAAS;AAAA,EAChE,CAAC;AACD,QAAM,0BAA0B1C,kBAAY,CAAC,MAAM;;AACjD,UAAM,OAAO,EAAE,OAAO,SAAS,GAAG,EAAE;AACpC,WAAO,QAAO0C,cAAAA,gCAAgC,IAAI,MAApCA,mBAAuC,SAAS;AAAA,EAChE,CAAC;AACD,QAAM,iBAAiBC,MAAAA,gCAAgC;AAAA,IACrD,QAAQ;AAAA,IACR,QAAQ;AAAA,EAAA,CACT;AAED/B,aAAAA,UAAU,MAAM;AACd,QACE,CAAC,iBACD,kBACA,oBACAgC,SAAAA,yBAAyB,uBAAuB,EAChD;AAGF,QAAI,QAAS;AACb,QAAI,gBAAgB,KAAM;AAC1B,UAAM,aAAa,GAAG,YAAY,SAAS,IAAI,WAAW;AAC1D,QAAI,aAAa,QAAQ,IAAI,UAAU,EAAG;AAC1C,UAAM,YAAY,WAAW,MAAM;;AACjC,mBAAa,QAAQ,IAAI,UAAU;AACnC,uBAAW,YAAX,oCAAqB,EAAE,MAAM,kBAAkB,UAAU,QAAQ,aAAa;AAC9E,UAAI,SAAS,UAAU,EAAE,IAAI,aAAa,EAAE,KAAK,EAAE,MAAM,SAAS;AAAA,IACpE,GAAG,OAAO;AACV,WAAO,MAAM,aAAa,SAAS;AAAA,EACrC,GAAG;AAAA,IACD;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,EAAA,CACD;AAED,SAAO;AACT;AASA,MAAM,eAAqC,CAAC,EAAE,WAAW;AACvD,QAAM,UAAUjC,WAAAA,OAA6B,IAAI;AACjD,QAAM,CAAC,UAAU,WAAW,IAAID,WAAAA,SAAS,KAAK;AAC9C,QAAM,CAAC,WAAW,YAAY,IAAIA,WAAAA,SAAS,KAAK;AAEhDO,aAAAA,gBAAgB,MAAM;AACpB,UAAM,OAAO,QAAQ;AAErB,QAAI,CAAC,QAAQ,SAAU;AACvB,UAAM,UAAU,MAAY,aAAa,KAAK,eAAe,KAAK,eAAe,CAAC;AAClF,YAAA;AACA,QAAI,OAAO,mBAAmB,YAAa;AAC3C,UAAM,WAAW,IAAI,eAAe,OAAO;AAC3C,aAAS,QAAQ,IAAI;AACrB,WAAO,MAAM,SAAS,WAAA;AAAA,EACxB,GAAG,CAAC,MAAM,QAAQ,CAAC;AAEnB,MAAI,CAAC,MAAM;AACT,WAAOf,2BAAAA,IAAC,KAAA,EAAE,WAAU,0CAAyC,UAAA,qBAAiB;AAAA,EAChF;AACA,SACEqB,2BAAAA,KAAC,OAAA,EAAI,WAAU,kBACb,UAAA;AAAA,IAAArB,2BAAAA;AAAAA,MAAC;AAAA,MAAA;AAAA,QACC,KAAK;AAAA,QACL,WAAWsB,OAAAA;AAAAA,UACT;AAAA,UACA,CAAC,YAAY;AAAA,QAAA;AAAA,QAEf,OAAO,aAAa,CAAC,WAAWqB,YAAAA,oBAAoB,IAAI,IAAI;AAAA,QAE3D,0CAAoB,IAAI;AAAA,MAAA;AAAA,IAAA;AAAA,IAE1B,aAAa,WACZ3C,2BAAAA;AAAAA,MAAC;AAAA,MAAA;AAAA,QACC,MAAK;AAAA,QACL,iBAAe;AAAA,QACf,SAAS,MAAM,YAAY,CAAC,UAAU,CAAC,KAAK;AAAA,QAC5C,WAAU;AAAA,QAET,qBAAW,cAAc;AAAA,MAAA;AAAA,IAAA,IAE1B;AAAA,EAAA,GACN;AAEJ;AAGA,MAAM,qBAAsD,CAAC;AAAA,EAC3D;AAAA,EACA;AAAA,EACA;AAAA,EACA;AACF,MAAM;AACJ,QAAM,UAAU,MAAM,KAAA,EAAO,SAAS;AACtC,QAAM,gBAAgB,CAAC,UAAoD;AACzE,QAAI,MAAM,QAAQ,WAAW,CAAC,MAAM,UAAU;AAC5C,YAAM,eAAA;AACN,UAAI,gBAAgB,KAAK;AAAA,IAC3B,WAAW,MAAM,QAAQ,UAAU;AACjC,YAAM,eAAA;AACN,eAAA;AAAA,IACF;AAAA,EACF;AACA,SACEqB,2BAAAA,KAAC,OAAA,EAAI,WAAU,yCACb,UAAA;AAAA,IAAArB,2BAAAA;AAAAA,MAAC;AAAA,MAAA;AAAA,QACC,WAAS;AAAA,QACT,cAAW;AAAA,QACX;AAAA,QACA,UAAU,CAAC,UAAU,SAAS,MAAM,OAAO,KAAK;AAAA,QAChD,WAAW;AAAA,QACX,MAAM,KAAK,IAAI,GAAG,KAAK,IAAI,GAAG,MAAM,MAAM,IAAI,EAAE,MAAM,CAAC;AAAA,QACvD,WAAU;AAAA,MAAA;AAAA,IAAA;AAAA,IAEZA,2BAAAA;AAAAA,MAAC;AAAA,MAAA;AAAA,QACC,MAAK;AAAA,QACL,cAAW;AAAA,QACX,UAAU,CAAC;AAAA,QACX,SAAS,MAAM,OAAO,KAAK;AAAA,QAC3B,WAAWsB,OAAAA;AAAAA,UACT;AAAA,UACA,CAAC,WAAW;AAAA,QAAA;AAAA,QAGd,UAAAtB,2BAAAA,IAAC4C,YAAAA,WAAA,EAAU,WAAU,WAAA,CAAW;AAAA,MAAA;AAAA,IAAA;AAAA,IAElC5C,2BAAAA;AAAAA,MAAC;AAAA,MAAA;AAAA,QACC,MAAK;AAAA,QACL,cAAW;AAAA,QACX,SAAS;AAAA,QACT,WAAU;AAAA,QAEV,UAAAA,2BAAAA,IAAC6C,YAAAA,OAAA,EAAM,WAAU,WAAA,CAAW;AAAA,MAAA;AAAA,IAAA;AAAA,EAC9B,GACF;AAEJ;;"}
@@ -1,55 +1,18 @@
1
1
  import type { StatewireThread } from '@assistant-ui/react-statewire';
2
2
  import { type DeepAgentThreadStatus } from '../agent-runtime/src/index';
3
3
  import { type FC, type ReactNode } from 'react';
4
- declare module '@assistant-ui/core' {
5
- namespace Assistant {
6
- interface Commands {
7
- /**
8
- * The ⚡ on a queued row (`DeepAgentThread.run_prioritize`). With
9
- * `priority: true` the host moves the entry to the head of the queue
10
- * lane (behind entries prioritized before it), records it durably, and
11
- * the live run ends at its next model-call boundary — after the
12
- * in-flight tool chain, never mid-tool — so the settle delivers the
13
- * entry on top of the finished tool results instead of after the whole
14
- * turn. `priority: false` withdraws the request and leaves the entry
15
- * where it is.
16
- */
17
- runPrioritize: {
18
- type: 'run/prioritize';
19
- runId: string;
20
- messageId: string;
21
- priority: boolean;
22
- };
23
- /**
24
- * "Steer" on a queued row (`DeepAgentThread.run_steer_live`) — what
25
- * ChatGPT and Codex call Steer, versus Queue. The host moves the entry
26
- * to the steer lane and records it as a live steer, so the running
27
- * turn is NOT cancelled: at its next model call — after the in-flight
28
- * tool chain, never mid-tool — the run drains the entry into its own
29
- * context as a user turn and continues. Everything the run produces
30
- * from then on lands after the steered message. Mirrors `run/steer`'s
31
- * params (exactly one of `message` or `messageId`).
32
- */
33
- runSteerLive: {
34
- type: 'run/steer-live';
35
- runId: string;
36
- messageId: string;
37
- };
38
- }
39
- }
40
- }
41
4
  /**
42
5
  * The one queued-messages tray for the server-owned statewire queue and steer
43
6
  * lanes, mounted by the SDK's `AthenaChat`, the Chrome side panel, the Office
44
7
  * task pane, and Olympus.
45
8
  *
46
- * A message sent before the live run has produced any output is a double
47
- * text: the host folds it into the run's turn (`run/enqueue` steers it and
48
- * the run redispatches with both messages), so it never lists here. A
49
- * message sent once the run is answering queues behind it. Rows offer
50
- * "Steer" (`run/steer-live` — the host parks the entry on the steer lane as a
51
- * live steer and the running turn drains it into its own context at its next
52
- * model call, so the run continues with it; ChatGPT's Steer versus Queue),
9
+ * A message the composer sends while a run is live is an `auto` `run/send`:
10
+ * the host's prioritizer folds it into the running turn (the steer lane, which
11
+ * renders in the message list), stops the run for it, or queues it here. A row
12
+ * this client sent as `auto` that the host queued carries a small "queued"
13
+ * hint. Rows offer "Steer" (`run/send` `steer` — the entry moves to the steer
14
+ * lane and the running turn folds it into its own context at its next safe
15
+ * boundary, so the run continues with it; ChatGPT's Steer versus Queue),
53
16
  * inline edit (re-sent under the entry's own id on its own lane, which the
54
17
  * host folds as an in-place content update), and remove (`run/dequeue`).
55
18
  * While the thread rests stopped/errored, stranded steer-lane entries list
@@ -60,7 +23,7 @@ declare module '@assistant-ui/core' {
60
23
  * A row whose send has not settled yet (`isQueueEntryUnsettled` — this
61
24
  * client's optimistic fold, not a host-admitted lane entry) renders as
62
25
  * "Sending…" with no acting affordances: admission is server-side and can
63
- * still refuse the message. Failed run sends (`runs.failed`) list after the
26
+ * still refuse the message. Failed run sends (held, with `localMeta.error`) list after the
64
27
  * lanes with Retry (`retryFailed`) and Discard (`discardFailed`).
65
28
  *
66
29
  * With `autoContinue`, an ordinary stranded settle promotes the queue head