@assistant-ui/core 0.3.15 → 0.3.16

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 (251) hide show
  1. package/dist/internal.d.ts +7 -2
  2. package/dist/internal.js +8 -3
  3. package/dist/model-context/frame/host.d.ts.map +1 -1
  4. package/dist/model-context/frame/host.js +3 -2
  5. package/dist/model-context/frame/host.js.map +1 -1
  6. package/dist/model-context/frame/provider.d.ts +2 -0
  7. package/dist/model-context/frame/provider.d.ts.map +1 -1
  8. package/dist/model-context/frame/provider.js +88 -25
  9. package/dist/model-context/frame/provider.js.map +1 -1
  10. package/dist/model-context/interactable-composer-metadata.d.ts +1 -1
  11. package/dist/model-context/interactable-composer-metadata.js +1 -1
  12. package/dist/model-context/interactable-composer-metadata.js.map +1 -1
  13. package/dist/model-context/registry.d.ts +2 -2
  14. package/dist/model-context/registry.d.ts.map +1 -1
  15. package/dist/model-context/registry.js +9 -28
  16. package/dist/model-context/registry.js.map +1 -1
  17. package/dist/react/client/InMemoryThreadList.d.ts.map +1 -1
  18. package/dist/react/client/InMemoryThreadList.js +24 -20
  19. package/dist/react/client/InMemoryThreadList.js.map +1 -1
  20. package/dist/react/client/Interactables.d.ts.map +1 -1
  21. package/dist/react/client/Interactables.js +59 -177
  22. package/dist/react/client/Interactables.js.map +1 -1
  23. package/dist/react/client/RemoteThreadList.d.ts.map +1 -1
  24. package/dist/react/client/RemoteThreadList.js +23 -56
  25. package/dist/react/client/RemoteThreadList.js.map +1 -1
  26. package/dist/react/index.d.ts +2 -1
  27. package/dist/react/interactables-legacy/Interactables.d.ts.map +1 -1
  28. package/dist/react/interactables-legacy/Interactables.js +56 -174
  29. package/dist/react/interactables-legacy/Interactables.js.map +1 -1
  30. package/dist/react/interactables-shared/useInteractablePersistenceQueue.d.ts +24 -0
  31. package/dist/react/interactables-shared/useInteractablePersistenceQueue.d.ts.map +1 -0
  32. package/dist/react/interactables-shared/useInteractablePersistenceQueue.js +138 -0
  33. package/dist/react/interactables-shared/useInteractablePersistenceQueue.js.map +1 -0
  34. package/dist/react/primitives/composer/ComposerIf.js.map +1 -1
  35. package/dist/react/primitives/composer/ComposerQueue.d.ts +2 -1
  36. package/dist/react/primitives/composer/ComposerQueue.d.ts.map +1 -1
  37. package/dist/react/primitives/message/MessageParts.js.map +1 -1
  38. package/dist/react/runtimes/RemoteThreadListHookInstanceManager.d.ts +1 -1
  39. package/dist/react/runtimes/RemoteThreadListThreadListRuntimeCore.d.ts +1 -1
  40. package/dist/react/runtimes/RemoteThreadListThreadListRuntimeCore.d.ts.map +1 -1
  41. package/dist/react/runtimes/RemoteThreadListThreadListRuntimeCore.js +23 -55
  42. package/dist/react/runtimes/RemoteThreadListThreadListRuntimeCore.js.map +1 -1
  43. package/dist/react/runtimes/assistant-transport/runManager.d.ts.map +1 -1
  44. package/dist/react/runtimes/assistant-transport/runManager.js +2 -12
  45. package/dist/react/runtimes/assistant-transport/runManager.js.map +1 -1
  46. package/dist/react/runtimes/cloud/AssistantCloudThreadHistoryAdapter.d.ts +3 -10
  47. package/dist/react/runtimes/cloud/AssistantCloudThreadHistoryAdapter.d.ts.map +1 -1
  48. package/dist/react/runtimes/cloud/AssistantCloudThreadHistoryAdapter.js +20 -67
  49. package/dist/react/runtimes/cloud/AssistantCloudThreadHistoryAdapter.js.map +1 -1
  50. package/dist/react/runtimes/cloud/createCloudThreadListAdapterCreateFallback.d.ts +12 -0
  51. package/dist/react/runtimes/cloud/createCloudThreadListAdapterCreateFallback.d.ts.map +1 -0
  52. package/dist/react/runtimes/cloud/createCloudThreadListAdapterCreateFallback.js +10 -0
  53. package/dist/react/runtimes/cloud/createCloudThreadListAdapterCreateFallback.js.map +1 -0
  54. package/dist/react/runtimes/cloud/useCloudThreadListRuntime.js.map +1 -1
  55. package/dist/react/runtimes/createMessageConverter.d.ts +2 -1
  56. package/dist/react/runtimes/createMessageConverter.d.ts.map +1 -1
  57. package/dist/react/runtimes/external-message-converter.d.ts +6 -25
  58. package/dist/react/runtimes/external-message-converter.d.ts.map +1 -1
  59. package/dist/react/runtimes/external-message-converter.js +33 -233
  60. package/dist/react/runtimes/external-message-converter.js.map +1 -1
  61. package/dist/runtime/api/composer-runtime.d.ts +1 -1
  62. package/dist/runtime/api/composer-runtime.js.map +1 -1
  63. package/dist/runtime/api/thread-runtime.d.ts +1 -2
  64. package/dist/runtime/api/thread-runtime.d.ts.map +1 -1
  65. package/dist/runtime/base/base-composer-runtime-core.d.ts +1 -1
  66. package/dist/runtime/base/base-composer-runtime-core.d.ts.map +1 -1
  67. package/dist/runtime/base/base-composer-runtime-core.js +14 -29
  68. package/dist/runtime/base/base-composer-runtime-core.js.map +1 -1
  69. package/dist/runtime/base/base-thread-runtime-core.d.ts +2 -4
  70. package/dist/runtime/base/base-thread-runtime-core.d.ts.map +1 -1
  71. package/dist/runtime/base/base-thread-runtime-core.js +3 -9
  72. package/dist/runtime/base/base-thread-runtime-core.js.map +1 -1
  73. package/dist/runtime/base/default-thread-composer-runtime-core.d.ts +1 -1
  74. package/dist/runtime/base/default-thread-composer-runtime-core.d.ts.map +1 -1
  75. package/dist/runtime/base/default-thread-composer-runtime-core.js +1 -1
  76. package/dist/runtime/base/default-thread-composer-runtime-core.js.map +1 -1
  77. package/dist/runtime/interfaces/composer-runtime-core.d.ts +1 -1
  78. package/dist/runtime/interfaces/thread-runtime-core.d.ts +1 -1
  79. package/dist/runtime/internal.d.ts +2 -1
  80. package/dist/runtime/internal.js +2 -1
  81. package/dist/runtime/queue/external-thread-queue-adapter.d.ts +1 -1
  82. package/dist/runtime/queue/message-queue.d.ts.map +1 -1
  83. package/dist/runtime/queue/message-queue.js +1 -1
  84. package/dist/runtime/queue/message-queue.js.map +1 -1
  85. package/dist/runtime/queue/queue-item.d.ts +12 -0
  86. package/dist/runtime/queue/queue-item.d.ts.map +1 -0
  87. package/dist/runtime/queue/queue-item.js +6 -0
  88. package/dist/runtime/queue/queue-item.js.map +1 -0
  89. package/dist/runtime/utils/abortable-thread-load.d.ts +15 -0
  90. package/dist/runtime/utils/abortable-thread-load.d.ts.map +1 -0
  91. package/dist/runtime/utils/abortable-thread-load.js +35 -0
  92. package/dist/runtime/utils/abortable-thread-load.js.map +1 -0
  93. package/dist/runtime/utils/attachment-add-operations.d.ts +18 -0
  94. package/dist/runtime/utils/attachment-add-operations.d.ts.map +1 -0
  95. package/dist/runtime/utils/attachment-add-operations.js +43 -0
  96. package/dist/runtime/utils/attachment-add-operations.js.map +1 -0
  97. package/dist/runtime/utils/auto-status.d.ts +6 -1
  98. package/dist/runtime/utils/auto-status.d.ts.map +1 -1
  99. package/dist/runtime/utils/auto-status.js +7 -1
  100. package/dist/runtime/utils/auto-status.js.map +1 -1
  101. package/dist/runtime/utils/external-message-conversion.d.ts +47 -0
  102. package/dist/runtime/utils/external-message-conversion.d.ts.map +1 -0
  103. package/dist/runtime/utils/external-message-conversion.js +221 -0
  104. package/dist/runtime/utils/external-message-conversion.js.map +1 -0
  105. package/dist/runtime/utils/external-store-message.d.ts +2 -1
  106. package/dist/runtime/utils/external-store-message.d.ts.map +1 -1
  107. package/dist/runtime/utils/external-store-message.js +2 -1
  108. package/dist/runtime/utils/external-store-message.js.map +1 -1
  109. package/dist/runtime/utils/message-repository-session.d.ts +30 -0
  110. package/dist/runtime/utils/message-repository-session.d.ts.map +1 -0
  111. package/dist/runtime/utils/message-repository-session.js +130 -0
  112. package/dist/runtime/utils/message-repository-session.js.map +1 -0
  113. package/dist/runtime/utils/message-repository.d.ts.map +1 -1
  114. package/dist/runtime/utils/message-repository.js +3 -4
  115. package/dist/runtime/utils/message-repository.js.map +1 -1
  116. package/dist/runtime/utils/pending-tool-calls.d.ts +20 -0
  117. package/dist/runtime/utils/pending-tool-calls.d.ts.map +1 -0
  118. package/dist/runtime/utils/pending-tool-calls.js +22 -0
  119. package/dist/runtime/utils/pending-tool-calls.js.map +1 -0
  120. package/dist/runtime/utils/thread-message-like.d.ts +2 -1
  121. package/dist/runtime/utils/thread-message-like.d.ts.map +1 -1
  122. package/dist/runtime/utils/thread-message-like.js.map +1 -1
  123. package/dist/runtimes/external-store/external-store-thread-list-runtime-core.d.ts +2 -5
  124. package/dist/runtimes/external-store/external-store-thread-list-runtime-core.d.ts.map +1 -1
  125. package/dist/runtimes/external-store/external-store-thread-list-runtime-core.js +3 -10
  126. package/dist/runtimes/external-store/external-store-thread-list-runtime-core.js.map +1 -1
  127. package/dist/runtimes/external-store/external-store-thread-runtime-core.d.ts +19 -1
  128. package/dist/runtimes/external-store/external-store-thread-runtime-core.d.ts.map +1 -1
  129. package/dist/runtimes/external-store/external-store-thread-runtime-core.js +122 -20
  130. package/dist/runtimes/external-store/external-store-thread-runtime-core.js.map +1 -1
  131. package/dist/runtimes/local/local-thread-runtime-core.d.ts +3 -1
  132. package/dist/runtimes/local/local-thread-runtime-core.d.ts.map +1 -1
  133. package/dist/runtimes/local/local-thread-runtime-core.js +20 -2
  134. package/dist/runtimes/local/local-thread-runtime-core.js.map +1 -1
  135. package/dist/runtimes/remote-thread-list/remote-thread-state.d.ts +12 -1
  136. package/dist/runtimes/remote-thread-list/remote-thread-state.d.ts.map +1 -1
  137. package/dist/runtimes/remote-thread-list/remote-thread-state.js +77 -1
  138. package/dist/runtimes/remote-thread-list/remote-thread-state.js.map +1 -1
  139. package/dist/runtimes/tool-invocations/ToolInvocationTracker.d.ts.map +1 -1
  140. package/dist/runtimes/tool-invocations/ToolInvocationTracker.js +2 -0
  141. package/dist/runtimes/tool-invocations/ToolInvocationTracker.js.map +1 -1
  142. package/dist/store/clients/external-thread.d.ts.map +1 -1
  143. package/dist/store/clients/external-thread.js +74 -99
  144. package/dist/store/clients/external-thread.js.map +1 -1
  145. package/dist/store/clients/single-thread-list.d.ts.map +1 -1
  146. package/dist/store/clients/single-thread-list.js +1 -1
  147. package/dist/store/clients/single-thread-list.js.map +1 -1
  148. package/dist/store/clients/suggestions.d.ts.map +1 -1
  149. package/dist/store/clients/suggestions.js +16 -7
  150. package/dist/store/clients/suggestions.js.map +1 -1
  151. package/dist/store/index.d.ts +4 -2
  152. package/dist/store/scope-registration.d.ts +1 -1
  153. package/dist/store/scopes/composer.d.ts +2 -1
  154. package/dist/store/scopes/composer.d.ts.map +1 -1
  155. package/dist/store/scopes/message.d.ts +1 -1
  156. package/dist/store/scopes/queue-item.d.ts +2 -9
  157. package/dist/store/scopes/queue-item.d.ts.map +1 -1
  158. package/dist/store/scopes/queue-item.js +0 -6
  159. package/dist/types/message.d.ts +7 -3
  160. package/dist/types/message.d.ts.map +1 -1
  161. package/dist/types/message.js.map +1 -1
  162. package/dist/utils/data-url.d.ts +14 -1
  163. package/dist/utils/data-url.d.ts.map +1 -1
  164. package/dist/utils/data-url.js +13 -1
  165. package/dist/utils/data-url.js.map +1 -1
  166. package/dist/utils/invoke-user-callback.d.ts +5 -0
  167. package/dist/utils/invoke-user-callback.d.ts.map +1 -0
  168. package/dist/utils/invoke-user-callback.js +19 -0
  169. package/dist/utils/invoke-user-callback.js.map +1 -0
  170. package/dist/utils/normalizePartStatus.js.map +1 -1
  171. package/package.json +10 -10
  172. package/src/internal.ts +12 -0
  173. package/src/model-context/frame/host.test.ts +91 -7
  174. package/src/model-context/frame/host.ts +7 -2
  175. package/src/model-context/frame/provider.test.ts +267 -12
  176. package/src/model-context/frame/provider.ts +113 -31
  177. package/src/model-context/interactable-composer-metadata.ts +1 -1
  178. package/src/model-context/registry.test.ts +44 -0
  179. package/src/model-context/registry.ts +13 -35
  180. package/src/react/client/InMemoryThreadList.test.tsx +49 -0
  181. package/src/react/client/InMemoryThreadList.ts +7 -1
  182. package/src/react/client/Interactables.ts +19 -178
  183. package/src/react/client/RemoteThreadList.test.ts +96 -0
  184. package/src/react/client/RemoteThreadList.ts +27 -59
  185. package/src/react/interactables-legacy/Interactables.ts +20 -177
  186. package/src/react/interactables-shared/useInteractablePersistenceQueue.test.tsx +161 -0
  187. package/src/react/interactables-shared/useInteractablePersistenceQueue.ts +206 -0
  188. package/src/react/runtimes/RemoteThreadListThreadListRuntimeCore.tsx +26 -56
  189. package/src/react/runtimes/assistant-transport/runManager.ts +4 -17
  190. package/src/react/runtimes/cloud/AssistantCloudThreadHistoryAdapter.test.tsx +92 -0
  191. package/src/react/runtimes/cloud/AssistantCloudThreadHistoryAdapter.ts +40 -141
  192. package/src/react/runtimes/cloud/createCloudThreadListAdapterCreateFallback.test.ts +37 -0
  193. package/src/react/runtimes/cloud/createCloudThreadListAdapterCreateFallback.ts +18 -0
  194. package/src/react/runtimes/external-message-converter.test.ts +0 -14
  195. package/src/react/runtimes/external-message-converter.test.tsx +77 -0
  196. package/src/react/runtimes/external-message-converter.ts +58 -481
  197. package/src/runtime/api/composer-runtime.ts +1 -1
  198. package/src/runtime/api/message-runtime.test.ts +28 -1
  199. package/src/runtime/base/base-composer-runtime-core.ts +20 -40
  200. package/src/runtime/base/base-thread-runtime-core.test.ts +16 -0
  201. package/src/runtime/base/base-thread-runtime-core.ts +6 -11
  202. package/src/runtime/base/default-thread-composer-runtime-core.ts +1 -4
  203. package/src/runtime/interfaces/composer-runtime-core.ts +1 -1
  204. package/src/runtime/interfaces/thread-runtime-core.ts +1 -1
  205. package/src/runtime/internal.ts +5 -0
  206. package/src/runtime/queue/external-thread-queue-adapter.ts +1 -1
  207. package/src/runtime/queue/message-queue.ts +1 -4
  208. package/src/runtime/queue/queue-item.ts +10 -0
  209. package/src/runtime/utils/abortable-thread-load.test.ts +87 -0
  210. package/src/runtime/utils/abortable-thread-load.ts +53 -0
  211. package/src/runtime/utils/attachment-add-operations.ts +59 -0
  212. package/src/runtime/utils/auto-status.ts +33 -0
  213. package/src/runtime/utils/external-message-conversion.test.ts +113 -0
  214. package/src/runtime/utils/external-message-conversion.ts +494 -0
  215. package/src/runtime/utils/external-store-message.ts +2 -0
  216. package/src/runtime/utils/message-repository-session.test.ts +195 -0
  217. package/src/runtime/utils/message-repository-session.ts +176 -0
  218. package/src/runtime/utils/message-repository.ts +7 -4
  219. package/src/runtime/utils/pending-tool-calls.test.ts +57 -0
  220. package/src/runtime/utils/pending-tool-calls.ts +35 -0
  221. package/src/runtime/utils/thread-message-like.ts +2 -0
  222. package/src/runtimes/external-store/external-store-thread-list-runtime-core.ts +6 -14
  223. package/src/runtimes/external-store/external-store-thread-runtime-core.ts +175 -28
  224. package/src/runtimes/local/local-thread-runtime-core.test.ts +172 -1
  225. package/src/runtimes/local/local-thread-runtime-core.ts +48 -3
  226. package/src/runtimes/remote-thread-list/remote-thread-state.test.ts +37 -0
  227. package/src/runtimes/remote-thread-list/remote-thread-state.ts +123 -0
  228. package/src/runtimes/tool-invocations/EDGE_CASES.md +17 -0
  229. package/src/runtimes/tool-invocations/ToolInvocationTracker.test.ts +140 -0
  230. package/src/runtimes/tool-invocations/ToolInvocationTracker.ts +3 -0
  231. package/src/store/clients/external-thread.ts +16 -61
  232. package/src/store/clients/single-thread-list.ts +4 -1
  233. package/src/store/clients/suggestions.test.ts +31 -0
  234. package/src/store/clients/suggestions.ts +18 -19
  235. package/src/store/scopes/message.ts +1 -1
  236. package/src/store/scopes/queue-item.ts +2 -9
  237. package/src/tests/MessageRepository.test.ts +77 -0
  238. package/src/tests/RemoteThreadListThreadListRuntimeCore-load-race.test.ts +194 -0
  239. package/src/tests/RemoteThreadListThreadListRuntimeCore-title-race.test.ts +158 -0
  240. package/src/tests/external-store-thread-runtime-core-adapter.test.ts +164 -0
  241. package/src/tests/external-store-thread-runtime-core.test.ts +642 -0
  242. package/src/tests/external-thread-attachments.test.tsx +173 -0
  243. package/src/tests/single-thread-list-item.test.tsx +47 -0
  244. package/src/tests/thread-message-like.test.ts +39 -1
  245. package/src/types/message.ts +8 -3
  246. package/src/utils/data-url.test.ts +52 -1
  247. package/src/utils/data-url.ts +21 -0
  248. package/src/utils/invoke-user-callback.test.ts +82 -0
  249. package/src/utils/invoke-user-callback.ts +31 -0
  250. package/src/utils/normalizePartStatus.ts +1 -1
  251. package/dist/store/scopes/queue-item.js.map +0 -1
