@assistant-ui/core 0.3.17 → 0.3.19
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.
- package/dist/adapters/attachment.d.ts.map +1 -1
- package/dist/adapters/attachment.js +5 -4
- package/dist/adapters/attachment.js.map +1 -1
- package/dist/adapters/speech.d.ts.map +1 -1
- package/dist/adapters/speech.js +13 -3
- package/dist/adapters/speech.js.map +1 -1
- package/dist/adapters/thread-history.d.ts +4 -0
- package/dist/adapters/thread-history.d.ts.map +1 -1
- package/dist/index.d.ts +3 -3
- package/dist/index.js.map +1 -1
- package/dist/internal.d.ts +4 -3
- package/dist/internal.js +3 -2
- package/dist/model-context/frame/host.d.ts.map +1 -1
- package/dist/model-context/frame/host.js +35 -14
- package/dist/model-context/frame/host.js.map +1 -1
- package/dist/model-context/frame/provider.d.ts +2 -0
- package/dist/model-context/frame/provider.d.ts.map +1 -1
- package/dist/model-context/frame/provider.js +30 -7
- package/dist/model-context/frame/provider.js.map +1 -1
- package/dist/model-context/interactable-composer-metadata.d.ts.map +1 -1
- package/dist/model-context/interactable-composer-metadata.js +27 -18
- package/dist/model-context/interactable-composer-metadata.js.map +1 -1
- package/dist/model-context/registry.d.ts.map +1 -1
- package/dist/model-context/registry.js +3 -5
- package/dist/model-context/registry.js.map +1 -1
- package/dist/model-context/types.d.ts.map +1 -1
- package/dist/model-context/types.js +5 -4
- package/dist/model-context/types.js.map +1 -1
- package/dist/react/adapters/LocalStorageThreadListAdapter.d.ts.map +1 -1
- package/dist/react/adapters/LocalStorageThreadListAdapter.js +45 -7
- package/dist/react/adapters/LocalStorageThreadListAdapter.js.map +1 -1
- package/dist/react/client/DataRenderers.d.ts.map +1 -1
- package/dist/react/client/DataRenderers.js +20 -15
- package/dist/react/client/DataRenderers.js.map +1 -1
- package/dist/react/client/InMemoryThreadList.d.ts.map +1 -1
- package/dist/react/client/InMemoryThreadList.js +62 -56
- package/dist/react/client/InMemoryThreadList.js.map +1 -1
- package/dist/react/client/Interactables.d.ts.map +1 -1
- package/dist/react/client/Interactables.js +35 -32
- package/dist/react/client/Interactables.js.map +1 -1
- package/dist/react/client/RemoteThreadList.d.ts +1 -0
- package/dist/react/client/RemoteThreadList.d.ts.map +1 -1
- package/dist/react/client/RemoteThreadList.js +154 -143
- package/dist/react/client/RemoteThreadList.js.map +1 -1
- package/dist/react/client/Tools.d.ts.map +1 -1
- package/dist/react/client/Tools.js +18 -16
- package/dist/react/client/Tools.js.map +1 -1
- package/dist/react/client/interactable-model-context.d.ts.map +1 -1
- package/dist/react/client/interactable-model-context.js +3 -2
- package/dist/react/client/interactable-model-context.js.map +1 -1
- package/dist/react/index.d.ts +2 -2
- package/dist/react/index.js +2 -2
- package/dist/react/interactables-legacy/Interactables.js +242 -121
- package/dist/react/interactables-legacy/Interactables.js.map +1 -1
- package/dist/react/interactables-legacy/useAssistantInteractable.d.ts.map +1 -1
- package/dist/react/interactables-legacy/useAssistantInteractable.js +3 -0
- package/dist/react/interactables-legacy/useAssistantInteractable.js.map +1 -1
- package/dist/react/interactables-shared/useInteractablePersistenceQueue.d.ts.map +1 -1
- package/dist/react/interactables-shared/useInteractablePersistenceQueue.js +11 -9
- package/dist/react/interactables-shared/useInteractablePersistenceQueue.js.map +1 -1
- package/dist/react/model-context/makeAssistantTool.d.ts +2 -2
- package/dist/react/model-context/makeAssistantTool.js +1 -1
- package/dist/react/model-context/makeAssistantTool.js.map +1 -1
- package/dist/react/model-context/useAssistantTool.d.ts +2 -2
- package/dist/react/model-context/useAssistantTool.js +1 -1
- package/dist/react/model-context/useAssistantTool.js.map +1 -1
- package/dist/react/model-context/useInteractable.d.ts.map +1 -1
- package/dist/react/model-context/useInteractable.js +4 -1
- package/dist/react/model-context/useInteractable.js.map +1 -1
- package/dist/react/model-context/useInteractableVersions.js +1 -1
- package/dist/react/model-context/useToolArgsStatus.d.ts.map +1 -1
- package/dist/react/model-context/useToolArgsStatus.js +2 -1
- package/dist/react/model-context/useToolArgsStatus.js.map +1 -1
- package/dist/react/primitives/message/MessageGroupedParts.d.ts +11 -2
- package/dist/react/primitives/message/MessageGroupedParts.d.ts.map +1 -1
- package/dist/react/primitives/message/MessageGroupedParts.js +3 -2
- package/dist/react/primitives/message/MessageGroupedParts.js.map +1 -1
- package/dist/react/primitives/part/PartMessages.d.ts +1 -0
- package/dist/react/primitives/part/PartMessages.d.ts.map +1 -1
- package/dist/react/primitives/part/PartMessages.js +1 -0
- package/dist/react/primitives/part/PartMessages.js.map +1 -1
- package/dist/react/primitives/thread/ThreadMessages.d.ts.map +1 -1
- package/dist/react/primitives/thread/ThreadMessages.js +6 -5
- package/dist/react/primitives/thread/ThreadMessages.js.map +1 -1
- package/dist/react/runtimes/RemoteThreadListHookInstanceManager.d.ts.map +1 -1
- package/dist/react/runtimes/RemoteThreadListHookInstanceManager.js +16 -8
- package/dist/react/runtimes/RemoteThreadListHookInstanceManager.js.map +1 -1
- package/dist/react/runtimes/RemoteThreadListThreadListRuntimeCore.d.ts +5 -1
- package/dist/react/runtimes/RemoteThreadListThreadListRuntimeCore.d.ts.map +1 -1
- package/dist/react/runtimes/RemoteThreadListThreadListRuntimeCore.js +105 -104
- package/dist/react/runtimes/RemoteThreadListThreadListRuntimeCore.js.map +1 -1
- package/dist/react/runtimes/RemoteThreadResource.d.ts +1 -0
- package/dist/react/runtimes/RemoteThreadResource.d.ts.map +1 -1
- package/dist/react/runtimes/RemoteThreadResource.js +13 -11
- package/dist/react/runtimes/RemoteThreadResource.js.map +1 -1
- package/dist/react/runtimes/cloud/AssistantCloudThreadHistoryAdapter.d.ts +5 -24
- package/dist/react/runtimes/cloud/AssistantCloudThreadHistoryAdapter.d.ts.map +1 -1
- package/dist/react/runtimes/cloud/AssistantCloudThreadHistoryAdapter.js +354 -226
- package/dist/react/runtimes/cloud/AssistantCloudThreadHistoryAdapter.js.map +1 -1
- package/dist/react/runtimes/cloud/CloudFileAttachmentAdapter.d.ts +1 -0
- package/dist/react/runtimes/cloud/CloudFileAttachmentAdapter.d.ts.map +1 -1
- package/dist/react/runtimes/cloud/CloudFileAttachmentAdapter.js +22 -2
- package/dist/react/runtimes/cloud/CloudFileAttachmentAdapter.js.map +1 -1
- package/dist/react/runtimes/cloud/auiV0.d.ts +40 -15
- package/dist/react/runtimes/cloud/auiV0.d.ts.map +1 -1
- package/dist/react/runtimes/cloud/auiV0.js +62 -15
- package/dist/react/runtimes/cloud/auiV0.js.map +1 -1
- package/dist/react/runtimes/cloud/createCloudThreadListAdapter.d.ts +2 -1
- package/dist/react/runtimes/cloud/createCloudThreadListAdapter.d.ts.map +1 -1
- package/dist/react/runtimes/cloud/createCloudThreadListAdapter.js +6 -1
- package/dist/react/runtimes/cloud/createCloudThreadListAdapter.js.map +1 -1
- package/dist/react/runtimes/cloud/sdkIdentity.d.ts +6 -0
- package/dist/react/runtimes/cloud/sdkIdentity.d.ts.map +1 -0
- package/dist/react/runtimes/cloud/sdkIdentity.js +9 -0
- package/dist/react/runtimes/cloud/sdkIdentity.js.map +1 -0
- package/dist/react/runtimes/external-message-converter.d.ts +12 -2
- package/dist/react/runtimes/external-message-converter.d.ts.map +1 -1
- package/dist/react/runtimes/external-message-converter.js +26 -61
- package/dist/react/runtimes/external-message-converter.js.map +1 -1
- package/dist/react/runtimes/useExternalStoreRuntime.js +75 -46
- package/dist/react/runtimes/useExternalStoreRuntime.js.map +1 -1
- package/dist/react/runtimes/useRemoteThreadListRuntime.d.ts.map +1 -1
- package/dist/react/runtimes/useRemoteThreadListRuntime.js +64 -24
- package/dist/react/runtimes/useRemoteThreadListRuntime.js.map +1 -1
- package/dist/react/utils/groupParts.d.ts +6 -1
- package/dist/react/utils/groupParts.d.ts.map +1 -1
- package/dist/react/utils/groupParts.js +6 -0
- package/dist/react/utils/groupParts.js.map +1 -1
- package/dist/react/utils/useJSONEqual.d.ts +3 -1
- package/dist/react/utils/useJSONEqual.d.ts.map +1 -1
- package/dist/react/utils/useJSONEqual.js +6 -1
- package/dist/react/utils/useJSONEqual.js.map +1 -1
- package/dist/react/utils/useJSONSchemaDependency.d.ts +7 -0
- package/dist/react/utils/useJSONSchemaDependency.d.ts.map +1 -0
- package/dist/react/utils/useJSONSchemaDependency.js +20 -0
- package/dist/react/utils/useJSONSchemaDependency.js.map +1 -0
- package/dist/runtime/api/thread-list-item-runtime.d.ts +7 -3
- package/dist/runtime/api/thread-list-item-runtime.d.ts.map +1 -1
- package/dist/runtime/api/thread-list-item-runtime.js +2 -2
- package/dist/runtime/api/thread-list-item-runtime.js.map +1 -1
- package/dist/runtime/api/thread-list-runtime.d.ts +3 -0
- package/dist/runtime/api/thread-list-runtime.d.ts.map +1 -1
- package/dist/runtime/api/thread-list-runtime.js +18 -14
- package/dist/runtime/api/thread-list-runtime.js.map +1 -1
- package/dist/runtime/api/thread-runtime.d.ts +4 -0
- package/dist/runtime/api/thread-runtime.d.ts.map +1 -1
- package/dist/runtime/api/thread-runtime.js +3 -6
- package/dist/runtime/api/thread-runtime.js.map +1 -1
- package/dist/runtime/base/base-composer-runtime-core.d.ts +1 -0
- package/dist/runtime/base/base-composer-runtime-core.d.ts.map +1 -1
- package/dist/runtime/base/base-composer-runtime-core.js +62 -22
- package/dist/runtime/base/base-composer-runtime-core.js.map +1 -1
- package/dist/runtime/base/base-thread-runtime-core.d.ts +2 -0
- package/dist/runtime/base/base-thread-runtime-core.d.ts.map +1 -1
- package/dist/runtime/base/base-thread-runtime-core.js +161 -69
- package/dist/runtime/base/base-thread-runtime-core.js.map +1 -1
- package/dist/runtime/interfaces/composer-runtime-core.d.ts +12 -5
- package/dist/runtime/interfaces/composer-runtime-core.d.ts.map +1 -1
- package/dist/runtime/interfaces/thread-list-runtime-core.d.ts +4 -1
- package/dist/runtime/interfaces/thread-list-runtime-core.d.ts.map +1 -1
- package/dist/runtime/interfaces/thread-runtime-core.d.ts +6 -0
- package/dist/runtime/interfaces/thread-runtime-core.d.ts.map +1 -1
- package/dist/runtime/queue/message-queue.d.ts +5 -0
- package/dist/runtime/queue/message-queue.d.ts.map +1 -1
- package/dist/runtime/queue/message-queue.js +61 -6
- package/dist/runtime/queue/message-queue.js.map +1 -1
- package/dist/runtime/utils/auto-status.d.ts +6 -2
- package/dist/runtime/utils/auto-status.d.ts.map +1 -1
- package/dist/runtime/utils/auto-status.js +12 -4
- package/dist/runtime/utils/auto-status.js.map +1 -1
- package/dist/runtime/utils/external-message-conversion.d.ts +16 -4
- package/dist/runtime/utils/external-message-conversion.d.ts.map +1 -1
- package/dist/runtime/utils/external-message-conversion.js +49 -13
- package/dist/runtime/utils/external-message-conversion.js.map +1 -1
- package/dist/runtime/utils/message-repository.d.ts +1 -0
- package/dist/runtime/utils/message-repository.d.ts.map +1 -1
- package/dist/runtime/utils/message-repository.js +18 -9
- package/dist/runtime/utils/message-repository.js.map +1 -1
- package/dist/runtime/utils/thread-message-like.d.ts +2 -1
- package/dist/runtime/utils/thread-message-like.d.ts.map +1 -1
- package/dist/runtime/utils/thread-message-like.js +5 -3
- package/dist/runtime/utils/thread-message-like.js.map +1 -1
- package/dist/runtimes/external-store/external-store-thread-list-runtime-core.d.ts.map +1 -1
- package/dist/runtimes/external-store/external-store-thread-list-runtime-core.js +21 -27
- package/dist/runtimes/external-store/external-store-thread-list-runtime-core.js.map +1 -1
- package/dist/runtimes/external-store/external-store-thread-runtime-core.d.ts.map +1 -1
- package/dist/runtimes/external-store/external-store-thread-runtime-core.js +8 -1
- package/dist/runtimes/external-store/external-store-thread-runtime-core.js.map +1 -1
- package/dist/runtimes/internal.d.ts +3 -3
- package/dist/runtimes/internal.js +2 -2
- package/dist/runtimes/local/local-thread-runtime-core.d.ts +1 -1
- package/dist/runtimes/local/local-thread-runtime-core.d.ts.map +1 -1
- package/dist/runtimes/local/local-thread-runtime-core.js +4 -1
- package/dist/runtimes/local/local-thread-runtime-core.js.map +1 -1
- package/dist/runtimes/remote-thread-list/remote-thread-state.d.ts +18 -1
- package/dist/runtimes/remote-thread-list/remote-thread-state.d.ts.map +1 -1
- package/dist/runtimes/remote-thread-list/remote-thread-state.js +130 -42
- package/dist/runtimes/remote-thread-list/remote-thread-state.js.map +1 -1
- package/dist/runtimes/remote-thread-list/title-generation.d.ts +49 -0
- package/dist/runtimes/remote-thread-list/title-generation.d.ts.map +1 -0
- package/dist/runtimes/remote-thread-list/title-generation.js +197 -0
- package/dist/runtimes/remote-thread-list/title-generation.js.map +1 -0
- package/dist/runtimes/remote-thread-list/title.d.ts +3 -1
- package/dist/runtimes/remote-thread-list/title.d.ts.map +1 -1
- package/dist/runtimes/remote-thread-list/title.js +9 -1
- package/dist/runtimes/remote-thread-list/title.js.map +1 -1
- package/dist/runtimes/remote-thread-list/types.d.ts +10 -0
- package/dist/runtimes/remote-thread-list/types.d.ts.map +1 -1
- package/dist/runtimes/tool-invocations/ToolInvocationTracker.d.ts.map +1 -1
- package/dist/runtimes/tool-invocations/ToolInvocationTracker.js +2 -1
- package/dist/runtimes/tool-invocations/ToolInvocationTracker.js.map +1 -1
- package/dist/store/clients/external-thread.d.ts.map +1 -1
- package/dist/store/clients/external-thread.js +260 -203
- package/dist/store/clients/external-thread.js.map +1 -1
- package/dist/store/clients/model-context-client.d.ts.map +1 -1
- package/dist/store/clients/model-context-client.js +2 -1
- package/dist/store/clients/model-context-client.js.map +1 -1
- package/dist/store/clients/single-thread-list.d.ts.map +1 -1
- package/dist/store/clients/single-thread-list.js +1 -0
- package/dist/store/clients/single-thread-list.js.map +1 -1
- package/dist/store/clients/suggestions.d.ts.map +1 -1
- package/dist/store/clients/suggestions.js +5 -4
- package/dist/store/clients/suggestions.js.map +1 -1
- package/dist/store/clients/thread-tasks.d.ts +13 -0
- package/dist/store/clients/thread-tasks.d.ts.map +1 -0
- package/dist/store/clients/thread-tasks.js +69 -0
- package/dist/store/clients/thread-tasks.js.map +1 -0
- package/dist/store/index.d.ts +3 -2
- package/dist/store/index.js +3 -3
- package/dist/store/primitive-predicates.d.ts.map +1 -1
- package/dist/store/primitive-predicates.js +4 -4
- package/dist/store/primitive-predicates.js.map +1 -1
- package/dist/store/runtime-clients/composer-runtime-client.d.ts +1 -0
- package/dist/store/runtime-clients/composer-runtime-client.d.ts.map +1 -1
- package/dist/store/runtime-clients/composer-runtime-client.js +97 -61
- package/dist/store/runtime-clients/composer-runtime-client.js.map +1 -1
- package/dist/store/runtime-clients/message-runtime-client.d.ts +1 -0
- package/dist/store/runtime-clients/message-runtime-client.d.ts.map +1 -1
- package/dist/store/runtime-clients/message-runtime-client.js +221 -144
- package/dist/store/runtime-clients/message-runtime-client.js.map +1 -1
- package/dist/store/runtime-clients/thread-list-item-runtime-client.d.ts.map +1 -1
- package/dist/store/runtime-clients/thread-list-item-runtime-client.js +1 -1
- package/dist/store/runtime-clients/thread-list-item-runtime-client.js.map +1 -1
- package/dist/store/runtime-clients/thread-list-runtime-client.d.ts.map +1 -1
- package/dist/store/runtime-clients/thread-list-runtime-client.js +54 -52
- package/dist/store/runtime-clients/thread-list-runtime-client.js.map +1 -1
- package/dist/store/runtime-clients/thread-runtime-client.d.ts.map +1 -1
- package/dist/store/runtime-clients/thread-runtime-client.js +246 -126
- package/dist/store/runtime-clients/thread-runtime-client.js.map +1 -1
- package/dist/store/scope-registration.d.ts +2 -0
- package/dist/store/scope-registration.d.ts.map +1 -1
- package/dist/store/scopes/composer.d.ts +10 -2
- package/dist/store/scopes/composer.d.ts.map +1 -1
- package/dist/store/scopes/message.d.ts +30 -1
- package/dist/store/scopes/message.d.ts.map +1 -1
- package/dist/store/scopes/task.d.ts +36 -0
- package/dist/store/scopes/task.d.ts.map +1 -0
- package/dist/store/scopes/task.js +0 -0
- package/dist/store/scopes/thread-list-item.d.ts +2 -2
- package/dist/store/scopes/thread-list-item.d.ts.map +1 -1
- package/dist/store/scopes/thread.d.ts +28 -0
- package/dist/store/scopes/thread.d.ts.map +1 -1
- package/dist/store/scopes/threads.d.ts +1 -0
- package/dist/store/scopes/threads.d.ts.map +1 -1
- package/dist/subscribable/subscribable.d.ts +2 -1
- package/dist/subscribable/subscribable.d.ts.map +1 -1
- package/dist/subscribable/subscribable.js +23 -15
- package/dist/subscribable/subscribable.js.map +1 -1
- package/dist/types/attachment.d.ts +2 -1
- package/dist/types/attachment.d.ts.map +1 -1
- package/dist/types/attachment.js +2 -1
- package/dist/types/attachment.js.map +1 -1
- package/dist/types/index.d.ts +2 -2
- package/dist/types/message.d.ts +8 -1
- package/dist/types/message.d.ts.map +1 -1
- package/dist/types/message.js.map +1 -1
- package/dist/utils/abortable-iterable.d.ts +19 -0
- package/dist/utils/abortable-iterable.d.ts.map +1 -0
- package/dist/utils/abortable-iterable.js +88 -0
- package/dist/utils/abortable-iterable.js.map +1 -0
- package/dist/utils/composite-context-provider.d.ts.map +1 -1
- package/dist/utils/composite-context-provider.js +20 -2
- package/dist/utils/composite-context-provider.js.map +1 -1
- package/dist/utils/getGroupStatus.d.ts +18 -2
- package/dist/utils/getGroupStatus.d.ts.map +1 -1
- package/dist/utils/getGroupStatus.js +32 -7
- package/dist/utils/getGroupStatus.js.map +1 -1
- package/dist/utils/record.d.ts +11 -0
- package/dist/utils/record.d.ts.map +1 -0
- package/dist/utils/record.js +12 -0
- package/dist/utils/record.js.map +1 -0
- package/dist/utils/wire-media.d.ts.map +1 -1
- package/dist/utils/wire-media.js +2 -2
- package/dist/utils/wire-media.js.map +1 -1
- package/package.json +11 -11
- package/src/adapters/attachment.test.ts +50 -1
- package/src/adapters/attachment.ts +7 -4
- package/src/adapters/speech.test.ts +236 -0
- package/src/adapters/speech.ts +17 -10
- package/src/adapters/thread-history.ts +3 -0
- package/src/index.ts +2 -0
- package/src/internal.ts +4 -0
- package/src/model-context/frame/host.test.ts +137 -1
- package/src/model-context/frame/host.ts +49 -16
- package/src/model-context/frame/provider.test.ts +71 -0
- package/src/model-context/frame/provider.ts +37 -7
- package/src/model-context/interactable-composer-metadata.test.ts +58 -0
- package/src/model-context/interactable-composer-metadata.ts +19 -13
- package/src/model-context/registry.test.ts +12 -0
- package/src/model-context/registry.ts +3 -2
- package/src/model-context/types.test.ts +25 -0
- package/src/model-context/types.ts +9 -4
- package/src/react/RuntimeAdapter.test.ts +34 -0
- package/src/react/adapters/LocalStorageThreadListAdapter.test.ts +244 -0
- package/src/react/adapters/LocalStorageThreadListAdapter.tsx +104 -7
- package/src/react/client/DataRenderers.test.tsx +45 -0
- package/src/react/client/DataRenderers.ts +13 -9
- package/src/react/client/InMemoryThreadList.ts +1 -0
- package/src/react/client/Interactables.test.ts +72 -1
- package/src/react/client/Interactables.ts +22 -14
- package/src/react/client/RemoteThreadList.background.test.ts +148 -6
- package/src/react/client/RemoteThreadList.concurrent.test.tsx +42 -1
- package/src/react/client/RemoteThreadList.test.ts +386 -4
- package/src/react/client/RemoteThreadList.ts +181 -112
- package/src/react/client/Tools.ts +22 -11
- package/src/react/client/interactable-model-context.test.ts +44 -0
- package/src/react/client/interactable-model-context.ts +3 -2
- package/src/react/index.ts +5 -1
- package/src/react/interactables-legacy/Interactables.ts +16 -16
- package/src/react/interactables-legacy/useAssistantInteractable.test.tsx +132 -0
- package/src/react/interactables-legacy/useAssistantInteractable.ts +10 -1
- package/src/react/interactables-shared/useInteractablePersistenceQueue.ts +9 -10
- package/src/react/model-context/makeAssistantTool.ts +2 -2
- package/src/react/model-context/useAssistantTool.ts +2 -2
- package/src/react/model-context/useInteractable.test.tsx +177 -0
- package/src/react/model-context/useInteractable.ts +3 -0
- package/src/react/model-context/useToolArgsStatus.test.tsx +30 -0
- package/src/react/model-context/useToolArgsStatus.ts +2 -1
- package/src/react/primitive-hooks/useActionBarCopy.test.ts +0 -1
- package/src/react/primitive-hooks/useSuggestionTrigger.test.ts +0 -1
- package/src/react/primitives/message/MessageGroupedParts.test.tsx +96 -0
- package/src/react/primitives/message/MessageGroupedParts.tsx +15 -4
- package/src/react/primitives/part/PartMessages.test.tsx +104 -1
- package/src/react/primitives/part/PartMessages.tsx +1 -0
- package/src/react/primitives/thread/ThreadMessages.test.tsx +142 -0
- package/src/react/primitives/thread/ThreadMessages.tsx +8 -5
- package/src/react/providers/ReadonlyThreadProvider.test.tsx +56 -0
- package/src/react/runtimes/RemoteThreadListHookInstanceManager.destroy.test.tsx +172 -0
- package/src/react/runtimes/RemoteThreadListHookInstanceManager.running.test.tsx +33 -0
- package/src/react/runtimes/RemoteThreadListHookInstanceManager.test.tsx +7 -1
- package/src/react/runtimes/RemoteThreadListHookInstanceManager.tsx +28 -5
- package/src/react/runtimes/RemoteThreadListThreadListRuntimeCore.load-error.test.ts +132 -0
- package/src/react/runtimes/RemoteThreadListThreadListRuntimeCore.switch-delete.test.ts +105 -0
- package/src/react/runtimes/RemoteThreadListThreadListRuntimeCore.tsx +143 -112
- package/src/react/runtimes/RemoteThreadResource.test.ts +9 -0
- package/src/react/runtimes/RemoteThreadResource.ts +19 -12
- package/src/react/runtimes/cloud/AssistantCloudThreadHistoryAdapter.test.ts +20 -14
- package/src/react/runtimes/cloud/AssistantCloudThreadHistoryAdapter.test.tsx +703 -6
- package/src/react/runtimes/cloud/AssistantCloudThreadHistoryAdapter.ts +492 -402
- package/src/react/runtimes/cloud/CloudFileAttachmentAdapter.test.ts +77 -0
- package/src/react/runtimes/cloud/CloudFileAttachmentAdapter.ts +27 -1
- package/src/react/runtimes/cloud/auiV0.ts +160 -25
- package/src/react/runtimes/cloud/createCloudThreadListAdapter.test.ts +36 -0
- package/src/react/runtimes/cloud/createCloudThreadListAdapter.ts +8 -1
- package/src/react/runtimes/cloud/sdkIdentity.ts +9 -0
- package/src/react/runtimes/cloud/useCloudThreadListAdapter.test.tsx +18 -4
- package/src/react/runtimes/external-message-converter.test.ts +136 -1
- package/src/react/runtimes/external-message-converter.ts +39 -93
- package/src/react/runtimes/useExternalStoreRuntime.lifecycle.test.tsx +41 -0
- package/src/react/runtimes/useExternalStoreRuntime.ts +10 -4
- package/src/react/runtimes/useLocalRuntime.test.tsx +20 -0
- package/src/react/runtimes/useRemoteThreadListRuntime.load-error.test.tsx +108 -0
- package/src/react/runtimes/useRemoteThreadListRuntime.ts +34 -1
- package/src/react/utils/groupParts.ts +12 -1
- package/src/react/utils/useJSONEqual.ts +9 -0
- package/src/react/utils/useJSONSchemaDependency.ts +22 -0
- package/src/runtime/api/message-runtime.test.ts +75 -0
- package/src/runtime/api/thread-list-item-runtime.ts +10 -3
- package/src/runtime/api/thread-list-runtime.ts +21 -11
- package/src/runtime/api/thread-runtime.test.ts +136 -0
- package/src/runtime/api/thread-runtime.ts +10 -5
- package/src/runtime/base/base-composer-runtime-core.ts +105 -24
- package/src/runtime/base/base-thread-runtime-core.test.ts +1063 -2
- package/src/runtime/base/base-thread-runtime-core.ts +228 -87
- package/src/runtime/interfaces/composer-runtime-core.ts +10 -5
- package/src/runtime/interfaces/thread-list-runtime-core.ts +5 -1
- package/src/runtime/interfaces/thread-runtime-core.ts +6 -0
- package/src/runtime/queue/message-queue.ts +68 -6
- package/src/runtime/utils/auto-status.test.ts +112 -1
- package/src/runtime/utils/auto-status.ts +31 -5
- package/src/runtime/utils/external-message-conversion.test.ts +202 -0
- package/src/runtime/utils/external-message-conversion.ts +123 -32
- package/src/runtime/utils/message-repository.test.ts +49 -0
- package/src/runtime/utils/message-repository.ts +32 -20
- package/src/runtime/utils/thread-message-like.test.ts +52 -0
- package/src/runtime/utils/thread-message-like.ts +5 -1
- package/src/runtimes/external-store/external-store-thread-list-runtime-core.ts +18 -13
- package/src/runtimes/external-store/external-store-thread-runtime-core.ts +31 -1
- package/src/runtimes/internal.ts +1 -0
- package/src/runtimes/local/local-thread-runtime-core.test.ts +21 -0
- package/src/runtimes/local/local-thread-runtime-core.ts +11 -1
- package/src/runtimes/remote-thread-list/remote-thread-state.test.ts +128 -2
- package/src/runtimes/remote-thread-list/remote-thread-state.ts +182 -42
- package/src/runtimes/remote-thread-list/title-generation.test.ts +602 -0
- package/src/runtimes/remote-thread-list/title-generation.ts +329 -0
- package/src/runtimes/remote-thread-list/title.test.ts +62 -0
- package/src/runtimes/remote-thread-list/title.ts +13 -0
- package/src/runtimes/remote-thread-list/types.ts +10 -0
- package/src/runtimes/tool-invocations/EDGE_CASES.md +2 -6
- package/src/runtimes/tool-invocations/ToolInvocationTracker.test.ts +133 -0
- package/src/runtimes/tool-invocations/ToolInvocationTracker.ts +10 -6
- package/src/store/clients/external-thread.ts +67 -4
- package/src/store/clients/model-context-client.ts +5 -1
- package/src/store/clients/single-thread-list.ts +1 -0
- package/src/store/clients/suggestions.test.ts +40 -0
- package/src/store/clients/suggestions.ts +13 -10
- package/src/store/clients/thread-tasks.test.ts +274 -0
- package/src/store/clients/thread-tasks.ts +138 -0
- package/src/store/index.ts +8 -0
- package/src/store/primitive-predicates.test.ts +48 -5
- package/src/store/primitive-predicates.ts +7 -2
- package/src/store/runtime-clients/composer-runtime-client.ts +42 -9
- package/src/store/runtime-clients/message-runtime-client.ts +54 -6
- package/src/store/runtime-clients/thread-list-item-runtime-client.ts +4 -2
- package/src/store/runtime-clients/thread-list-runtime-client.ts +1 -0
- package/src/store/runtime-clients/thread-runtime-client.ts +89 -11
- package/src/store/scope-registration.ts +2 -0
- package/src/store/scopes/composer.ts +16 -4
- package/src/store/scopes/message.ts +14 -0
- package/src/store/scopes/task.ts +34 -0
- package/src/store/scopes/thread-list-item.ts +5 -2
- package/src/store/scopes/thread.ts +20 -0
- package/src/store/scopes/threads.ts +1 -0
- package/src/store/thread-tasks.test.tsx +209 -0
- package/src/subscribable/subscribable.test.ts +156 -1
- package/src/subscribable/subscribable.ts +25 -15
- package/src/tests/MessageRepository.test.ts +117 -5
- package/src/tests/OptimisticState-list-race.test.ts +1 -0
- package/src/tests/RemoteThreadListThreadListRuntimeCore-initialize-adapter-change.test.ts +38 -0
- package/src/tests/RemoteThreadListThreadListRuntimeCore-load-race.test.ts +47 -0
- package/src/tests/RemoteThreadListThreadListRuntimeCore-title-race.test.ts +89 -0
- package/src/tests/attachment-adapters.test.ts +14 -0
- package/src/tests/auiV0Encode.test.ts +300 -0
- package/src/tests/base-composer-runtime-core-send.test.ts +51 -0
- package/src/tests/base-composer-runtime-core.test.ts +353 -2
- package/src/tests/external-store-thread-list-runtime-core.test.ts +83 -0
- package/src/tests/external-store-thread-runtime-core-adapter.test.ts +178 -18
- package/src/tests/external-thread-attachments.test.tsx +208 -0
- package/src/tests/external-thread-parity.test.tsx +57 -0
- package/src/tests/groupParts.test.ts +71 -0
- package/src/tests/message-queue.test.ts +253 -0
- package/src/tests/remote-thread-list-isLoading.test.ts +1 -0
- package/src/tests/remote-thread-list-reactive-threadId.test.ts +51 -0
- package/src/tests/thread-list-runtime-getLoadThreadsPromise.test.ts +1 -0
- package/src/tests/thread-switch-events.test.tsx +78 -0
- package/src/tests/tools-scope-migration.test.tsx +28 -0
- package/src/tests/useRemoteThreadListRuntime-controlled.test.tsx +43 -0
- package/src/types/attachment.ts +4 -0
- package/src/types/index.ts +1 -0
- package/src/types/message.ts +8 -0
- package/src/utils/abortable-iterable.test.ts +328 -0
- package/src/utils/abortable-iterable.ts +104 -0
- package/src/utils/composite-context-provider.test.ts +25 -0
- package/src/utils/composite-context-provider.ts +23 -2
- package/src/utils/getGroupStatus.test.ts +70 -4
- package/src/utils/getGroupStatus.ts +35 -12
- package/src/utils/record.test.ts +48 -0
- package/src/utils/record.ts +11 -0
- package/src/utils/wire-media.test.ts +10 -0
- package/src/utils/wire-media.ts +6 -2
|
@@ -25,6 +25,8 @@ import {
|
|
|
25
25
|
createThreadMappingId,
|
|
26
26
|
getThreadData,
|
|
27
27
|
normalizeCursor,
|
|
28
|
+
reconcileInitializedThread,
|
|
29
|
+
promoteNewThreadReducer,
|
|
28
30
|
updateStatusReducer,
|
|
29
31
|
type RemoteThreadData,
|
|
30
32
|
type RemoteThreadState,
|
|
@@ -38,14 +40,24 @@ import type {
|
|
|
38
40
|
} from "../../runtimes/remote-thread-list/types";
|
|
39
41
|
import { ThreadListAdapterChangedError } from "../../runtimes/remote-thread-list/adapter-changed";
|
|
40
42
|
import type { ThreadMessage } from "../../types/message";
|
|
41
|
-
import { AssistantMessageStream } from "assistant-stream";
|
|
42
43
|
import { handleThreadListAction } from "../../store/runtime-clients/handle-thread-list-action";
|
|
43
44
|
import {
|
|
44
45
|
inMemoryThreadListTransformScopes,
|
|
45
46
|
type InMemoryThreadListProps,
|
|
46
47
|
} from "./InMemoryThreadList";
|
|
47
48
|
import { AdaptedRemoteThread } from "./AdaptedRemoteThread";
|
|
48
|
-
import {
|
|
49
|
+
import {
|
|
50
|
+
applyTitleStream,
|
|
51
|
+
isTitleSourceMessage,
|
|
52
|
+
} from "../../runtimes/remote-thread-list/title";
|
|
53
|
+
import {
|
|
54
|
+
clearThreadTitleState,
|
|
55
|
+
finishThreadTitleRename,
|
|
56
|
+
runThreadTitleGeneration,
|
|
57
|
+
startThreadTitleRename,
|
|
58
|
+
type ThreadTitleState,
|
|
59
|
+
} from "../../runtimes/remote-thread-list/title-generation";
|
|
60
|
+
import { invokeUserCallback } from "../../utils/invoke-user-callback";
|
|
49
61
|
|
|
50
62
|
const RESOLVED_PROMISE = Promise.resolve();
|
|
51
63
|
|
|
@@ -67,6 +79,7 @@ export type RemoteThreadListProps = {
|
|
|
67
79
|
onThreadIdChange?: ((threadId: string | undefined) => void) | undefined;
|
|
68
80
|
onSwitchToThread?: ((threadId: string) => void) | undefined;
|
|
69
81
|
onSwitchToNewThread?: (() => void) | undefined;
|
|
82
|
+
/** Called after the backing adapter successfully deletes the thread. */
|
|
70
83
|
onDelete?: ((threadId: string) => void) | undefined;
|
|
71
84
|
/**
|
|
72
85
|
* Keeps every thread the session switched to mounted, so a run continues
|
|
@@ -101,16 +114,6 @@ const toInitializeResult = (
|
|
|
101
114
|
externalId: result.externalId,
|
|
102
115
|
});
|
|
103
116
|
|
|
104
|
-
const applyTitleStream = async (
|
|
105
|
-
stream: Parameters<typeof AssistantMessageStream.fromAssistantStream>[0],
|
|
106
|
-
onTitle: (title: string | undefined) => Promise<void>,
|
|
107
|
-
) => {
|
|
108
|
-
const messageStream = AssistantMessageStream.fromAssistantStream(stream);
|
|
109
|
-
for await (const result of messageStream) {
|
|
110
|
-
await onTitle(result.parts.filter((part) => part.type === "text")[0]?.text);
|
|
111
|
-
}
|
|
112
|
-
};
|
|
113
|
-
|
|
114
117
|
const useThreadListItemClient = (props: {
|
|
115
118
|
data: RemoteThreadData;
|
|
116
119
|
isRunning: boolean;
|
|
@@ -120,7 +123,7 @@ const useThreadListItemClient = (props: {
|
|
|
120
123
|
onArchive: () => void;
|
|
121
124
|
onUnarchive: () => void;
|
|
122
125
|
onDelete: () => void;
|
|
123
|
-
onGenerateTitle: () => void;
|
|
126
|
+
onGenerateTitle: (options?: { automatic?: boolean }) => void;
|
|
124
127
|
onInitialize: () => Promise<{
|
|
125
128
|
remoteId: string;
|
|
126
129
|
externalId: string | undefined;
|
|
@@ -271,7 +274,7 @@ const useRemoteThreadBody = ({
|
|
|
271
274
|
useEffect(() => {
|
|
272
275
|
if (!hasTitleSource || titleFiredRef.current) return;
|
|
273
276
|
titleFiredRef.current = true;
|
|
274
|
-
client.threadListItem.generateTitle();
|
|
277
|
+
client.threadListItem.generateTitle({ automatic: true });
|
|
275
278
|
}, [hasTitleSource]);
|
|
276
279
|
return body.methods;
|
|
277
280
|
});
|
|
@@ -343,6 +346,7 @@ const useRemoteThreadListView = ({
|
|
|
343
346
|
onGenerateTitle: (
|
|
344
347
|
threadId: string,
|
|
345
348
|
messages: readonly ThreadMessage[] | undefined,
|
|
349
|
+
options?: { automatic?: boolean },
|
|
346
350
|
) => Promise<void>;
|
|
347
351
|
onInitialize: (threadId: string) => Promise<{
|
|
348
352
|
remoteId: string;
|
|
@@ -385,7 +389,7 @@ const useRemoteThreadListView = ({
|
|
|
385
389
|
onUnarchive: () =>
|
|
386
390
|
handleThreadListAction("unarchive", () => onUnarchive(data.id)),
|
|
387
391
|
onDelete: () => handleThreadListAction("delete", () => onDelete(data.id)),
|
|
388
|
-
onGenerateTitle: () =>
|
|
392
|
+
onGenerateTitle: (options) =>
|
|
389
393
|
handleThreadListAction("generate title", () =>
|
|
390
394
|
onGenerateTitle(
|
|
391
395
|
data.id,
|
|
@@ -394,6 +398,7 @@ const useRemoteThreadListView = ({
|
|
|
394
398
|
: mainThreadClient.state.messages) as
|
|
395
399
|
| readonly ThreadMessage[]
|
|
396
400
|
| undefined,
|
|
401
|
+
options,
|
|
397
402
|
),
|
|
398
403
|
),
|
|
399
404
|
onInitialize: () => onInitialize(data.id),
|
|
@@ -489,6 +494,7 @@ const useRemoteThreadList = (
|
|
|
489
494
|
adapter,
|
|
490
495
|
adapterAtLoad: adapter,
|
|
491
496
|
adapterGeneration: 0,
|
|
497
|
+
titleStates: new Map<string, ThreadTitleState>(),
|
|
492
498
|
loadGeneration: 0,
|
|
493
499
|
switchGeneration: 0,
|
|
494
500
|
loadPromise: undefined as Promise<void> | undefined,
|
|
@@ -545,7 +551,14 @@ const useRemoteThreadList = (
|
|
|
545
551
|
(remoteId: string | undefined, emit: boolean) => {
|
|
546
552
|
if (session.lastNotifiedRemoteId === remoteId) return;
|
|
547
553
|
session.lastNotifiedRemoteId = remoteId;
|
|
548
|
-
if (emit)
|
|
554
|
+
if (emit) {
|
|
555
|
+
invokeUserCallback(
|
|
556
|
+
"assistant-ui",
|
|
557
|
+
"onThreadIdChange",
|
|
558
|
+
session.onThreadIdChange,
|
|
559
|
+
remoteId,
|
|
560
|
+
);
|
|
561
|
+
}
|
|
549
562
|
},
|
|
550
563
|
[session],
|
|
551
564
|
);
|
|
@@ -560,7 +573,7 @@ const useRemoteThreadList = (
|
|
|
560
573
|
execute: () => adapter.list(),
|
|
561
574
|
loading: (state) => {
|
|
562
575
|
if (generation !== session.loadGeneration) return state;
|
|
563
|
-
return { ...state, isLoading: true };
|
|
576
|
+
return { ...state, isLoading: true, loadError: undefined };
|
|
564
577
|
},
|
|
565
578
|
then: (state, page) => {
|
|
566
579
|
if (generation !== session.loadGeneration) return state;
|
|
@@ -574,6 +587,7 @@ const useRemoteThreadList = (
|
|
|
574
587
|
const merged = {
|
|
575
588
|
...state,
|
|
576
589
|
isLoading: false,
|
|
590
|
+
loadError: undefined,
|
|
577
591
|
cursor: normalizeCursor(page.nextCursor),
|
|
578
592
|
threadIds: fresh.threadIds,
|
|
579
593
|
archivedThreadIds: fresh.archivedThreadIds,
|
|
@@ -590,6 +604,7 @@ const useRemoteThreadList = (
|
|
|
590
604
|
store.update({
|
|
591
605
|
...store.baseValue,
|
|
592
606
|
isLoading: false,
|
|
607
|
+
loadError: error,
|
|
593
608
|
});
|
|
594
609
|
})
|
|
595
610
|
.then(() => {});
|
|
@@ -603,6 +618,7 @@ const useRemoteThreadList = (
|
|
|
603
618
|
session.loadMorePromise = undefined;
|
|
604
619
|
if (adapterChanged) {
|
|
605
620
|
session.adapterGeneration++;
|
|
621
|
+
session.titleStates.clear();
|
|
606
622
|
session.switchGeneration++;
|
|
607
623
|
session.switchTask = undefined;
|
|
608
624
|
session.adapterAtLoad = adapter;
|
|
@@ -627,6 +643,26 @@ const useRemoteThreadList = (
|
|
|
627
643
|
store,
|
|
628
644
|
]);
|
|
629
645
|
|
|
646
|
+
useEffect(() => {
|
|
647
|
+
if (typeof window === "undefined" || typeof document === "undefined") {
|
|
648
|
+
return;
|
|
649
|
+
}
|
|
650
|
+
|
|
651
|
+
const retryAfterError = () => {
|
|
652
|
+
if (store.value.loadError !== undefined) void getLoadThreadsPromise();
|
|
653
|
+
};
|
|
654
|
+
const retryAfterVisible = () => {
|
|
655
|
+
if (document.visibilityState === "visible") retryAfterError();
|
|
656
|
+
};
|
|
657
|
+
|
|
658
|
+
window.addEventListener("online", retryAfterError);
|
|
659
|
+
document.addEventListener("visibilitychange", retryAfterVisible);
|
|
660
|
+
return () => {
|
|
661
|
+
window.removeEventListener("online", retryAfterError);
|
|
662
|
+
document.removeEventListener("visibilitychange", retryAfterVisible);
|
|
663
|
+
};
|
|
664
|
+
}, [getLoadThreadsPromise, store]);
|
|
665
|
+
|
|
630
666
|
useEffect(() => {
|
|
631
667
|
void getLoadThreadsPromise();
|
|
632
668
|
}, [getLoadThreadsPromise]);
|
|
@@ -881,70 +917,60 @@ const useRemoteThreadList = (
|
|
|
881
917
|
requireAdapterGeneration(adapterGeneration);
|
|
882
918
|
return result;
|
|
883
919
|
}
|
|
920
|
+
requireAdapterGeneration(adapterGeneration);
|
|
921
|
+
const initializeTask = currentAdapter.initialize(threadId);
|
|
922
|
+
let removedMappingId: string | undefined;
|
|
923
|
+
let replacementMainThreadId: string | undefined;
|
|
884
924
|
const result = await store.optimisticUpdate({
|
|
885
|
-
execute: () =>
|
|
886
|
-
|
|
887
|
-
|
|
888
|
-
},
|
|
889
|
-
optimistic: (state) => updateStatusReducer(state, threadId, "regular"),
|
|
890
|
-
loading: (state, task) => {
|
|
891
|
-
const mappingId = createThreadMappingId(threadId);
|
|
892
|
-
return {
|
|
893
|
-
...state,
|
|
894
|
-
threadData: {
|
|
895
|
-
...state.threadData,
|
|
896
|
-
[mappingId]: {
|
|
897
|
-
...state.threadData[mappingId],
|
|
898
|
-
initializeTask: task,
|
|
899
|
-
},
|
|
900
|
-
},
|
|
901
|
-
};
|
|
902
|
-
},
|
|
925
|
+
execute: () => initializeTask,
|
|
926
|
+
optimistic: (state) =>
|
|
927
|
+
promoteNewThreadReducer(state, threadId, initializeTask),
|
|
903
928
|
then: (state, { remoteId, externalId }) => {
|
|
904
929
|
if (adapterGeneration !== session.adapterGeneration) return state;
|
|
905
|
-
|
|
906
|
-
|
|
907
|
-
const
|
|
908
|
-
|
|
909
|
-
|
|
910
|
-
|
|
911
|
-
|
|
912
|
-
|
|
913
|
-
listedMappingId !== undefined && listedMappingId !== mappingId
|
|
914
|
-
? state.threadData[listedMappingId]
|
|
915
|
-
: undefined;
|
|
916
|
-
|
|
917
|
-
const threadData = { ...state.threadData };
|
|
918
|
-
if (orphan !== undefined) delete threadData[listedMappingId!];
|
|
919
|
-
threadData[mappingId] = {
|
|
920
|
-
...data,
|
|
921
|
-
initializeTask: Promise.resolve({ remoteId, externalId }),
|
|
930
|
+
// Background mode still owns the initializing body. Single-body mode
|
|
931
|
+
// has already replaced it, so retain the currently mounted body.
|
|
932
|
+
const retainedThreadId = backgroundThreads
|
|
933
|
+
? threadId
|
|
934
|
+
: session.mainThreadId;
|
|
935
|
+
const reconciliation = reconcileInitializedThread(
|
|
936
|
+
state,
|
|
937
|
+
threadId,
|
|
922
938
|
remoteId,
|
|
923
939
|
externalId,
|
|
924
|
-
|
|
925
|
-
|
|
926
|
-
|
|
927
|
-
|
|
928
|
-
|
|
929
|
-
|
|
930
|
-
|
|
931
|
-
threadIds: rewire(state.threadIds),
|
|
932
|
-
archivedThreadIds: rewire(state.archivedThreadIds),
|
|
933
|
-
threadIdMap: {
|
|
934
|
-
...state.threadIdMap,
|
|
935
|
-
[remoteId]: mappingId,
|
|
936
|
-
},
|
|
937
|
-
threadData,
|
|
938
|
-
};
|
|
940
|
+
retainedThreadId,
|
|
941
|
+
);
|
|
942
|
+
removedMappingId = reconciliation.removedMappingId;
|
|
943
|
+
if (removedMappingId === session.mainThreadId) {
|
|
944
|
+
replacementMainThreadId = reconciliation.survivorMappingId;
|
|
945
|
+
}
|
|
946
|
+
return reconciliation.state;
|
|
939
947
|
},
|
|
940
948
|
});
|
|
941
949
|
requireAdapterGeneration(adapterGeneration);
|
|
950
|
+
if (removedMappingId !== undefined) {
|
|
951
|
+
setStartedIds((prev) =>
|
|
952
|
+
prev.filter((startedId) => startedId !== removedMappingId),
|
|
953
|
+
);
|
|
954
|
+
}
|
|
955
|
+
if (
|
|
956
|
+
replacementMainThreadId !== undefined &&
|
|
957
|
+
session.mainThreadId === removedMappingId
|
|
958
|
+
) {
|
|
959
|
+
assignMainThreadId(replacementMainThreadId);
|
|
960
|
+
}
|
|
942
961
|
if (threadId === session.mainThreadId) {
|
|
943
962
|
notifyRemoteId(result.remoteId, true);
|
|
944
963
|
}
|
|
945
964
|
return toInitializeResult(result);
|
|
946
965
|
},
|
|
947
|
-
[
|
|
966
|
+
[
|
|
967
|
+
assignMainThreadId,
|
|
968
|
+
backgroundThreads,
|
|
969
|
+
notifyRemoteId,
|
|
970
|
+
requireAdapterGeneration,
|
|
971
|
+
session,
|
|
972
|
+
store,
|
|
973
|
+
],
|
|
948
974
|
);
|
|
949
975
|
|
|
950
976
|
const rename = useCallback(
|
|
@@ -956,27 +982,43 @@ const useRemoteThreadList = (
|
|
|
956
982
|
if (data.status === "new") {
|
|
957
983
|
throw threadStatusError(threadIdOrRemoteId, data.status, "be renamed");
|
|
958
984
|
}
|
|
959
|
-
|
|
960
|
-
|
|
961
|
-
|
|
962
|
-
|
|
963
|
-
|
|
964
|
-
|
|
965
|
-
|
|
966
|
-
|
|
967
|
-
|
|
968
|
-
|
|
969
|
-
|
|
970
|
-
|
|
971
|
-
|
|
972
|
-
|
|
973
|
-
|
|
974
|
-
|
|
985
|
+
const claim = startThreadTitleRename(
|
|
986
|
+
session.titleStates,
|
|
987
|
+
data.id,
|
|
988
|
+
newTitle,
|
|
989
|
+
);
|
|
990
|
+
return store
|
|
991
|
+
.optimisticUpdate({
|
|
992
|
+
execute: async () => {
|
|
993
|
+
const { remoteId } = await data.initializeTask;
|
|
994
|
+
requireAdapterGeneration(adapterGeneration);
|
|
995
|
+
return currentAdapter.rename(remoteId, newTitle);
|
|
996
|
+
},
|
|
997
|
+
optimistic: (state) => {
|
|
998
|
+
const current = getThreadData(state, threadIdOrRemoteId);
|
|
999
|
+
if (!current) return state;
|
|
1000
|
+
return {
|
|
1001
|
+
...state,
|
|
1002
|
+
threadData: {
|
|
1003
|
+
...state.threadData,
|
|
1004
|
+
[current.id]: {
|
|
1005
|
+
...current,
|
|
1006
|
+
title: newTitle,
|
|
1007
|
+
},
|
|
975
1008
|
},
|
|
976
|
-
}
|
|
977
|
-
}
|
|
978
|
-
}
|
|
979
|
-
|
|
1009
|
+
};
|
|
1010
|
+
},
|
|
1011
|
+
})
|
|
1012
|
+
.then(
|
|
1013
|
+
(result) => {
|
|
1014
|
+
finishThreadTitleRename(session.titleStates, data.id, claim, true);
|
|
1015
|
+
return result;
|
|
1016
|
+
},
|
|
1017
|
+
(error: unknown) => {
|
|
1018
|
+
finishThreadTitleRename(session.titleStates, data.id, claim, false);
|
|
1019
|
+
throw error;
|
|
1020
|
+
},
|
|
1021
|
+
);
|
|
980
1022
|
},
|
|
981
1023
|
[requireAdapterGeneration, session, store],
|
|
982
1024
|
);
|
|
@@ -1104,8 +1146,7 @@ const useRemoteThreadList = (
|
|
|
1104
1146
|
}
|
|
1105
1147
|
await ensureNotMain(data.id);
|
|
1106
1148
|
requireAdapterGeneration(adapterGeneration);
|
|
1107
|
-
|
|
1108
|
-
return store.optimisticUpdate({
|
|
1149
|
+
const result = await store.optimisticUpdate({
|
|
1109
1150
|
execute: async () => {
|
|
1110
1151
|
const { remoteId } = await data.initializeTask;
|
|
1111
1152
|
requireAdapterGeneration(adapterGeneration);
|
|
@@ -1113,6 +1154,13 @@ const useRemoteThreadList = (
|
|
|
1113
1154
|
},
|
|
1114
1155
|
optimistic: (state) => updateStatusReducer(state, data.id, "deleted"),
|
|
1115
1156
|
});
|
|
1157
|
+
// An adapter swap resets the optimistic layer, and a listed thread's slot
|
|
1158
|
+
// id is its remote id, so a replacement adapter can re-list this slot
|
|
1159
|
+
// while the deletion is in flight.
|
|
1160
|
+
if (getThreadData(store.value, data.id) !== undefined) return result;
|
|
1161
|
+
clearThreadTitleState(session.titleStates, data.id);
|
|
1162
|
+
onDelete?.(data.id);
|
|
1163
|
+
return result;
|
|
1116
1164
|
},
|
|
1117
1165
|
[ensureNotMain, onDelete, requireAdapterGeneration, session, store],
|
|
1118
1166
|
);
|
|
@@ -1121,6 +1169,7 @@ const useRemoteThreadList = (
|
|
|
1121
1169
|
async (
|
|
1122
1170
|
threadIdOrRemoteId: string,
|
|
1123
1171
|
messages: readonly ThreadMessage[] | undefined,
|
|
1172
|
+
options?: { automatic?: boolean },
|
|
1124
1173
|
) => {
|
|
1125
1174
|
const currentAdapter = session.adapter;
|
|
1126
1175
|
const adapterGeneration = session.adapterGeneration;
|
|
@@ -1144,27 +1193,39 @@ const useRemoteThreadList = (
|
|
|
1144
1193
|
return;
|
|
1145
1194
|
}
|
|
1146
1195
|
if (!messages) return;
|
|
1147
|
-
|
|
1148
|
-
|
|
1149
|
-
|
|
1150
|
-
|
|
1151
|
-
|
|
1152
|
-
|
|
1153
|
-
|
|
1154
|
-
|
|
1155
|
-
|
|
1156
|
-
|
|
1157
|
-
|
|
1158
|
-
|
|
1159
|
-
|
|
1160
|
-
|
|
1161
|
-
|
|
1162
|
-
|
|
1196
|
+
await runThreadTitleGeneration({
|
|
1197
|
+
states: session.titleStates,
|
|
1198
|
+
threadId: data.id,
|
|
1199
|
+
automatic: options?.automatic === true,
|
|
1200
|
+
generate: async (onTitle) => {
|
|
1201
|
+
const stream = await currentAdapter.generateTitle(remoteId, messages);
|
|
1202
|
+
requireAdapterGeneration(adapterGeneration);
|
|
1203
|
+
await applyTitleStream(stream, onTitle);
|
|
1204
|
+
},
|
|
1205
|
+
rename: async (title) => {
|
|
1206
|
+
requireAdapterGeneration(adapterGeneration);
|
|
1207
|
+
await currentAdapter.rename(remoteId, title);
|
|
1208
|
+
},
|
|
1209
|
+
applyTitle: async (title) => {
|
|
1210
|
+
await store.optimisticUpdate({
|
|
1211
|
+
execute: async () => {},
|
|
1212
|
+
optimistic: (state) => {
|
|
1213
|
+
if (adapterGeneration !== session.adapterGeneration) return state;
|
|
1214
|
+
const current = getThreadData(state, data.id);
|
|
1215
|
+
if (!current) return state;
|
|
1216
|
+
return {
|
|
1217
|
+
...state,
|
|
1218
|
+
threadData: {
|
|
1219
|
+
...state.threadData,
|
|
1220
|
+
[current.id]: {
|
|
1221
|
+
...current,
|
|
1222
|
+
title,
|
|
1223
|
+
},
|
|
1163
1224
|
},
|
|
1164
|
-
}
|
|
1165
|
-
}
|
|
1166
|
-
}
|
|
1167
|
-
}
|
|
1225
|
+
};
|
|
1226
|
+
},
|
|
1227
|
+
});
|
|
1228
|
+
},
|
|
1168
1229
|
});
|
|
1169
1230
|
},
|
|
1170
1231
|
[backgroundThreads, requireAdapterGeneration, session, store],
|
|
@@ -1192,7 +1253,8 @@ const useRemoteThreadList = (
|
|
|
1192
1253
|
onArchive: (id) => archive(id),
|
|
1193
1254
|
onUnarchive: (id) => unarchive(id),
|
|
1194
1255
|
onDelete: (id) => deleteThread(id),
|
|
1195
|
-
onGenerateTitle: (id, messages) =>
|
|
1256
|
+
onGenerateTitle: (id, messages, options) =>
|
|
1257
|
+
generateTitle(id, messages, options),
|
|
1196
1258
|
onInitialize: async (id) => toInitializeResult(await initialize(id)),
|
|
1197
1259
|
onDetach: (id) => detach(id),
|
|
1198
1260
|
});
|
|
@@ -1201,7 +1263,12 @@ const useRemoteThreadList = (
|
|
|
1201
1263
|
useEffect(() => {
|
|
1202
1264
|
if (session.lastNotifiedRemoteId === mainRemoteId) return;
|
|
1203
1265
|
session.lastNotifiedRemoteId = mainRemoteId;
|
|
1204
|
-
|
|
1266
|
+
invokeUserCallback(
|
|
1267
|
+
"assistant-ui",
|
|
1268
|
+
"onThreadIdChange",
|
|
1269
|
+
onThreadIdChange,
|
|
1270
|
+
mainRemoteId,
|
|
1271
|
+
);
|
|
1205
1272
|
}, [mainRemoteId, onThreadIdChange, session]);
|
|
1206
1273
|
|
|
1207
1274
|
useEffect(() => {
|
|
@@ -1230,6 +1297,7 @@ const useRemoteThreadList = (
|
|
|
1230
1297
|
mainThreadId,
|
|
1231
1298
|
newThreadId: listState.newThreadId ?? null,
|
|
1232
1299
|
isLoading: listState.isLoading,
|
|
1300
|
+
loadError: listState.loadError,
|
|
1233
1301
|
isLoadingMore: listState.isLoadingMore,
|
|
1234
1302
|
hasMore: listState.cursor !== undefined,
|
|
1235
1303
|
threadIds: listState.threadIds,
|
|
@@ -1241,6 +1309,7 @@ const useRemoteThreadList = (
|
|
|
1241
1309
|
listState.archivedThreadIds,
|
|
1242
1310
|
listState.cursor,
|
|
1243
1311
|
listState.isLoading,
|
|
1312
|
+
listState.loadError,
|
|
1244
1313
|
listState.isLoadingMore,
|
|
1245
1314
|
listState.newThreadId,
|
|
1246
1315
|
listState.threadIds,
|
|
@@ -21,6 +21,7 @@ import {
|
|
|
21
21
|
} from "../model-context/toolbox";
|
|
22
22
|
import type { ToolCallMessagePartComponent } from "../types/MessagePartComponentTypes";
|
|
23
23
|
import { ModelContext } from "../../store/clients/model-context-client";
|
|
24
|
+
import { nullProtoRecord } from "../../utils/record";
|
|
24
25
|
|
|
25
26
|
export type { McpAppResourceOutput };
|
|
26
27
|
|
|
@@ -44,7 +45,9 @@ const useTools = ({
|
|
|
44
45
|
const mcpAppOutputs = useResources(mcpApp ? [withKey("mcpApp", mcpApp)] : []);
|
|
45
46
|
const mcpAppOutput = mcpAppOutputs[0];
|
|
46
47
|
|
|
47
|
-
const [toolUIs, setToolUIs] = useState<ToolsState["toolUIs"]>(() =>
|
|
48
|
+
const [toolUIs, setToolUIs] = useState<ToolsState["toolUIs"]>(() =>
|
|
49
|
+
nullProtoRecord(),
|
|
50
|
+
);
|
|
48
51
|
|
|
49
52
|
const state = useMemo(
|
|
50
53
|
(): ToolsState => ({
|
|
@@ -73,20 +76,25 @@ const useTools = ({
|
|
|
73
76
|
standalone: options?.standalone ?? false,
|
|
74
77
|
};
|
|
75
78
|
|
|
76
|
-
setToolUIs((prev) =>
|
|
77
|
-
|
|
78
|
-
[toolName]
|
|
79
|
-
|
|
79
|
+
setToolUIs((prev) => {
|
|
80
|
+
const next = nullProtoRecord(prev);
|
|
81
|
+
next[toolName] = [...(next[toolName] ?? []), registration];
|
|
82
|
+
return next;
|
|
83
|
+
});
|
|
80
84
|
|
|
81
85
|
return () => {
|
|
82
86
|
setToolUIs((prev) => {
|
|
83
|
-
const
|
|
84
|
-
|
|
87
|
+
const registrations =
|
|
88
|
+
prev[toolName]?.filter((r) => r !== registration) ?? [];
|
|
89
|
+
const next = nullProtoRecord(prev);
|
|
90
|
+
if (registrations.length > 0) {
|
|
91
|
+
next[toolName] = registrations;
|
|
92
|
+
return next;
|
|
93
|
+
}
|
|
85
94
|
// Drop the key entirely so repeatedly mounted/unmounted tools
|
|
86
95
|
// don't leave empty arrays accumulating across a long session.
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
return rest;
|
|
96
|
+
delete next[toolName];
|
|
97
|
+
return next;
|
|
90
98
|
});
|
|
91
99
|
};
|
|
92
100
|
},
|
|
@@ -108,6 +116,9 @@ const useTools = ({
|
|
|
108
116
|
: undefined);
|
|
109
117
|
if (render) {
|
|
110
118
|
unsubscribes.push(
|
|
119
|
+
// Registration has to be undone on unmount, so the registry write and
|
|
120
|
+
// its unsubscribe belong to the same effect.
|
|
121
|
+
// eslint-disable-next-line react-hooks/set-state-in-effect
|
|
111
122
|
setToolUI(toolName, render, {
|
|
112
123
|
standalone: isStandaloneToolDisplay(tool),
|
|
113
124
|
renderText: toolRenderText,
|
|
@@ -141,7 +152,7 @@ const useTools = ({
|
|
|
141
152
|
acc[name] = rest as Tool<any, any>;
|
|
142
153
|
return acc;
|
|
143
154
|
},
|
|
144
|
-
|
|
155
|
+
nullProtoRecord<Tool<any, any>>(),
|
|
145
156
|
);
|
|
146
157
|
|
|
147
158
|
const modelContextProvider = {
|
|
@@ -241,6 +241,50 @@ describe("buildInteractableModelContext", () => {
|
|
|
241
241
|
expect(mockGenerateId).toHaveBeenCalledOnce();
|
|
242
242
|
});
|
|
243
243
|
|
|
244
|
+
it.each(["__proto__", "toString"])(
|
|
245
|
+
"mints ids for items in a prototype-named array field %s",
|
|
246
|
+
async (field) => {
|
|
247
|
+
const itemSchema = {
|
|
248
|
+
type: "object" as const,
|
|
249
|
+
properties: {
|
|
250
|
+
id: { type: "string" as const },
|
|
251
|
+
title: { type: "string" as const },
|
|
252
|
+
},
|
|
253
|
+
required: ["id", "title"],
|
|
254
|
+
};
|
|
255
|
+
const schema = {
|
|
256
|
+
type: "object" as const,
|
|
257
|
+
properties: Object.fromEntries([
|
|
258
|
+
[field, { type: "array" as const, items: itemSchema }],
|
|
259
|
+
]),
|
|
260
|
+
};
|
|
261
|
+
const state = Object.fromEntries([[field, []]]);
|
|
262
|
+
const defs = { b1: def("b1", "taskBoard", state) };
|
|
263
|
+
const { ctx } = build(defs, new Map([["b1", schema]]));
|
|
264
|
+
const args = Object.fromEntries([
|
|
265
|
+
["id", "b1"],
|
|
266
|
+
[field, { add: [{ title: "Write tests" }] }],
|
|
267
|
+
]);
|
|
268
|
+
|
|
269
|
+
const result = (await ctx!.tools["update_taskBoard"]!.execute!(
|
|
270
|
+
args,
|
|
271
|
+
{} as never,
|
|
272
|
+
)) as {
|
|
273
|
+
addedItemIds: Record<string, string[]>;
|
|
274
|
+
};
|
|
275
|
+
|
|
276
|
+
expect(Object.getPrototypeOf(result.addedItemIds)).toBe(
|
|
277
|
+
Object.prototype,
|
|
278
|
+
);
|
|
279
|
+
expect(Object.hasOwn(result.addedItemIds, field)).toBe(true);
|
|
280
|
+
expect(result.addedItemIds[field]).toEqual(["generated-id"]);
|
|
281
|
+
expect(Object.hasOwn(defs.b1.state as object, field)).toBe(true);
|
|
282
|
+
expect((defs.b1.state as Record<string, unknown>)[field]).toEqual([
|
|
283
|
+
{ title: "Write tests", id: "generated-id" },
|
|
284
|
+
]);
|
|
285
|
+
},
|
|
286
|
+
);
|
|
287
|
+
|
|
244
288
|
it("rejects an unknown id and lists valid ids", async () => {
|
|
245
289
|
const defs = { n1: def("n1", "note"), n2: def("n2", "note") };
|
|
246
290
|
const { ctx, setDefState } = build(defs);
|
|
@@ -8,6 +8,7 @@ import {
|
|
|
8
8
|
} from "../../model-context/interactable-composer-metadata";
|
|
9
9
|
import { generateId } from "../../utils/id";
|
|
10
10
|
import { isRecord } from "../../utils/json/is-json";
|
|
11
|
+
import { nullProtoRecord } from "../../utils/record";
|
|
11
12
|
|
|
12
13
|
export type PartialJSONSchema = ReturnType<typeof toJSONSchema>;
|
|
13
14
|
|
|
@@ -243,7 +244,7 @@ export function buildInteractableModelContext(
|
|
|
243
244
|
}
|
|
244
245
|
const baseline = streamBaselines.get(toolCallId);
|
|
245
246
|
streamBaselines.delete(toolCallId);
|
|
246
|
-
const addedItemIds
|
|
247
|
+
const addedItemIds = nullProtoRecord<string[]>();
|
|
247
248
|
setDefState(target.id, (prev) =>
|
|
248
249
|
shallowMergeInteractableState(prev, partial, {
|
|
249
250
|
arrayBaseline:
|
|
@@ -264,7 +265,7 @@ export function buildInteractableModelContext(
|
|
|
264
265
|
addedItemIds?: Record<string, string[]>;
|
|
265
266
|
} = { success: true, id: target.id };
|
|
266
267
|
if (Object.keys(addedItemIds).length > 0) {
|
|
267
|
-
result.addedItemIds = addedItemIds;
|
|
268
|
+
result.addedItemIds = { ...addedItemIds };
|
|
268
269
|
}
|
|
269
270
|
return result;
|
|
270
271
|
},
|
package/src/react/index.ts
CHANGED
|
@@ -217,8 +217,12 @@ export { useExternalStoreSharedOptions } from "./runtimes/useExternalStoreShared
|
|
|
217
217
|
export {
|
|
218
218
|
useExternalMessageConverter,
|
|
219
219
|
convertExternalMessages,
|
|
220
|
+
createExternalMessageConversionCache,
|
|
221
|
+
} from "./runtimes/external-message-converter";
|
|
222
|
+
export type {
|
|
223
|
+
ExternalMessageConversionCache,
|
|
224
|
+
JoinStrategy,
|
|
220
225
|
} from "./runtimes/external-message-converter";
|
|
221
|
-
export type { JoinStrategy } from "./runtimes/external-message-converter";
|
|
222
226
|
export { createMessageConverter } from "./runtimes/createMessageConverter";
|
|
223
227
|
export {
|
|
224
228
|
useStreamingTiming,
|