@@ -0,0 +1,176 @@
1
+ import type { ThreadMessage } from "../../types/message";
2
+ import {
3
+ MessageRepository,
4
+ type ExportedMessageRepository,
5
+ } from "./message-repository";
6
+
7
+ export type MessageRepositorySessionOptions = {
8
+ decorateExport?: (
9
+ exported: ExportedMessageRepository,
10
+ repository: MessageRepository,
11
+ ) => ExportedMessageRepository;
12
+ };
13
+
14
+ export const createMessageRepositorySession = (
15
+ options: MessageRepositorySessionOptions = {},
16
+ ) => {
17
+ const repository = new MessageRepository();
18
+ let exportedRepository: ExportedMessageRepository | undefined;
19
+
20
+ const getMessages = (): readonly ThreadMessage[] => {
21
+ return repository.getMessages();
22
+ };
23
+
24
+ const tryGetMessage = (messageId: string) => {
25
+ try {
26
+ return repository.getMessage(messageId);
27
+ } catch {
28
+ return undefined;
29
+ }
30
+ };
31
+
32
+ const tryGetMessages = (
33
+ messageId: string,
34
+ ): readonly ThreadMessage[] | undefined => {
35
+ try {
36
+ return repository.getMessages(messageId);
37
+ } catch {
38
+ return undefined;
39
+ }
40
+ };
41
+
42
+ const hasMessage = (messageId: string): boolean => {
43
+ return tryGetMessage(messageId) !== undefined;
44
+ };
45
+
46
+ const addOrUpdateMessage = (
47
+ parentId: string | null,
48
+ message: ThreadMessage,
49
+ ): void => {
50
+ repository.addOrUpdateMessage(parentId, message);
51
+ exportedRepository = undefined;
52
+ };
53
+
54
+ const deleteMessage = (
55
+ messageId: string,
56
+ replacementId?: string | null,
57
+ ): void => {
58
+ repository.deleteMessage(messageId, replacementId);
59
+ exportedRepository = undefined;
60
+ };
61
+
62
+ const tryDeleteMessage = (messageId: string): boolean => {
63
+ if (!hasMessage(messageId)) return false;
64
+ deleteMessage(messageId);
65
+ return true;
66
+ };
67
+
68
+ const switchToBranch = (messageId: string): void => {
69
+ repository.switchToBranch(messageId);
70
+ exportedRepository = undefined;
71
+ };
72
+
73
+ const resetHead = (messageId: string | null): void => {
74
+ repository.resetHead(messageId);
75
+ exportedRepository = undefined;
76
+ };
77
+
78
+ const clear = (): void => {
79
+ repository.clear();
80
+ exportedRepository = undefined;
81
+ };
82
+
83
+ const updateMessage = (
84
+ messageId: string,
85
+ updater: (message: ThreadMessage) => ThreadMessage,
86
+ ): boolean => {
87
+ const item = tryGetMessage(messageId);
88
+ if (!item) return false;
89
+ const message = updater(item.message);
90
+ if (message === item.message) return false;
91
+ addOrUpdateMessage(item.parentId, message);
92
+ return true;
93
+ };
94
+
95
+ const applyExternalMessageRepository = (
96
+ loaded: ExportedMessageRepository,
97
+ ): void => {
98
+ const headId = loaded.headId ?? loaded.messages.at(-1)?.message.id ?? null;
99
+ const ids = new Set<string>();
100
+ let degenerate = false;
101
+ for (const { message } of loaded.messages) {
102
+ if (ids.has(message.id)) {
103
+ degenerate = true;
104
+ break;
105
+ }
106
+ ids.add(message.id);
107
+ }
108
+ if (headId !== null && !ids.has(headId)) degenerate = true;
109
+
110
+ if (!degenerate) {
111
+ clear();
112
+ let pending = [...loaded.messages];
113
+ const importedIds = new Set<string>();
114
+
115
+ while (pending.length > 0) {
116
+ const unresolved: typeof pending = [];
117
+ let progressed = false;
118
+ for (const item of pending) {
119
+ if (item.parentId !== null && !importedIds.has(item.parentId)) {
120
+ unresolved.push(item);
121
+ continue;
122
+ }
123
+ addOrUpdateMessage(item.parentId, item.message);
124
+ importedIds.add(item.message.id);
125
+ progressed = true;
126
+ }
127
+ if (!progressed) {
128
+ degenerate = true;
129
+ break;
130
+ }
131
+ pending = unresolved;
132
+ }
133
+ }
134
+
135
+ if (degenerate) {
136
+ clear();
137
+ let previousId: string | null = null;
138
+ for (const { message } of loaded.messages) {
139
+ const existing = tryGetMessage(message.id);
140
+ addOrUpdateMessage(existing ? existing.parentId : previousId, message);
141
+ previousId = message.id;
142
+ }
143
+ resetHead(previousId);
144
+ } else {
145
+ resetHead(headId);
146
+ }
147
+ };
148
+
149
+ return {
150
+ getMessages,
151
+ get headId() {
152
+ return repository.headId;
153
+ },
154
+ export: (): ExportedMessageRepository => {
155
+ exportedRepository ??= options.decorateExport
156
+ ? options.decorateExport(repository.export(), repository)
157
+ : repository.export();
158
+ return exportedRepository;
159
+ },
160
+ tryGetMessage,
161
+ tryGetMessages,
162
+ hasMessage,
163
+ addOrUpdateMessage,
164
+ deleteMessage,
165
+ tryDeleteMessage,
166
+ switchToBranch,
167
+ resetHead,
168
+ clear,
169
+ updateMessage,
170
+ applyExternalMessageRepository,
171
+ };
172
+ };
173
+
174
+ export type MessageRepositorySession = ReturnType<
175
+ typeof createMessageRepositorySession
176
+ >;
@@ -2,7 +2,7 @@ import type { ThreadMessage } from "../../types/message";
2
2
  import type { RunConfig } from "../../types/message";
3
3
  import { generateId } from "../../utils/id";
4
4
  import type { ThreadMessageLike } from "./thread-message-like";
5
- import { getAutoStatus } from "./auto-status";
5
+ import { getContentAutoStatus } from "./auto-status";
6
6
  import { fromThreadMessageLike } from "./thread-message-like";
7
7
 
8
8
  export type ExportedMessageRepositoryItem = {
@@ -28,7 +28,7 @@ export const ExportedMessageRepository = {
28
28
  fromThreadMessageLike(
29
29
  m,
30
30
  generateId(),
31
- getAutoStatus(false, false, false, false, undefined),
31
+ getContentAutoStatus(m.content, false, false),
32
32
  ),
33
33
  );
34
34
 
@@ -47,7 +47,6 @@ export const ExportedMessageRepository = {
47
47
  }[],
48
48
  options?: { headId?: string | null },
49
49
  ): ExportedMessageRepository => {
50
- const fallbackStatus = getAutoStatus(false, false, false, false, undefined);
51
50
  return {
52
51
  ...(options?.headId !== undefined
53
52
  ? { headId: options.headId }
@@ -60,7 +59,11 @@ export const ExportedMessageRepository = {
60
59
  }
61
60
  return {
62
61
  parentId,
63
- message: fromThreadMessageLike(message, message.id, fallbackStatus),
62
+ message: fromThreadMessageLike(
63
+ message,
64
+ message.id,
65
+ getContentAutoStatus(message.content, false, false),
66
+ ),
64
67
  };
65
68
  }),
66
69
  };
@@ -0,0 +1,57 @@
1
+ import { describe, expect, it } from "vitest";
2
+ import {
3
+ createToolCallCancellationStub,
4
+ scanPendingToolCalls,
5
+ } from "./pending-tool-calls";
6
+
7
+ type Message =
8
+ | { type: "assistant"; toolCalls: { id: string; name: string }[] }
9
+ | { type: "tool"; toolCallId: string };
10
+
11
+ const getPendingToolCalls = (messages: readonly Message[]) =>
12
+ scanPendingToolCalls(
13
+ messages,
14
+ (message) =>
15
+ message.type === "assistant"
16
+ ? { toolCalls: message.toolCalls }
17
+ : { toolCallId: message.toolCallId },
18
+ (toolCall) => toolCall.id,
19
+ );
20
+
21
+ describe("scanPendingToolCalls", () => {
22
+ it("returns tool calls without matching results in history order", () => {
23
+ expect(
24
+ getPendingToolCalls([
25
+ {
26
+ type: "assistant",
27
+ toolCalls: [
28
+ { id: "call-1", name: "first" },
29
+ { id: "call-2", name: "second" },
30
+ ],
31
+ },
32
+ { type: "tool", toolCallId: "call-1" },
33
+ {
34
+ type: "assistant",
35
+ toolCalls: [{ id: "call-3", name: "third" }],
36
+ },
37
+ ]),
38
+ ).toEqual([
39
+ { id: "call-2", name: "second" },
40
+ { id: "call-3", name: "third" },
41
+ ]);
42
+ });
43
+ });
44
+
45
+ describe("createToolCallCancellationStub", () => {
46
+ it("creates an error tool result with the cancellation payload", () => {
47
+ expect(
48
+ createToolCallCancellationStub({ id: "call-1", name: "lookup" }),
49
+ ).toEqual({
50
+ type: "tool",
51
+ name: "lookup",
52
+ tool_call_id: "call-1",
53
+ content: JSON.stringify({ cancelled: true }),
54
+ status: "error",
55
+ });
56
+ });
57
+ });
@@ -0,0 +1,35 @@
1
+ type PendingToolCallMessage<TToolCall> =
2
+ | { toolCalls: readonly TToolCall[] }
3
+ | { toolCallId: string }
4
+ | undefined;
5
+
6
+ export const scanPendingToolCalls = <TMessage, TToolCall>(
7
+ messages: readonly TMessage[],
8
+ getMessage: (message: TMessage) => PendingToolCallMessage<TToolCall>,
9
+ getToolCallId: (toolCall: TToolCall) => string,
10
+ ): TToolCall[] => {
11
+ const pending = new Map<string, TToolCall>();
12
+ for (const message of messages) {
13
+ const value = getMessage(message);
14
+ if (!value) continue;
15
+ if ("toolCalls" in value) {
16
+ for (const toolCall of value.toolCalls) {
17
+ pending.set(getToolCallId(toolCall), toolCall);
18
+ }
19
+ } else {
20
+ pending.delete(value.toolCallId);
21
+ }
22
+ }
23
+ return [...pending.values()];
24
+ };
25
+
26
+ export const createToolCallCancellationStub = (toolCall: {
27
+ readonly id: string;
28
+ readonly name: string;
29
+ }) => ({
30
+ type: "tool" as const,
31
+ name: toolCall.name,
32
+ tool_call_id: toolCall.id,
33
+ content: JSON.stringify({ cancelled: true }),
34
+ status: "error" as const,
35
+ });
@@ -25,6 +25,7 @@ import type {
25
25
  TextMessagePart,
26
26
  ToolApprovalOption,
27
27
  ToolCallTiming,
28
+ ToolCallMessagePartMcpMetadata,
28
29
  } from "../../types/message";
29
30
  import type {
30
31
  ReadonlyJSONObject,
@@ -63,6 +64,7 @@ export type ThreadMessageLike = {
63
64
  readonly messages?: readonly ThreadMessage[] | undefined;
64
65
  readonly interrupt?: { type: "human"; payload: unknown };
65
66
  readonly timing?: ToolCallTiming;
67
+ readonly mcp?: ToolCallMessagePartMcpMetadata;
66
68
  readonly providerMetadata?: PartProviderMetadata;
67
69
  readonly approval?: {
68
70
  readonly id: string;
@@ -1,4 +1,3 @@
1
- import type { Unsubscribe } from "../../types/unsubscribe";
2
1
  import type { ExternalStoreThreadRuntimeCore } from "./external-store-thread-runtime-core";
3
2
  import type {
4
3
  ThreadListItemCoreState,
@@ -6,7 +5,7 @@ import type {
6
5
  } from "../../runtime/interfaces/thread-list-runtime-core";
7
6
  import type { ExternalStoreThreadListAdapter } from "./external-store-adapter";
8
7
  import { invalidateThreadRuntime } from "../../runtime/utils/thread-runtime-lifecycle";
9
- import { notifySubscribers } from "../../subscribable/subscribable";
8
+ import { BaseSubscribable } from "../../subscribable/subscribable";
10
9
 
11
10
  export type ExternalStoreThreadFactory = () => ExternalStoreThreadRuntimeCore;
12
11
 
@@ -24,7 +23,10 @@ const DEFAULT_THREAD_DATA = Object.freeze({
24
23
  [DEFAULT_THREAD_ID]: DEFAULT_THREAD,
25
24
  });
26
25
 
27
- export class ExternalStoreThreadListRuntimeCore implements ThreadListRuntimeCore {
26
+ export class ExternalStoreThreadListRuntimeCore
27
+ extends BaseSubscribable
28
+ implements ThreadListRuntimeCore
29
+ {
28
30
  private _mainThreadId: string = DEFAULT_THREAD_ID;
29
31
  private _threads: readonly string[] = DEFAULT_THREADS;
30
32
  private _archivedThreads: readonly string[] = EMPTY_ARRAY;
@@ -68,6 +70,7 @@ export class ExternalStoreThreadListRuntimeCore implements ThreadListRuntimeCore
68
70
  adapter: ExternalStoreThreadListAdapter = {},
69
71
  threadFactory: ExternalStoreThreadFactory,
70
72
  ) {
73
+ super();
71
74
  this.threadFactory = threadFactory;
72
75
  this.__internal_setAdapter(adapter, true);
73
76
  }
@@ -262,15 +265,4 @@ export class ExternalStoreThreadListRuntimeCore implements ThreadListRuntimeCore
262
265
  public generateTitle(): never {
263
266
  throw new Error("Method not implemented.");
264
267
  }
265
-
266
- private _subscriptions = new Set<() => void>();
267
-
268
- public subscribe(callback: () => void): Unsubscribe {
269
- this._subscriptions.add(callback);
270
- return () => this._subscriptions.delete(callback);
271
- }
272
-
273
- private _notifySubscribers() {
274
- notifySubscribers(this._subscriptions);
275
- }
276
268
  }