@athenaintel/react 0.41.3 → 0.42.2
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/README.md +132 -10
- package/dist/agent-runtime/src/asset-attachment.d.ts +98 -0
- package/dist/agent-runtime/src/athena-asset-drag.d.ts +32 -0
- package/dist/agent-runtime/src/auth-denial.d.ts +29 -0
- package/dist/agent-runtime/src/chat-outbox-attachments.cjs +41 -0
- package/dist/agent-runtime/src/chat-outbox-attachments.cjs.map +1 -0
- package/dist/agent-runtime/src/chat-outbox-attachments.d.ts +38 -0
- package/dist/agent-runtime/src/chat-outbox-attachments.js +41 -0
- package/dist/agent-runtime/src/chat-outbox-attachments.js.map +1 -0
- package/dist/agent-runtime/src/chat-outbox-signals.cjs +63 -0
- package/dist/agent-runtime/src/chat-outbox-signals.cjs.map +1 -0
- package/dist/agent-runtime/src/chat-outbox-signals.d.ts +12 -0
- package/dist/agent-runtime/src/chat-outbox-signals.js +63 -0
- package/dist/agent-runtime/src/chat-outbox-signals.js.map +1 -0
- package/dist/agent-runtime/src/chat-outbox-store.cjs +509 -0
- package/dist/agent-runtime/src/chat-outbox-store.cjs.map +1 -0
- package/dist/agent-runtime/src/chat-outbox-store.d.ts +203 -0
- package/dist/agent-runtime/src/chat-outbox-store.js +509 -0
- package/dist/agent-runtime/src/chat-outbox-store.js.map +1 -0
- package/dist/agent-runtime/src/chat-outbox-thread.cjs +136 -0
- package/dist/agent-runtime/src/chat-outbox-thread.cjs.map +1 -0
- package/dist/agent-runtime/src/chat-outbox-thread.d.ts +118 -0
- package/dist/agent-runtime/src/chat-outbox-thread.js +136 -0
- package/dist/agent-runtime/src/chat-outbox-thread.js.map +1 -0
- package/dist/agent-runtime/src/chat-outbox.cjs +696 -0
- package/dist/agent-runtime/src/chat-outbox.cjs.map +1 -0
- package/dist/agent-runtime/src/chat-outbox.d.ts +285 -0
- package/dist/agent-runtime/src/chat-outbox.js +696 -0
- package/dist/agent-runtime/src/chat-outbox.js.map +1 -0
- package/dist/agent-runtime/src/chat-socket-reachability.d.ts +45 -0
- package/dist/agent-runtime/src/client-tool-bridge.d.ts +152 -0
- package/dist/agent-runtime/src/client-tools.d.ts +133 -0
- package/dist/agent-runtime/src/composer-markdown.cjs +10 -0
- package/dist/agent-runtime/src/composer-markdown.cjs.map +1 -1
- package/dist/agent-runtime/src/composer-markdown.d.ts +108 -0
- package/dist/agent-runtime/src/composer-markdown.js +10 -0
- package/dist/agent-runtime/src/composer-markdown.js.map +1 -1
- package/dist/agent-runtime/src/config-mutations.d.ts +51 -0
- package/dist/agent-runtime/src/conversation-index.d.ts +110 -0
- package/dist/agent-runtime/src/conversation-list.d.ts +343 -0
- package/dist/agent-runtime/src/deep-agent-transport-recipe.cjs +3 -2
- package/dist/agent-runtime/src/deep-agent-transport-recipe.cjs.map +1 -1
- package/dist/agent-runtime/src/deep-agent-transport-recipe.d.ts +166 -0
- package/dist/agent-runtime/src/deep-agent-transport-recipe.js +3 -2
- package/dist/agent-runtime/src/deep-agent-transport-recipe.js.map +1 -1
- package/dist/agent-runtime/src/desktop-handoff.d.ts +139 -0
- package/dist/agent-runtime/src/durable-thread-snapshot-cache.d.ts +60 -0
- package/dist/agent-runtime/src/edit-command.d.ts +156 -0
- package/dist/agent-runtime/src/errors.d.ts +174 -0
- package/dist/agent-runtime/src/execute-output.d.ts +31 -0
- package/dist/agent-runtime/src/generated/runconfig-contract.cjs +16 -2
- package/dist/agent-runtime/src/generated/runconfig-contract.cjs.map +1 -1
- package/dist/agent-runtime/src/generated/runconfig-contract.d.ts +202 -0
- package/dist/agent-runtime/src/generated/runconfig-contract.js +16 -2
- package/dist/agent-runtime/src/generated/runconfig-contract.js.map +1 -1
- package/dist/agent-runtime/src/github-wake-event.d.ts +77 -0
- package/dist/agent-runtime/src/index.d.ts +74 -0
- package/dist/agent-runtime/src/interrupts.cjs +17 -0
- package/dist/agent-runtime/src/interrupts.cjs.map +1 -1
- package/dist/agent-runtime/src/interrupts.d.ts +348 -0
- package/dist/agent-runtime/src/interrupts.js +17 -0
- package/dist/agent-runtime/src/interrupts.js.map +1 -1
- package/dist/agent-runtime/src/lane-follow.d.ts +121 -0
- package/dist/agent-runtime/src/lane-history.cjs +209 -0
- package/dist/agent-runtime/src/lane-history.cjs.map +1 -0
- package/dist/agent-runtime/src/lane-history.d.ts +175 -0
- package/dist/agent-runtime/src/lane-history.js +209 -0
- package/dist/agent-runtime/src/lane-history.js.map +1 -0
- package/dist/agent-runtime/src/lane-images.d.ts +184 -0
- package/dist/agent-runtime/src/message-author.d.ts +43 -0
- package/dist/agent-runtime/src/message-text.cjs +15 -0
- package/dist/agent-runtime/src/message-text.cjs.map +1 -0
- package/dist/agent-runtime/src/message-text.d.ts +47 -0
- package/dist/agent-runtime/src/message-text.js +15 -0
- package/dist/agent-runtime/src/message-text.js.map +1 -0
- package/dist/agent-runtime/src/message-window.cjs +15 -1
- package/dist/agent-runtime/src/message-window.cjs.map +1 -1
- package/dist/agent-runtime/src/message-window.d.ts +159 -0
- package/dist/agent-runtime/src/message-window.js +16 -2
- package/dist/agent-runtime/src/message-window.js.map +1 -1
- package/dist/agent-runtime/src/messages.cjs +123 -8
- package/dist/agent-runtime/src/messages.cjs.map +1 -1
- package/dist/agent-runtime/src/messages.d.ts +621 -0
- package/dist/agent-runtime/src/messages.js +123 -8
- package/dist/agent-runtime/src/messages.js.map +1 -1
- package/dist/agent-runtime/src/model-context.d.ts +22 -0
- package/dist/agent-runtime/src/offline-status.d.ts +157 -0
- package/dist/agent-runtime/src/optimistic-content.d.ts +21 -0
- package/dist/agent-runtime/src/protocol.cjs +12 -4
- package/dist/agent-runtime/src/protocol.cjs.map +1 -1
- package/dist/agent-runtime/src/protocol.d.ts +119 -0
- package/dist/agent-runtime/src/protocol.js +13 -5
- package/dist/agent-runtime/src/protocol.js.map +1 -1
- package/dist/agent-runtime/src/ptc-subcalls.d.ts +51 -0
- package/dist/agent-runtime/src/queue.d.ts +138 -0
- package/dist/agent-runtime/src/quota-safe-local-storage-session.cjs +10 -0
- package/dist/agent-runtime/src/quota-safe-local-storage-session.cjs.map +1 -1
- package/dist/agent-runtime/src/quota-safe-local-storage-session.d.ts +161 -0
- package/dist/agent-runtime/src/quota-safe-local-storage-session.js +10 -0
- package/dist/agent-runtime/src/quota-safe-local-storage-session.js.map +1 -1
- package/dist/agent-runtime/src/running-tool-placeholder.cjs +11 -0
- package/dist/agent-runtime/src/running-tool-placeholder.cjs.map +1 -0
- package/dist/agent-runtime/src/running-tool-placeholder.d.ts +25 -0
- package/dist/agent-runtime/src/running-tool-placeholder.js +11 -0
- package/dist/agent-runtime/src/running-tool-placeholder.js.map +1 -0
- package/dist/agent-runtime/src/runtime-messages.d.ts +104 -0
- package/dist/agent-runtime/src/screen-point.d.ts +151 -0
- package/dist/agent-runtime/src/sealed-idb.cjs +112 -0
- package/dist/agent-runtime/src/sealed-idb.cjs.map +1 -0
- package/dist/agent-runtime/src/sealed-idb.d.ts +106 -0
- package/dist/agent-runtime/src/sealed-idb.js +112 -0
- package/dist/agent-runtime/src/sealed-idb.js.map +1 -0
- package/dist/agent-runtime/src/send-recovery.d.ts +40 -0
- package/dist/agent-runtime/src/session-lane-scope.cjs +25 -0
- package/dist/agent-runtime/src/session-lane-scope.cjs.map +1 -0
- package/dist/agent-runtime/src/session-lane-scope.d.ts +59 -0
- package/dist/agent-runtime/src/session-lane-scope.js +25 -0
- package/dist/agent-runtime/src/session-lane-scope.js.map +1 -0
- package/dist/agent-runtime/src/statewire-attach-observer.d.ts +194 -0
- package/dist/agent-runtime/src/statewire-diagnostics.d.ts +74 -0
- package/dist/agent-runtime/src/statewire-state.d.ts +29 -0
- package/dist/agent-runtime/src/statewire-suspended.cjs.map +1 -1
- package/dist/agent-runtime/src/statewire-suspended.d.ts +27 -0
- package/dist/agent-runtime/src/statewire-suspended.js.map +1 -1
- package/dist/agent-runtime/src/statewire-transport.d.ts +40 -0
- package/dist/agent-runtime/src/streaming-markdown.d.ts +46 -0
- package/dist/agent-runtime/src/subagent-transcripts.cjs +209 -0
- package/dist/agent-runtime/src/subagent-transcripts.cjs.map +1 -0
- package/dist/agent-runtime/src/subagent-transcripts.d.ts +71 -0
- package/dist/agent-runtime/src/subagent-transcripts.js +209 -0
- package/dist/agent-runtime/src/subagent-transcripts.js.map +1 -0
- package/dist/agent-runtime/src/subagents.cjs +253 -0
- package/dist/agent-runtime/src/subagents.cjs.map +1 -0
- package/dist/agent-runtime/src/subagents.d.ts +311 -0
- package/dist/agent-runtime/src/subagents.js +253 -0
- package/dist/agent-runtime/src/subagents.js.map +1 -0
- package/dist/agent-runtime/src/subscription-wake-event.d.ts +111 -0
- package/dist/agent-runtime/src/thread-extras.d.ts +43 -0
- package/dist/agent-runtime/src/thread-handoff.d.ts +364 -0
- package/dist/agent-runtime/src/thread-prewarm-controller.d.ts +76 -0
- package/dist/agent-runtime/src/thread-prewarm.d.ts +118 -0
- package/dist/agent-runtime/src/thread-snapshot-cache.d.ts +99 -0
- package/dist/agent-runtime/src/thread-snapshot-mirror.cjs +46 -117
- package/dist/agent-runtime/src/thread-snapshot-mirror.cjs.map +1 -1
- package/dist/agent-runtime/src/thread-snapshot-mirror.d.ts +101 -0
- package/dist/agent-runtime/src/thread-snapshot-mirror.js +17 -88
- package/dist/agent-runtime/src/thread-snapshot-mirror.js.map +1 -1
- package/dist/agent-runtime/src/thread-status.d.ts +53 -0
- package/dist/agent-runtime/src/tool-metadata.d.ts +146 -0
- package/dist/agent-runtime/src/tool-names.cjs +71 -0
- package/dist/agent-runtime/src/tool-names.cjs.map +1 -1
- package/dist/agent-runtime/src/tool-names.d.ts +67 -0
- package/dist/agent-runtime/src/tool-names.js +72 -1
- package/dist/agent-runtime/src/tool-names.js.map +1 -1
- package/dist/agent-runtime/src/tool-outputs.d.ts +35 -0
- package/dist/agent-runtime/src/tool-result.cjs +1 -0
- package/dist/agent-runtime/src/tool-result.cjs.map +1 -1
- package/dist/agent-runtime/src/tool-result.d.ts +126 -0
- package/dist/agent-runtime/src/tool-result.js +1 -0
- package/dist/agent-runtime/src/tool-result.js.map +1 -1
- package/dist/agent-runtime/src/types.d.ts +159 -0
- package/dist/agent-runtime/src/use-conversation-list.d.ts +76 -0
- package/dist/agent-runtime/src/use-deep-agent-chat-outbox.cjs +136 -0
- package/dist/agent-runtime/src/use-deep-agent-chat-outbox.cjs.map +1 -0
- package/dist/agent-runtime/src/use-deep-agent-chat-outbox.d.ts +64 -0
- package/dist/agent-runtime/src/use-deep-agent-chat-outbox.js +136 -0
- package/dist/agent-runtime/src/use-deep-agent-chat-outbox.js.map +1 -0
- package/dist/agent-runtime/src/use-deep-agent-config.d.ts +169 -0
- package/dist/agent-runtime/src/use-deep-agent-edit-submit.cjs +13 -0
- package/dist/agent-runtime/src/use-deep-agent-edit-submit.cjs.map +1 -1
- package/dist/agent-runtime/src/use-deep-agent-edit-submit.d.ts +22 -0
- package/dist/agent-runtime/src/use-deep-agent-edit-submit.js +13 -0
- package/dist/agent-runtime/src/use-deep-agent-edit-submit.js.map +1 -1
- package/dist/agent-runtime/src/use-deep-agent-runtime.cjs +37 -2
- package/dist/agent-runtime/src/use-deep-agent-runtime.cjs.map +1 -1
- package/dist/agent-runtime/src/use-deep-agent-runtime.d.ts +177 -0
- package/dist/agent-runtime/src/use-deep-agent-runtime.js +38 -3
- package/dist/agent-runtime/src/use-deep-agent-runtime.js.map +1 -1
- package/dist/agent-runtime/src/use-deep-agent-thread.cjs +39 -13
- package/dist/agent-runtime/src/use-deep-agent-thread.cjs.map +1 -1
- package/dist/agent-runtime/src/use-deep-agent-thread.d.ts +352 -0
- package/dist/agent-runtime/src/use-deep-agent-thread.js +39 -13
- package/dist/agent-runtime/src/use-deep-agent-thread.js.map +1 -1
- package/dist/agent-runtime/src/use-deep-agent-voice.cjs +1019 -0
- package/dist/agent-runtime/src/use-deep-agent-voice.cjs.map +1 -0
- package/dist/agent-runtime/src/use-deep-agent-voice.d.ts +409 -0
- package/dist/agent-runtime/src/use-deep-agent-voice.js +1019 -0
- package/dist/agent-runtime/src/use-deep-agent-voice.js.map +1 -0
- package/dist/agent-runtime/src/use-deep-agent-window-sync.d.ts +102 -0
- package/dist/agent-runtime/src/use-historical-edit-attachments.d.ts +2 -0
- package/dist/agent-runtime/src/use-thread-handoff-flow.d.ts +84 -0
- package/dist/agent-runtime/src/voice-presentation.cjs +2 -0
- package/dist/agent-runtime/src/voice-presentation.cjs.map +1 -1
- package/dist/agent-runtime/src/voice-presentation.d.ts +80 -0
- package/dist/agent-runtime/src/voice-presentation.js +2 -0
- package/dist/agent-runtime/src/voice-presentation.js.map +1 -1
- package/dist/agent-runtime/src/voice-turn-grouping.d.ts +28 -0
- package/dist/agent-runtime/src/voice-wire-types.d.ts +15 -0
- package/dist/agent-runtime/src/withdrawn-turns.d.ts +97 -0
- package/dist/catalog/runtime-catalog.js +1 -1
- package/dist/chat/AthenaChat.cjs +192 -103
- package/dist/chat/AthenaChat.cjs.map +1 -1
- package/dist/chat/AthenaChat.d.ts +9 -0
- package/dist/chat/AthenaChat.js +194 -105
- package/dist/chat/AthenaChat.js.map +1 -1
- package/dist/chat/StatewireApprovalCard.d.ts +1 -1
- package/dist/chat/StatewireClientToolBridge.d.ts +1 -1
- package/dist/chat/StatewireQueuedMessages.cjs +11 -4
- package/dist/chat/StatewireQueuedMessages.cjs.map +1 -1
- package/dist/chat/StatewireQueuedMessages.d.ts +1 -1
- package/dist/chat/StatewireQueuedMessages.js +11 -4
- package/dist/chat/StatewireQueuedMessages.js.map +1 -1
- package/dist/chat/chat-outbox-rows.cjs +223 -0
- package/dist/chat/chat-outbox-rows.cjs.map +1 -0
- package/dist/chat/chat-outbox-rows.d.ts +29 -0
- package/dist/chat/chat-outbox-rows.js +223 -0
- package/dist/chat/chat-outbox-rows.js.map +1 -0
- package/dist/chat/chat-voice-controls.cjs +128 -0
- package/dist/chat/chat-voice-controls.cjs.map +1 -0
- package/dist/chat/chat-voice-controls.d.ts +19 -0
- package/dist/chat/chat-voice-controls.js +128 -0
- package/dist/chat/chat-voice-controls.js.map +1 -0
- package/dist/chat/statewire-approval.d.ts +1 -1
- package/dist/chat/statewire-client-tools.d.ts +1 -1
- package/dist/chat/super-grouping/SuperGroupingCard.cjs +3 -1
- package/dist/chat/super-grouping/SuperGroupingCard.cjs.map +1 -1
- package/dist/chat/super-grouping/SuperGroupingCard.d.ts +7 -1
- package/dist/chat/super-grouping/SuperGroupingCard.js +3 -1
- package/dist/chat/super-grouping/SuperGroupingCard.js.map +1 -1
- package/dist/chat/super-grouping/SuperGroupingTranscript.cjs +7 -2
- package/dist/chat/super-grouping/SuperGroupingTranscript.cjs.map +1 -1
- package/dist/chat/super-grouping/SuperGroupingTranscript.d.ts +2 -2
- package/dist/chat/super-grouping/SuperGroupingTranscript.js +7 -2
- package/dist/chat/super-grouping/SuperGroupingTranscript.js.map +1 -1
- package/dist/chat/super-grouping/activity-timeline.cjs +15 -8
- package/dist/chat/super-grouping/activity-timeline.cjs.map +1 -1
- package/dist/chat/super-grouping/activity-timeline.d.ts +18 -8
- package/dist/chat/super-grouping/activity-timeline.js +15 -8
- package/dist/chat/super-grouping/activity-timeline.js.map +1 -1
- package/dist/chat/use-statewire-approval-request.cjs +36 -0
- package/dist/chat/use-statewire-approval-request.cjs.map +1 -1
- package/dist/chat/use-statewire-approval-request.d.ts +49 -1
- package/dist/chat/use-statewire-approval-request.js +39 -3
- package/dist/chat/use-statewire-approval-request.js.map +1 -1
- package/dist/chat-ui/composer/tiptap-composer.cjs +133 -14
- package/dist/chat-ui/composer/tiptap-composer.cjs.map +1 -1
- package/dist/chat-ui/composer/tiptap-composer.d.ts +33 -1
- package/dist/chat-ui/composer/tiptap-composer.js +135 -16
- package/dist/chat-ui/composer/tiptap-composer.js.map +1 -1
- package/dist/chat-ui/header/conversation-history-panel.d.ts +1 -1
- package/dist/chat-ui/index.d.ts +1 -1
- package/dist/chat-ui/mentions/suggestions/data/api-client.cjs +2 -1
- package/dist/chat-ui/mentions/suggestions/data/api-client.cjs.map +1 -1
- package/dist/chat-ui/mentions/suggestions/data/api-client.d.ts +3 -1
- package/dist/chat-ui/mentions/suggestions/data/api-client.js +2 -1
- package/dist/chat-ui/mentions/suggestions/data/api-client.js.map +1 -1
- package/dist/chat-ui/mentions/use-account-workspace-id.cjs +29 -51
- package/dist/chat-ui/mentions/use-account-workspace-id.cjs.map +1 -1
- package/dist/chat-ui/mentions/use-account-workspace-id.d.ts +2 -2
- package/dist/chat-ui/mentions/use-account-workspace-id.js +30 -52
- package/dist/chat-ui/mentions/use-account-workspace-id.js.map +1 -1
- package/dist/chat-ui/messages/message-components.cjs +15 -0
- package/dist/chat-ui/messages/message-components.cjs.map +1 -1
- package/dist/chat-ui/messages/message-components.js +15 -0
- package/dist/chat-ui/messages/message-components.js.map +1 -1
- package/dist/chat-ui/messages/runtime-message.d.ts +1 -1
- package/dist/chat-ui/messages/statewire-continue-run.d.ts +1 -1
- package/dist/chat-ui/messages/user-edit-composer.cjs +15 -2
- package/dist/chat-ui/messages/user-edit-composer.cjs.map +1 -1
- package/dist/chat-ui/messages/user-edit-composer.d.ts +4 -2
- package/dist/chat-ui/messages/user-edit-composer.js +15 -2
- package/dist/chat-ui/messages/user-edit-composer.js.map +1 -1
- package/dist/chat-ui/messages/wake-marker.d.ts +1 -1
- package/dist/chat-ui/rich-text/chat-text-schema.cjs +1 -0
- package/dist/chat-ui/rich-text/chat-text-schema.cjs.map +1 -1
- package/dist/chat-ui/rich-text/chat-text-schema.d.ts +3 -0
- package/dist/chat-ui/rich-text/chat-text-schema.js +1 -0
- package/dist/chat-ui/rich-text/chat-text-schema.js.map +1 -1
- package/dist/chat-ui/statewire.cjs +1 -0
- package/dist/chat-ui/statewire.cjs.map +1 -1
- package/dist/chat-ui/statewire.d.ts +2 -2
- package/dist/chat-ui/statewire.js +2 -1
- package/dist/chat-ui/thread/composer-send-or-stop.cjs +2 -1
- package/dist/chat-ui/thread/composer-send-or-stop.cjs.map +1 -1
- package/dist/chat-ui/thread/composer-send-or-stop.d.ts +2 -0
- package/dist/chat-ui/thread/composer-send-or-stop.js +2 -1
- package/dist/chat-ui/thread/composer-send-or-stop.js.map +1 -1
- package/dist/chat-ui/thread/statewire-history-edge.d.ts +1 -1
- package/dist/composer/AttachmentContext.cjs +8 -4
- package/dist/composer/AttachmentContext.cjs.map +1 -1
- package/dist/composer/AttachmentContext.d.ts +7 -0
- package/dist/composer/AttachmentContext.js +8 -4
- package/dist/composer/AttachmentContext.js.map +1 -1
- package/dist/composer/build-composed-message.cjs +34 -0
- package/dist/composer/build-composed-message.cjs.map +1 -1
- package/dist/composer/build-composed-message.d.ts +20 -0
- package/dist/composer/build-composed-message.js +35 -1
- package/dist/composer/build-composed-message.js.map +1 -1
- package/dist/composer/composer-handoff.cjs +39 -2
- package/dist/composer/composer-handoff.cjs.map +1 -1
- package/dist/composer/composer-handoff.d.ts +28 -3
- package/dist/composer/composer-handoff.js +39 -2
- package/dist/composer/composer-handoff.js.map +1 -1
- package/dist/composer/useAttachFiles.cjs +15 -2
- package/dist/composer/useAttachFiles.cjs.map +1 -1
- package/dist/composer/useAttachFiles.d.ts +11 -0
- package/dist/composer/useAttachFiles.js +15 -2
- package/dist/composer/useAttachFiles.js.map +1 -1
- package/dist/composer/useSendMessage.cjs.map +1 -1
- package/dist/composer/useSendMessage.d.ts +4 -3
- package/dist/composer/useSendMessage.js.map +1 -1
- package/dist/diagnostics/athena-diagnostics.cjs.map +1 -1
- package/dist/diagnostics/athena-diagnostics.d.ts +3 -1
- package/dist/diagnostics/athena-diagnostics.js.map +1 -1
- package/dist/index.cjs +13 -0
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.ts +14 -7
- package/dist/index.js +14 -1
- package/dist/index.js.map +1 -1
- package/dist/offline/chat-outbox.cjs +57 -0
- package/dist/offline/chat-outbox.cjs.map +1 -0
- package/dist/offline/chat-outbox.d.ts +80 -0
- package/dist/offline/chat-outbox.js +57 -0
- package/dist/offline/chat-outbox.js.map +1 -0
- package/dist/offline/offline-history.d.ts +1 -1
- package/dist/provider/AthenaProvider.cjs +162 -8
- package/dist/provider/AthenaProvider.cjs.map +1 -1
- package/dist/provider/AthenaProvider.d.ts +15 -1
- package/dist/provider/AthenaProvider.js +163 -9
- package/dist/provider/AthenaProvider.js.map +1 -1
- package/dist/provider/statewire-window-context.d.ts +1 -1
- package/dist/react/package.json.cjs +1 -1
- package/dist/react/package.json.js +1 -1
- package/dist/references/src/anchors/file-line-range.d.ts +58 -0
- package/dist/references/src/anchors/format.d.ts +21 -0
- package/dist/references/src/anchors/message-anchors.d.ts +71 -0
- package/dist/references/src/anchors/parse.d.ts +8 -0
- package/dist/references/src/anchors/registry-contract.d.ts +24 -0
- package/dist/references/src/anchors/registry.d.ts +19 -0
- package/dist/references/src/anchors/schemas.d.ts +194 -0
- package/dist/references/src/anchors/serialize.d.ts +8 -0
- package/dist/references/src/anchors/time.d.ts +78 -0
- package/dist/references/src/anchors/types.d.ts +474 -0
- package/dist/references/src/asset-bounds.d.ts +27 -0
- package/dist/references/src/asset-links.d.ts +23 -0
- package/dist/references/src/asset-reference.d.ts +16 -0
- package/dist/references/src/formats/format-catalog.d.ts +79 -0
- package/dist/references/src/formats/markdown/parse-reference-markdown.d.ts +28 -0
- package/dist/references/src/formats/markdown/reference-display-name.d.ts +6 -0
- package/dist/references/src/formats/object/asset-object.d.ts +9 -0
- package/dist/references/src/formats/object/callable-object.d.ts +6 -0
- package/dist/references/src/formats/object/decode-reference-object-payload.d.ts +3 -0
- package/dist/references/src/formats/object/external-url-object.d.ts +9 -0
- package/dist/references/src/formats/object/group-object.d.ts +9 -0
- package/dist/references/src/formats/object/navigation-object.d.ts +9 -0
- package/dist/references/src/formats/object/parse-reference-object.d.ts +11 -0
- package/dist/references/src/formats/object/person-object.d.ts +9 -0
- package/dist/references/src/formats/uri/asset-mention-uri.d.ts +9 -0
- package/dist/references/src/formats/uri/asset-spaces-url.d.ts +9 -0
- package/dist/references/src/formats/uri/callable-mention-uris.d.ts +9 -0
- package/dist/references/src/formats/uri/detect-uri-wire.d.ts +9 -0
- package/dist/references/src/formats/uri/group-mention-uri.d.ts +12 -0
- package/dist/references/src/formats/uri/navigation-spaces-url.d.ts +14 -0
- package/dist/references/src/formats/uri/parse-reference-uri.d.ts +20 -0
- package/dist/references/src/formats/uri/person-mention-uri.d.ts +9 -0
- package/dist/references/src/formats/uri/template-placeholder.d.ts +12 -0
- package/dist/references/src/index.d.ts +47 -0
- package/dist/references/src/legacy/index.d.ts +14 -0
- package/dist/references/src/legacy/pre-reference-asset-url.d.ts +57 -0
- package/dist/references/src/legacy/pre-reference-citation-bridge.d.ts +22 -0
- package/dist/references/src/legacy/pre-reference-citation.d.ts +138 -0
- package/dist/references/src/legacy/pre-reference-external-url.d.ts +31 -0
- package/dist/references/src/legacy/pre-reference-format.d.ts +8 -0
- package/dist/references/src/legacy/pre-reference-mention.d.ts +27 -0
- package/dist/references/src/legacy/pre-reference-object.d.ts +8 -0
- package/dist/references/src/legacy/pre-reference-uri.d.ts +12 -0
- package/dist/references/src/legacy.d.ts +2 -0
- package/dist/references/src/mention-href-patterns.d.ts +19 -0
- package/dist/references/src/mention-node/index.d.ts +5 -0
- package/dist/references/src/mention-node/mention-node.d.ts +31 -0
- package/dist/references/src/mention-node/resolve-node-attrs.d.ts +27 -0
- package/dist/references/src/parse-reference.d.ts +23 -0
- package/dist/references/src/schemas.d.ts +463 -0
- package/dist/references/src/serialize-reference.d.ts +50 -0
- package/dist/references/src/sheet-name.d.ts +10 -0
- package/dist/references/src/tool-option-schemas.d.ts +597 -0
- package/dist/references/src/types.d.ts +125 -0
- package/dist/references/src/version-ref.d.ts +30 -0
- package/dist/runtime/statewire-lifecycle.d.ts +1 -1
- package/dist/runtime/statewire-model-lane.d.ts +1 -1
- package/dist/runtime/statewire-server-lane-context.d.ts +1 -1
- package/dist/runtime/statewire-session-key.cjs +7 -0
- package/dist/runtime/statewire-session-key.cjs.map +1 -1
- package/dist/runtime/statewire-session-key.d.ts +19 -0
- package/dist/runtime/statewire-session-key.js +8 -1
- package/dist/runtime/statewire-session-key.js.map +1 -1
- package/dist/runtime/statewire-session-lane.cjs +48 -0
- package/dist/runtime/statewire-session-lane.cjs.map +1 -0
- package/dist/runtime/statewire-session-lane.d.ts +29 -0
- package/dist/runtime/statewire-session-lane.js +48 -0
- package/dist/runtime/statewire-session-lane.js.map +1 -0
- package/dist/runtime/statewire-thread-config-lane.d.ts +1 -1
- package/dist/runtime/useAthenaStatewireRuntime.cjs +19 -5
- package/dist/runtime/useAthenaStatewireRuntime.cjs.map +1 -1
- package/dist/runtime/useAthenaStatewireRuntime.d.ts +15 -1
- package/dist/runtime/useAthenaStatewireRuntime.js +20 -6
- package/dist/runtime/useAthenaStatewireRuntime.js.map +1 -1
- package/dist/styles.css +1 -1
- package/dist/threads/api.d.ts +1 -1
- package/dist/threads/conversation-list-fetcher.d.ts +1 -1
- package/dist/threads/index-triggered-refresh.cjs +164 -0
- package/dist/threads/index-triggered-refresh.cjs.map +1 -0
- package/dist/threads/index-triggered-refresh.d.ts +70 -0
- package/dist/threads/index-triggered-refresh.js +164 -0
- package/dist/threads/index-triggered-refresh.js.map +1 -0
- package/dist/threads/offline-session-list.d.ts +1 -1
- package/dist/threads/pull-request-display.d.ts +1 -1
- package/dist/threads/session-list-model.d.ts +1 -1
- package/dist/threads/session-list-tab-share.cjs +150 -0
- package/dist/threads/session-list-tab-share.cjs.map +1 -0
- package/dist/threads/session-list-tab-share.d.ts +73 -0
- package/dist/threads/session-list-tab-share.js +150 -0
- package/dist/threads/session-list-tab-share.js.map +1 -0
- package/dist/threads/session-row-parts.d.ts +1 -1
- package/dist/threads/sessions-query.d.ts +1 -1
- package/dist/threads/statewire-thread-list.cjs +42 -16
- package/dist/threads/statewire-thread-list.cjs.map +1 -1
- package/dist/threads/statewire-thread-list.d.ts +11 -2
- package/dist/threads/statewire-thread-list.js +43 -17
- package/dist/threads/statewire-thread-list.js.map +1 -1
- package/dist/threads/thread-prefetcher.d.ts +1 -1
- package/dist/threads/use-athena-session-attention.d.ts +1 -1
- package/dist/threads/use-athena-sessions.cjs +32 -22
- package/dist/threads/use-athena-sessions.cjs.map +1 -1
- package/dist/threads/use-athena-sessions.js +33 -23
- package/dist/threads/use-athena-sessions.js.map +1 -1
- package/dist/threads/use-rest-conversation-history.d.ts +1 -1
- package/dist/threads/use-statewire-conversation-history.d.ts +5 -5
- package/dist/tiptap-markdown-table/src/markdown-table-serializer.d.ts +56 -0
- package/dist/tools/NestedPtcMessages.cjs +14 -9
- package/dist/tools/NestedPtcMessages.cjs.map +1 -1
- package/dist/tools/NestedPtcMessages.d.ts +9 -0
- package/dist/tools/NestedPtcMessages.js +6 -1
- package/dist/tools/NestedPtcMessages.js.map +1 -1
- package/dist/tools/index.d.ts +1 -1
- package/dist/tools/primitives.d.ts +1 -1
- package/dist/tools/subagent-task-tool-ui.cjs +494 -0
- package/dist/tools/subagent-task-tool-ui.cjs.map +1 -0
- package/dist/tools/subagent-task-tool-ui.d.ts +109 -0
- package/dist/tools/subagent-task-tool-ui.js +494 -0
- package/dist/tools/subagent-task-tool-ui.js.map +1 -0
- package/dist/tools/tool-fallback.d.ts +1 -1
- package/dist/tools/tool-icons.d.ts +1 -1
- package/dist/tools/tool-summary.d.ts +1 -1
- package/dist/tools/tool-uis.cjs +4 -0
- package/dist/tools/tool-uis.cjs.map +1 -1
- package/dist/tools/tool-uis.js +4 -0
- package/dist/tools/tool-uis.js.map +1 -1
- package/dist/voice/chat.cjs +6 -0
- package/dist/voice/chat.cjs.map +1 -0
- package/dist/voice/chat.d.ts +2 -0
- package/dist/voice/chat.js +6 -0
- package/dist/voice/chat.js.map +1 -0
- package/dist/voice/livekit-join.cjs +119 -0
- package/dist/voice/livekit-join.cjs.map +1 -0
- package/dist/voice/livekit-join.d.ts +8 -0
- package/dist/voice/livekit-join.js +119 -0
- package/dist/voice/livekit-join.js.map +1 -0
- package/dist/voice/livekit.cjs +32 -0
- package/dist/voice/livekit.cjs.map +1 -0
- package/dist/voice/livekit.d.ts +80 -0
- package/dist/voice/livekit.js +32 -0
- package/dist/voice/livekit.js.map +1 -0
- package/dist/voice/use-chat-voice-enabled.cjs +43 -0
- package/dist/voice/use-chat-voice-enabled.cjs.map +1 -0
- package/dist/voice/use-chat-voice-enabled.d.ts +9 -0
- package/dist/voice/use-chat-voice-enabled.js +43 -0
- package/dist/voice/use-chat-voice-enabled.js.map +1 -0
- package/package.json +22 -16
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"user-edit-composer.js","sources":["../../../src/chat-ui/messages/user-edit-composer.tsx"],"sourcesContent":["import { ComposerPrimitive, useAuiState } from \"@assistant-ui/react\";\nimport {
|
|
1
|
+
{"version":3,"file":"user-edit-composer.js","sources":["../../../src/chat-ui/messages/user-edit-composer.tsx"],"sourcesContent":["import { ComposerPrimitive, useAuiState } from \"@assistant-ui/react\";\nimport {\n CHAT_EDIT_KEPT_MESSAGE,\n ChatEditUnreachableError,\n useChatOutboxReachable,\n useDeepAgentChatOutboxContext,\n useDeepAgentMessageEditSubmit,\n} from \"@athenaintel/agent-runtime\";\nimport { type FC, type KeyboardEvent, useState } from \"react\";\n\n/**\n * Rendered in place of a user message while it is being edited (entered via\n * the action bar's Edit control, which seeds this composer with the message\n * text). Sending leaves as a `run/edit` anchored on the host's own parent of\n * the message (`useDeepAgentMessageEditSubmit`) — on a windowed wire the\n * lane's `anchorBefore` at the window edge — so the rewind is never rejected\n * `wrong-anchor` the way the library's converted-message anchor is after a\n * chunked assistant turn; Escape/Cancel exits edit mode. An edit submitted\n * while the host's chat outbox says Athena can't be reached is refused: the\n * draft stays here and the composer says why until Athena answers again.\n */\nexport const UserEditComposer: FC = () => {\n const submit = useDeepAgentMessageEditSubmit();\n const isEmpty = useAuiState((s) => s.message.composer.isEmpty);\n const reachable = useChatOutboxReachable(useDeepAgentChatOutboxContext());\n const [refused, setRefused] = useState(false);\n const send = () => {\n setRefused(false);\n submit().catch((error: unknown) => {\n if (!(error instanceof ChatEditUnreachableError)) throw error;\n setRefused(true);\n });\n };\n const onKeyDown = (event: KeyboardEvent<HTMLTextAreaElement>) => {\n if (event.key !== \"Enter\" || event.shiftKey || event.nativeEvent.isComposing) return;\n event.preventDefault();\n send();\n };\n return (\n <div className=\"mb-3 flex justify-end\" data-testid=\"chat-user-edit-composer\">\n <ComposerPrimitive.Root className=\"flex w-full max-w-[85%] flex-col gap-2 rounded-2xl rounded-br-md border border-border bg-muted px-3.5 py-2.5\">\n <ComposerPrimitive.Input\n autoFocus\n submitMode=\"none\"\n onKeyDown={onKeyDown}\n className=\"w-full resize-none bg-transparent text-sm text-foreground outline-none placeholder:text-muted-foreground\"\n />\n {refused && !reachable && (\n <p role=\"status\" data-testid=\"chat-user-edit-refused\" className=\"text-xs text-muted-foreground\">\n {CHAT_EDIT_KEPT_MESSAGE}\n </p>\n )}\n <div className=\"flex items-center justify-end gap-1.5\">\n <ComposerPrimitive.Cancel asChild>\n <button\n type=\"button\"\n className=\"rounded-lg px-2.5 py-1 text-xs font-medium text-muted-foreground transition-colors hover:bg-accent hover:text-foreground\"\n >\n Cancel\n </button>\n </ComposerPrimitive.Cancel>\n <button\n type=\"button\"\n data-testid=\"chat-user-edit-send\"\n disabled={isEmpty}\n onClick={send}\n className=\"rounded-lg bg-foreground px-2.5 py-1 text-xs font-medium text-background shadow-sm transition-colors hover:bg-foreground/80 disabled:cursor-not-allowed disabled:opacity-60\"\n >\n Send\n </button>\n </div>\n </ComposerPrimitive.Root>\n </div>\n );\n};\n"],"names":[],"mappings":";;;;;;AAqBO,MAAM,mBAAuB,MAAM;AACxC,QAAM,SAAS,8BAAA;AACf,QAAM,UAAU,YAAY,CAAC,MAAM,EAAE,QAAQ,SAAS,OAAO;AAC7D,QAAM,YAAY,uBAAuB,+BAA+B;AACxE,QAAM,CAAC,SAAS,UAAU,IAAI,SAAS,KAAK;AAC5C,QAAM,OAAO,MAAM;AACjB,eAAW,KAAK;AAChB,WAAA,EAAS,MAAM,CAAC,UAAmB;AACjC,UAAI,EAAE,iBAAiB,0BAA2B,OAAM;AACxD,iBAAW,IAAI;AAAA,IACjB,CAAC;AAAA,EACH;AACA,QAAM,YAAY,CAAC,UAA8C;AAC/D,QAAI,MAAM,QAAQ,WAAW,MAAM,YAAY,MAAM,YAAY,YAAa;AAC9E,UAAM,eAAA;AACN,SAAA;AAAA,EACF;AACA,SACE,oBAAC,OAAA,EAAI,WAAU,yBAAwB,eAAY,2BACjD,UAAA,qBAAC,kBAAkB,MAAlB,EAAuB,WAAU,gHAChC,UAAA;AAAA,IAAA;AAAA,MAAC,kBAAkB;AAAA,MAAlB;AAAA,QACC,WAAS;AAAA,QACT,YAAW;AAAA,QACX;AAAA,QACA,WAAU;AAAA,MAAA;AAAA,IAAA;AAAA,IAEX,WAAW,CAAC,aACX,oBAAC,KAAA,EAAE,MAAK,UAAS,eAAY,0BAAyB,WAAU,iCAC7D,UAAA,uBAAA,CACH;AAAA,IAEF,qBAAC,OAAA,EAAI,WAAU,yCACb,UAAA;AAAA,MAAA,oBAAC,kBAAkB,QAAlB,EAAyB,SAAO,MAC/B,UAAA;AAAA,QAAC;AAAA,QAAA;AAAA,UACC,MAAK;AAAA,UACL,WAAU;AAAA,UACX,UAAA;AAAA,QAAA;AAAA,MAAA,GAGH;AAAA,MACA;AAAA,QAAC;AAAA,QAAA;AAAA,UACC,MAAK;AAAA,UACL,eAAY;AAAA,UACZ,UAAU;AAAA,UACV,SAAS;AAAA,UACT,WAAU;AAAA,UACX,UAAA;AAAA,QAAA;AAAA,MAAA;AAAA,IAED,EAAA,CACF;AAAA,EAAA,EAAA,CACF,EAAA,CACF;AAEJ;"}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { type GithubWakeEvent, type SubscriptionWakeEvent } from "
|
|
1
|
+
import { type GithubWakeEvent, type SubscriptionWakeEvent } from "../../agent-runtime/src/index";
|
|
2
2
|
import { type ComponentPropsWithoutRef, type FC } from "react";
|
|
3
3
|
export interface WakeMarkerCardProps extends Omit<ComponentPropsWithoutRef<"div">, "children" | "role"> {
|
|
4
4
|
event: GithubWakeEvent;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"chat-text-schema.cjs","sources":["../../../src/chat-ui/rich-text/chat-text-schema.tsx"],"sourcesContent":["import { Editor, Extension, type Extensions } from \"@tiptap/core\";\nimport { DOMParser as ProseMirrorDOMParser } from \"@tiptap/pm/model\";\nimport StarterKit from \"@tiptap/starter-kit\";\nimport CodeBlock from \"@tiptap/extension-code-block\";\nimport { ReactNodeViewRenderer } from \"@tiptap/react\";\nimport Link from \"@tiptap/extension-link\";\nimport Image from \"@tiptap/extension-image\";\nimport { Table, TableCell, TableHeader, TableRow } from \"@tiptap/extension-table\";\nimport TaskList from \"@tiptap/extension-task-list\";\nimport TaskItem from \"@tiptap/extension-task-item\";\nimport { markdownTableStorage } from \"@athenaintel/tiptap-markdown-table\";\nimport { Markdown } from \"tiptap-markdown\";\nimport { getMarkdownStorage } from \"../markdown-storage\";\nimport { MentionExtension } from \"../mentions/mention-extension\";\nimport { ChatCodeBlockNodeView, ChatMentionNodeView } from \"./chat-node-views\";\nimport { isAllowedChatHref, normalizeCitationAnchors } from \"./citation-anchors\";\n\nconst ChatMentionExtension = MentionExtension.extend({\n addNodeView: () => ReactNodeViewRenderer(ChatMentionNodeView, { as: \"span\" }),\n});\n/** Fenced code rendered through `ChatCodeBlock` (language label + copy button). */\nexport const ChatCodeBlockExtension = CodeBlock.extend({\n addNodeView: () => ReactNodeViewRenderer(ChatCodeBlockNodeView),\n});\n\n/**\n * The table node, written to Markdown through the table writer Olympus's\n * editors share (`@athenaintel/tiptap-markdown-table`), which escapes a `|`\n * inside a cell as `\\|`, so a draft's table reaches the message with the cells\n * it was typed with.\n */\nexport const ChatTableExtension = Table.extend({\n addStorage() {\n return { ...this.parent?.(), ...markdownTableStorage() };\n },\n});\n\n/**\n * The Link mark with the excerpt a citation carries (`data-excerpt`, the\n * source chip's tooltip and scroll-to-text target) and an href allow-list\n * narrower than tiptap's default: `http(s):`, `mailto:`, the screen-point\n * protocol and app-relative Spaces paths pass; every other scheme\n * (`javascript:`, `ftp:`, `data:`, protocol-relative `//host`) is dropped and\n * its label kept as text. The same rule governs the composer's autolink.\n */\nexport const ChatLinkExtension = Link.extend({\n addAttributes() {\n return {\n ...this.parent?.(),\n excerpt: {\n default: null,\n parseHTML: (element: HTMLElement) => element.getAttribute(\"data-excerpt\"),\n renderHTML: (attributes: Record<string, unknown>) =>\n typeof attributes.excerpt === \"string\" && attributes.excerpt\n ? { \"data-excerpt\": attributes.excerpt }\n : {},\n },\n };\n },\n});\n\n/** Both the editable draft and the static message body use this schema and parser. */\nexport function createChatTextExtensions(): Extensions {\n return [\n StarterKit.configure({\n codeBlock: false,\n // Tiptap 3 StarterKit also bundles these; chat text registers its own link and never had the rest.\n link: false,\n underline: false,\n listKeymap: false,\n trailingNode: false,\n }),\n ChatCodeBlockExtension,\n ChatLinkExtension.configure({\n openOnClick: false,\n autolink: true,\n linkOnPaste: true,\n // No `protocols`: Tiptap's Link registers them with linkifyjs in every\n // editor's onCreate, and linkifyjs accepts a scheme only before its first\n // scan — so each chat body or composer created after the first one logged\n // \"linkifyjs: already initialized\" (seen in Chrome's extension Errors\n // page). Screen points arrive as markdown links (`[label](athena-point://…)`),\n // which parse without linkify, and `isAllowedChatHref` already admits\n // the scheme; only autolinking a bare `athena-point://` string needed it.\n isAllowedUri: (url) => isAllowedChatHref(url),\n }),\n Image.configure({ inline: true }),\n ChatTableExtension.configure({ resizable: false }),\n TableRow,\n TableCell,\n TableHeader,\n TaskList,\n TaskItem.configure({ nested: true }),\n Markdown.configure({\n html: true,\n tightLists: true,\n tightListClass: \"tight\",\n bulletListMarker: \"-\",\n linkify: true,\n breaks: true,\n transformPastedText: true,\n transformCopiedText: false,\n }),\n ChatMentionExtension,\n ];\n}\n\n/** The slice of a markdown-it token {@link TypedTextReading} rewrites. */\ninterface MarkdownToken {\n type: string;\n tag: string;\n nesting: number;\n markup: string;\n content: string;\n children: MarkdownToken[] | null;\n}\n\n/** The slice of markdown-it (the instance tiptap-markdown parses with) {@link TypedTextReading} configures. */\ninterface MarkdownIt {\n disable(rules: string | string[], ignoreInvalid?: boolean): unknown;\n core: {\n ruler: {\n after(\n afterName: string,\n ruleName: string,\n rule: (state: { tokens: MarkdownToken[] }) => void,\n ): void;\n };\n };\n}\n\n/** A line break tag: the one piece of HTML a composer writes, for a line break inside a table cell. */\nconst LINE_BREAK_TAG = /^<br\\s*\\/?>$/i;\n\n/**\n * The inline token a typed reading shows as the characters it was written\n * with. Raw HTML counts only when it is in the text itself (`source`, the\n * inline block's own content): a task list's checkbox is HTML markdown-it's\n * task-list rule makes, not text anyone typed.\n */\nfunction isTypedCharacters(token: MarkdownToken, source: string, inTable: boolean): boolean {\n if (token.type === \"html_inline\") {\n return (\n source.includes(token.content) && !(inTable && LINE_BREAK_TAG.test(token.content.trim()))\n );\n }\n return (\n (token.type === \"em_open\" ||\n token.type === \"em_close\" ||\n token.type === \"strong_open\" ||\n token.type === \"strong_close\") &&\n token.markup.startsWith(\"_\")\n );\n}\n\nconst typedReadingInstalled = new WeakSet<object>();\n\nfunction installTypedTextReading(markdownit: MarkdownIt): void {\n if (typedReadingInstalled.has(markdownit)) return;\n typedReadingInstalled.add(markdownit);\n markdownit.disable(\"html_block\");\n markdownit.core.ruler.after(\"inline\", \"athena_typed_text\", (state) => {\n let tables = 0;\n for (const block of state.tokens) {\n if (block.type === \"table_open\") tables += 1;\n if (block.type === \"table_close\") tables -= 1;\n for (const token of block.children ?? []) {\n if (!isTypedCharacters(token, block.content, tables > 0)) continue;\n if (token.type !== \"html_inline\") token.content = token.markup;\n token.type = \"text\";\n token.tag = \"\";\n token.nesting = 0;\n }\n }\n });\n}\n\n/**\n * How a person's typed text reads in the user bubble: the chat's Markdown,\n * except for the two readings no composer send relies on and plain text often\n * trips. Raw HTML stays the characters it was typed with (`List<T>` keeps its\n * `<T>`, `a <b>c</b>` is not bold): a composer writes a typed `<` as `<`,\n * and its only tag is a `<br>` for a line break inside a table cell, which a\n * table cell still reads as one. Underscore emphasis stays underscores\n * (`obj.__init__` keeps them, `_private_` is not italic): a composer writes\n * emphasis with `*` and escapes a typed `_`. Everything a composer does write\n * (bold, lists, code, links, mention chips, tables, and the escaped Markdown\n * of older sends) reads as the assistant's reading reads it.\n */\nconst TypedTextReading = Extension.create({\n name: \"athenaTypedTextReading\",\n addStorage() {\n return {\n markdown: {\n parse: {\n setup: (markdownit: MarkdownIt) => installTypedTextReading(markdownit),\n },\n },\n };\n },\n});\n\nlet parserEditor: Editor | undefined;\nlet typedParserEditor: Editor | undefined;\n\nfunction parseWith(editor: Editor, markdown: string) {\n const html: string = getMarkdownStorage(editor).parser.parse(markdown);\n const body = new window.DOMParser().parseFromString(html, \"text/html\").body;\n normalizeCitationAnchors(body);\n return ProseMirrorDOMParser.fromSchema(editor.schema).parse(body);\n}\n\n/**\n * A single detached parser per browser tab, never an editor per message.\n * Markdown → HTML (markdown-it, with bare URLs linkified and inline HTML kept)\n * → agora's citation anchors given their hrefs → the schema's document.\n */\nexport function parseChatText(markdown: string) {\n parserEditor ??= new Editor({\n extensions: createChatTextExtensions(),\n content: \"\",\n editable: false,\n });\n return parseWith(parserEditor, markdown);\n}\n\n/**\n * {@link parseChatText} for text a person typed (a user message): the same\n * schema and document, read with {@link TypedTextReading}.\n */\nexport function parseTypedChatText(markdown: string) {\n typedParserEditor ??= new Editor({\n extensions: [...createChatTextExtensions(), TypedTextReading],\n content: \"\",\n editable: false,\n });\n return parseWith(typedParserEditor, markdown);\n}\n\n/** Typography is shared; the composer supplies only its padding and scroll boundary. */\nexport const CHAT_TEXT_CLASS =\n \"aui-md prose prose-sm max-w-none min-w-0 break-words text-sm leading-snug text-foreground prose-p:my-1.5 prose-p:leading-snug prose-headings:mt-3 prose-headings:mb-1.5 prose-headings:font-semibold prose-h1:text-sm prose-h2:text-sm prose-h3:text-xs prose-ul:my-1.5 prose-ol:my-1.5 prose-li:my-0.5 prose-blockquote:border-l-2 prose-blockquote:border-border prose-blockquote:text-muted-foreground prose-code:rounded prose-code:bg-muted prose-code:px-1 prose-code:py-0.5 prose-code:text-xs prose-code:font-mono prose-code:before:content-none prose-code:after:content-none prose-pre:my-2 prose-pre:overflow-x-auto prose-pre:rounded-lg prose-pre:border prose-pre:border-border prose-pre:bg-muted/30 prose-pre:p-3 prose-a:text-primary prose-a:underline prose-a:decoration-primary/40 prose-a:underline-offset-2 hover:prose-a:decoration-primary prose-strong:font-semibold prose-hr:border-border [&>:first-child]:mt-0 [&>:last-child]:mb-0 [&_table]:block [&_table]:overflow-x-auto [&_td]:border [&_td]:border-border [&_td]:px-2 [&_th]:border [&_th]:border-border [&_th]:px-2 [&_ul[data-type=taskList]]:list-none [&_ul[data-type=taskList]]:pl-0 [&_li[data-type=taskItem]]:flex [&_li[data-type=taskItem]]:gap-2\";\n"],"names":["MentionExtension","ReactNodeViewRenderer","ChatMentionNodeView","ChatCodeBlockNodeView","Table","markdownTableStorage","isAllowedChatHref","TableRow","TableCell","TableHeader","Markdown","Extension","getMarkdownStorage","normalizeCitationAnchors","ProseMirrorDOMParser","Editor"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"chat-text-schema.cjs","sources":["../../../src/chat-ui/rich-text/chat-text-schema.tsx"],"sourcesContent":["import { Editor, Extension, type Extensions } from \"@tiptap/core\";\nimport { DOMParser as ProseMirrorDOMParser } from \"@tiptap/pm/model\";\nimport StarterKit from \"@tiptap/starter-kit\";\nimport CodeBlock from \"@tiptap/extension-code-block\";\nimport { ReactNodeViewRenderer } from \"@tiptap/react\";\nimport Link from \"@tiptap/extension-link\";\nimport Image from \"@tiptap/extension-image\";\nimport { Table, TableCell, TableHeader, TableRow } from \"@tiptap/extension-table\";\nimport TaskList from \"@tiptap/extension-task-list\";\nimport TaskItem from \"@tiptap/extension-task-item\";\nimport { markdownTableStorage } from \"@athenaintel/tiptap-markdown-table\";\nimport { Markdown } from \"tiptap-markdown\";\nimport { getMarkdownStorage } from \"../markdown-storage\";\nimport { MentionExtension } from \"../mentions/mention-extension\";\nimport { ChatCodeBlockNodeView, ChatMentionNodeView } from \"./chat-node-views\";\nimport { isAllowedChatHref, normalizeCitationAnchors } from \"./citation-anchors\";\n\nconst ChatMentionExtension = MentionExtension.extend({\n addNodeView: () => ReactNodeViewRenderer(ChatMentionNodeView, { as: \"span\" }),\n});\n/** Fenced code rendered through `ChatCodeBlock` (language label + copy button). */\nexport const ChatCodeBlockExtension = CodeBlock.extend({\n addNodeView: () => ReactNodeViewRenderer(ChatCodeBlockNodeView),\n});\n\n/**\n * The table node, written to Markdown through the table writer Olympus's\n * editors share (`@athenaintel/tiptap-markdown-table`), which escapes a `|`\n * inside a cell as `\\|`, so a draft's table reaches the message with the cells\n * it was typed with.\n */\nexport const ChatTableExtension = Table.extend({\n addStorage() {\n return { ...this.parent?.(), ...markdownTableStorage() };\n },\n});\n\n/**\n * The Link mark with the excerpt a citation carries (`data-excerpt`, the\n * source chip's tooltip and scroll-to-text target) and an href allow-list\n * narrower than tiptap's default: `http(s):`, `mailto:`, the screen-point\n * protocol and app-relative Spaces paths pass; every other scheme\n * (`javascript:`, `ftp:`, `data:`, protocol-relative `//host`) is dropped and\n * its label kept as text. The same rule governs the composer's autolink.\n *\n * Not inclusive (Tiptap makes an autolinking Link inclusive), so text typed at\n * a link's end, like the space after a pasted URL, stays outside the link.\n */\nexport const ChatLinkExtension = Link.extend({\n inclusive: false,\n\n addAttributes() {\n return {\n ...this.parent?.(),\n excerpt: {\n default: null,\n parseHTML: (element: HTMLElement) => element.getAttribute(\"data-excerpt\"),\n renderHTML: (attributes: Record<string, unknown>) =>\n typeof attributes.excerpt === \"string\" && attributes.excerpt\n ? { \"data-excerpt\": attributes.excerpt }\n : {},\n },\n };\n },\n});\n\n/** Both the editable draft and the static message body use this schema and parser. */\nexport function createChatTextExtensions(): Extensions {\n return [\n StarterKit.configure({\n codeBlock: false,\n // Tiptap 3 StarterKit also bundles these; chat text registers its own link and never had the rest.\n link: false,\n underline: false,\n listKeymap: false,\n trailingNode: false,\n }),\n ChatCodeBlockExtension,\n ChatLinkExtension.configure({\n openOnClick: false,\n autolink: true,\n linkOnPaste: true,\n // No `protocols`: Tiptap's Link registers them with linkifyjs in every\n // editor's onCreate, and linkifyjs accepts a scheme only before its first\n // scan — so each chat body or composer created after the first one logged\n // \"linkifyjs: already initialized\" (seen in Chrome's extension Errors\n // page). Screen points arrive as markdown links (`[label](athena-point://…)`),\n // which parse without linkify, and `isAllowedChatHref` already admits\n // the scheme; only autolinking a bare `athena-point://` string needed it.\n isAllowedUri: (url) => isAllowedChatHref(url),\n }),\n Image.configure({ inline: true }),\n ChatTableExtension.configure({ resizable: false }),\n TableRow,\n TableCell,\n TableHeader,\n TaskList,\n TaskItem.configure({ nested: true }),\n Markdown.configure({\n html: true,\n tightLists: true,\n tightListClass: \"tight\",\n bulletListMarker: \"-\",\n linkify: true,\n breaks: true,\n transformPastedText: true,\n transformCopiedText: false,\n }),\n ChatMentionExtension,\n ];\n}\n\n/** The slice of a markdown-it token {@link TypedTextReading} rewrites. */\ninterface MarkdownToken {\n type: string;\n tag: string;\n nesting: number;\n markup: string;\n content: string;\n children: MarkdownToken[] | null;\n}\n\n/** The slice of markdown-it (the instance tiptap-markdown parses with) {@link TypedTextReading} configures. */\ninterface MarkdownIt {\n disable(rules: string | string[], ignoreInvalid?: boolean): unknown;\n core: {\n ruler: {\n after(\n afterName: string,\n ruleName: string,\n rule: (state: { tokens: MarkdownToken[] }) => void,\n ): void;\n };\n };\n}\n\n/** A line break tag: the one piece of HTML a composer writes, for a line break inside a table cell. */\nconst LINE_BREAK_TAG = /^<br\\s*\\/?>$/i;\n\n/**\n * The inline token a typed reading shows as the characters it was written\n * with. Raw HTML counts only when it is in the text itself (`source`, the\n * inline block's own content): a task list's checkbox is HTML markdown-it's\n * task-list rule makes, not text anyone typed.\n */\nfunction isTypedCharacters(token: MarkdownToken, source: string, inTable: boolean): boolean {\n if (token.type === \"html_inline\") {\n return (\n source.includes(token.content) && !(inTable && LINE_BREAK_TAG.test(token.content.trim()))\n );\n }\n return (\n (token.type === \"em_open\" ||\n token.type === \"em_close\" ||\n token.type === \"strong_open\" ||\n token.type === \"strong_close\") &&\n token.markup.startsWith(\"_\")\n );\n}\n\nconst typedReadingInstalled = new WeakSet<object>();\n\nfunction installTypedTextReading(markdownit: MarkdownIt): void {\n if (typedReadingInstalled.has(markdownit)) return;\n typedReadingInstalled.add(markdownit);\n markdownit.disable(\"html_block\");\n markdownit.core.ruler.after(\"inline\", \"athena_typed_text\", (state) => {\n let tables = 0;\n for (const block of state.tokens) {\n if (block.type === \"table_open\") tables += 1;\n if (block.type === \"table_close\") tables -= 1;\n for (const token of block.children ?? []) {\n if (!isTypedCharacters(token, block.content, tables > 0)) continue;\n if (token.type !== \"html_inline\") token.content = token.markup;\n token.type = \"text\";\n token.tag = \"\";\n token.nesting = 0;\n }\n }\n });\n}\n\n/**\n * How a person's typed text reads in the user bubble: the chat's Markdown,\n * except for the two readings no composer send relies on and plain text often\n * trips. Raw HTML stays the characters it was typed with (`List<T>` keeps its\n * `<T>`, `a <b>c</b>` is not bold): a composer writes a typed `<` as `<`,\n * and its only tag is a `<br>` for a line break inside a table cell, which a\n * table cell still reads as one. Underscore emphasis stays underscores\n * (`obj.__init__` keeps them, `_private_` is not italic): a composer writes\n * emphasis with `*` and escapes a typed `_`. Everything a composer does write\n * (bold, lists, code, links, mention chips, tables, and the escaped Markdown\n * of older sends) reads as the assistant's reading reads it.\n */\nconst TypedTextReading = Extension.create({\n name: \"athenaTypedTextReading\",\n addStorage() {\n return {\n markdown: {\n parse: {\n setup: (markdownit: MarkdownIt) => installTypedTextReading(markdownit),\n },\n },\n };\n },\n});\n\nlet parserEditor: Editor | undefined;\nlet typedParserEditor: Editor | undefined;\n\nfunction parseWith(editor: Editor, markdown: string) {\n const html: string = getMarkdownStorage(editor).parser.parse(markdown);\n const body = new window.DOMParser().parseFromString(html, \"text/html\").body;\n normalizeCitationAnchors(body);\n return ProseMirrorDOMParser.fromSchema(editor.schema).parse(body);\n}\n\n/**\n * A single detached parser per browser tab, never an editor per message.\n * Markdown → HTML (markdown-it, with bare URLs linkified and inline HTML kept)\n * → agora's citation anchors given their hrefs → the schema's document.\n */\nexport function parseChatText(markdown: string) {\n parserEditor ??= new Editor({\n extensions: createChatTextExtensions(),\n content: \"\",\n editable: false,\n });\n return parseWith(parserEditor, markdown);\n}\n\n/**\n * {@link parseChatText} for text a person typed (a user message): the same\n * schema and document, read with {@link TypedTextReading}.\n */\nexport function parseTypedChatText(markdown: string) {\n typedParserEditor ??= new Editor({\n extensions: [...createChatTextExtensions(), TypedTextReading],\n content: \"\",\n editable: false,\n });\n return parseWith(typedParserEditor, markdown);\n}\n\n/** Typography is shared; the composer supplies only its padding and scroll boundary. */\nexport const CHAT_TEXT_CLASS =\n \"aui-md prose prose-sm max-w-none min-w-0 break-words text-sm leading-snug text-foreground prose-p:my-1.5 prose-p:leading-snug prose-headings:mt-3 prose-headings:mb-1.5 prose-headings:font-semibold prose-h1:text-sm prose-h2:text-sm prose-h3:text-xs prose-ul:my-1.5 prose-ol:my-1.5 prose-li:my-0.5 prose-blockquote:border-l-2 prose-blockquote:border-border prose-blockquote:text-muted-foreground prose-code:rounded prose-code:bg-muted prose-code:px-1 prose-code:py-0.5 prose-code:text-xs prose-code:font-mono prose-code:before:content-none prose-code:after:content-none prose-pre:my-2 prose-pre:overflow-x-auto prose-pre:rounded-lg prose-pre:border prose-pre:border-border prose-pre:bg-muted/30 prose-pre:p-3 prose-a:text-primary prose-a:underline prose-a:decoration-primary/40 prose-a:underline-offset-2 hover:prose-a:decoration-primary prose-strong:font-semibold prose-hr:border-border [&>:first-child]:mt-0 [&>:last-child]:mb-0 [&_table]:block [&_table]:overflow-x-auto [&_td]:border [&_td]:border-border [&_td]:px-2 [&_th]:border [&_th]:border-border [&_th]:px-2 [&_ul[data-type=taskList]]:list-none [&_ul[data-type=taskList]]:pl-0 [&_li[data-type=taskItem]]:flex [&_li[data-type=taskItem]]:gap-2\";\n"],"names":["MentionExtension","ReactNodeViewRenderer","ChatMentionNodeView","ChatCodeBlockNodeView","Table","markdownTableStorage","isAllowedChatHref","TableRow","TableCell","TableHeader","Markdown","Extension","getMarkdownStorage","normalizeCitationAnchors","ProseMirrorDOMParser","Editor"],"mappings":";;;;;;;;;;;;;;;;;;AAiBA,MAAM,uBAAuBA,iBAAAA,iBAAiB,OAAO;AAAA,EACnD,aAAa,MAAMC,MAAAA,sBAAsBC,cAAAA,qBAAqB,EAAE,IAAI,QAAQ;AAC9E,CAAC;AAEM,MAAM,yBAAyB,UAAU,OAAO;AAAA,EACrD,aAAa,MAAMD,MAAAA,sBAAsBE,cAAAA,qBAAqB;AAChE,CAAC;AAQM,MAAM,qBAAqBC,eAAAA,MAAM,OAAO;AAAA,EAC7C,aAAa;;AACX,WAAO,EAAE,IAAG,UAAK,WAAL,+BAAiB,GAAGC,wBAAAA,uBAAqB;AAAA,EACvD;AACF,CAAC;AAaM,MAAM,oBAAoB,KAAK,OAAO;AAAA,EAC3C,WAAW;AAAA,EAEX,gBAAgB;;AACd,WAAO;AAAA,MACL,IAAG,UAAK,WAAL;AAAA,MACH,SAAS;AAAA,QACP,SAAS;AAAA,QACT,WAAW,CAAC,YAAyB,QAAQ,aAAa,cAAc;AAAA,QACxE,YAAY,CAAC,eACX,OAAO,WAAW,YAAY,YAAY,WAAW,UACjD,EAAE,gBAAgB,WAAW,QAAA,IAC7B,CAAA;AAAA,MAAC;AAAA,IACT;AAAA,EAEJ;AACF,CAAC;AAGM,SAAS,2BAAuC;AACrD,SAAO;AAAA,IACL,WAAW,UAAU;AAAA,MACnB,WAAW;AAAA;AAAA,MAEX,MAAM;AAAA,MACN,WAAW;AAAA,MACX,YAAY;AAAA,MACZ,cAAc;AAAA,IAAA,CACf;AAAA,IACD;AAAA,IACA,kBAAkB,UAAU;AAAA,MAC1B,aAAa;AAAA,MACb,UAAU;AAAA,MACV,aAAa;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,MAQb,cAAc,CAAC,QAAQC,gBAAAA,kBAAkB,GAAG;AAAA,IAAA,CAC7C;AAAA,IACD,MAAM,UAAU,EAAE,QAAQ,MAAM;AAAA,IAChC,mBAAmB,UAAU,EAAE,WAAW,OAAO;AAAA,IACjDC,eAAAA;AAAAA,IACAC,eAAAA;AAAAA,IACAC,eAAAA;AAAAA,IACA;AAAA,IACA,SAAS,UAAU,EAAE,QAAQ,MAAM;AAAA,IACnCC,eAAAA,SAAS,UAAU;AAAA,MACjB,MAAM;AAAA,MACN,YAAY;AAAA,MACZ,gBAAgB;AAAA,MAChB,kBAAkB;AAAA,MAClB,SAAS;AAAA,MACT,QAAQ;AAAA,MACR,qBAAqB;AAAA,MACrB,qBAAqB;AAAA,IAAA,CACtB;AAAA,IACD;AAAA,EAAA;AAEJ;AA2BA,MAAM,iBAAiB;AAQvB,SAAS,kBAAkB,OAAsB,QAAgB,SAA2B;AAC1F,MAAI,MAAM,SAAS,eAAe;AAChC,WACE,OAAO,SAAS,MAAM,OAAO,KAAK,EAAE,WAAW,eAAe,KAAK,MAAM,QAAQ,KAAA,CAAM;AAAA,EAE3F;AACA,UACG,MAAM,SAAS,aACd,MAAM,SAAS,cACf,MAAM,SAAS,iBACf,MAAM,SAAS,mBACjB,MAAM,OAAO,WAAW,GAAG;AAE/B;AAEA,MAAM,4CAA4B,QAAA;AAElC,SAAS,wBAAwB,YAA8B;AAC7D,MAAI,sBAAsB,IAAI,UAAU,EAAG;AAC3C,wBAAsB,IAAI,UAAU;AACpC,aAAW,QAAQ,YAAY;AAC/B,aAAW,KAAK,MAAM,MAAM,UAAU,qBAAqB,CAAC,UAAU;AACpE,QAAI,SAAS;AACb,eAAW,SAAS,MAAM,QAAQ;AAChC,UAAI,MAAM,SAAS,aAAc,WAAU;AAC3C,UAAI,MAAM,SAAS,cAAe,WAAU;AAC5C,iBAAW,SAAS,MAAM,YAAY,CAAA,GAAI;AACxC,YAAI,CAAC,kBAAkB,OAAO,MAAM,SAAS,SAAS,CAAC,EAAG;AAC1D,YAAI,MAAM,SAAS,cAAe,OAAM,UAAU,MAAM;AACxD,cAAM,OAAO;AACb,cAAM,MAAM;AACZ,cAAM,UAAU;AAAA,MAClB;AAAA,IACF;AAAA,EACF,CAAC;AACH;AAcA,MAAM,mBAAmBC,KAAAA,UAAU,OAAO;AAAA,EACxC,MAAM;AAAA,EACN,aAAa;AACX,WAAO;AAAA,MACL,UAAU;AAAA,QACR,OAAO;AAAA,UACL,OAAO,CAAC,eAA2B,wBAAwB,UAAU;AAAA,QAAA;AAAA,MACvE;AAAA,IACF;AAAA,EAEJ;AACF,CAAC;AAED,IAAI;AACJ,IAAI;AAEJ,SAAS,UAAU,QAAgB,UAAkB;AACnD,QAAM,OAAeC,gBAAAA,mBAAmB,MAAM,EAAE,OAAO,MAAM,QAAQ;AACrE,QAAM,OAAO,IAAI,OAAO,UAAA,EAAY,gBAAgB,MAAM,WAAW,EAAE;AACvEC,kBAAAA,yBAAyB,IAAI;AAC7B,SAAOC,MAAAA,UAAqB,WAAW,OAAO,MAAM,EAAE,MAAM,IAAI;AAClE;AAOO,SAAS,cAAc,UAAkB;AAC9C,kCAAiB,IAAIC,KAAAA,OAAO;AAAA,IAC1B,YAAY,yBAAA;AAAA,IACZ,SAAS;AAAA,IACT,UAAU;AAAA,EAAA,CACX;AACD,SAAO,UAAU,cAAc,QAAQ;AACzC;AAMO,SAAS,mBAAmB,UAAkB;AACnD,4CAAsB,IAAIA,KAAAA,OAAO;AAAA,IAC/B,YAAY,CAAC,GAAG,yBAAA,GAA4B,gBAAgB;AAAA,IAC5D,SAAS;AAAA,IACT,UAAU;AAAA,EAAA,CACX;AACD,SAAO,UAAU,mBAAmB,QAAQ;AAC9C;AAGO,MAAM,kBACX;;;;;;;;"}
|
|
@@ -15,6 +15,9 @@ export declare const ChatTableExtension: import("@tiptap/core").Node<import("@ti
|
|
|
15
15
|
* protocol and app-relative Spaces paths pass; every other scheme
|
|
16
16
|
* (`javascript:`, `ftp:`, `data:`, protocol-relative `//host`) is dropped and
|
|
17
17
|
* its label kept as text. The same rule governs the composer's autolink.
|
|
18
|
+
*
|
|
19
|
+
* Not inclusive (Tiptap makes an autolinking Link inclusive), so text typed at
|
|
20
|
+
* a link's end, like the space after a pasted URL, stays outside the link.
|
|
18
21
|
*/
|
|
19
22
|
export declare const ChatLinkExtension: import("@tiptap/core").Mark<import("@tiptap/extension-link").LinkOptions, any>;
|
|
20
23
|
/** Both the editable draft and the static message body use this schema and parser. */
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"chat-text-schema.js","sources":["../../../src/chat-ui/rich-text/chat-text-schema.tsx"],"sourcesContent":["import { Editor, Extension, type Extensions } from \"@tiptap/core\";\nimport { DOMParser as ProseMirrorDOMParser } from \"@tiptap/pm/model\";\nimport StarterKit from \"@tiptap/starter-kit\";\nimport CodeBlock from \"@tiptap/extension-code-block\";\nimport { ReactNodeViewRenderer } from \"@tiptap/react\";\nimport Link from \"@tiptap/extension-link\";\nimport Image from \"@tiptap/extension-image\";\nimport { Table, TableCell, TableHeader, TableRow } from \"@tiptap/extension-table\";\nimport TaskList from \"@tiptap/extension-task-list\";\nimport TaskItem from \"@tiptap/extension-task-item\";\nimport { markdownTableStorage } from \"@athenaintel/tiptap-markdown-table\";\nimport { Markdown } from \"tiptap-markdown\";\nimport { getMarkdownStorage } from \"../markdown-storage\";\nimport { MentionExtension } from \"../mentions/mention-extension\";\nimport { ChatCodeBlockNodeView, ChatMentionNodeView } from \"./chat-node-views\";\nimport { isAllowedChatHref, normalizeCitationAnchors } from \"./citation-anchors\";\n\nconst ChatMentionExtension = MentionExtension.extend({\n addNodeView: () => ReactNodeViewRenderer(ChatMentionNodeView, { as: \"span\" }),\n});\n/** Fenced code rendered through `ChatCodeBlock` (language label + copy button). */\nexport const ChatCodeBlockExtension = CodeBlock.extend({\n addNodeView: () => ReactNodeViewRenderer(ChatCodeBlockNodeView),\n});\n\n/**\n * The table node, written to Markdown through the table writer Olympus's\n * editors share (`@athenaintel/tiptap-markdown-table`), which escapes a `|`\n * inside a cell as `\\|`, so a draft's table reaches the message with the cells\n * it was typed with.\n */\nexport const ChatTableExtension = Table.extend({\n addStorage() {\n return { ...this.parent?.(), ...markdownTableStorage() };\n },\n});\n\n/**\n * The Link mark with the excerpt a citation carries (`data-excerpt`, the\n * source chip's tooltip and scroll-to-text target) and an href allow-list\n * narrower than tiptap's default: `http(s):`, `mailto:`, the screen-point\n * protocol and app-relative Spaces paths pass; every other scheme\n * (`javascript:`, `ftp:`, `data:`, protocol-relative `//host`) is dropped and\n * its label kept as text. The same rule governs the composer's autolink.\n */\nexport const ChatLinkExtension = Link.extend({\n addAttributes() {\n return {\n ...this.parent?.(),\n excerpt: {\n default: null,\n parseHTML: (element: HTMLElement) => element.getAttribute(\"data-excerpt\"),\n renderHTML: (attributes: Record<string, unknown>) =>\n typeof attributes.excerpt === \"string\" && attributes.excerpt\n ? { \"data-excerpt\": attributes.excerpt }\n : {},\n },\n };\n },\n});\n\n/** Both the editable draft and the static message body use this schema and parser. */\nexport function createChatTextExtensions(): Extensions {\n return [\n StarterKit.configure({\n codeBlock: false,\n // Tiptap 3 StarterKit also bundles these; chat text registers its own link and never had the rest.\n link: false,\n underline: false,\n listKeymap: false,\n trailingNode: false,\n }),\n ChatCodeBlockExtension,\n ChatLinkExtension.configure({\n openOnClick: false,\n autolink: true,\n linkOnPaste: true,\n // No `protocols`: Tiptap's Link registers them with linkifyjs in every\n // editor's onCreate, and linkifyjs accepts a scheme only before its first\n // scan — so each chat body or composer created after the first one logged\n // \"linkifyjs: already initialized\" (seen in Chrome's extension Errors\n // page). Screen points arrive as markdown links (`[label](athena-point://…)`),\n // which parse without linkify, and `isAllowedChatHref` already admits\n // the scheme; only autolinking a bare `athena-point://` string needed it.\n isAllowedUri: (url) => isAllowedChatHref(url),\n }),\n Image.configure({ inline: true }),\n ChatTableExtension.configure({ resizable: false }),\n TableRow,\n TableCell,\n TableHeader,\n TaskList,\n TaskItem.configure({ nested: true }),\n Markdown.configure({\n html: true,\n tightLists: true,\n tightListClass: \"tight\",\n bulletListMarker: \"-\",\n linkify: true,\n breaks: true,\n transformPastedText: true,\n transformCopiedText: false,\n }),\n ChatMentionExtension,\n ];\n}\n\n/** The slice of a markdown-it token {@link TypedTextReading} rewrites. */\ninterface MarkdownToken {\n type: string;\n tag: string;\n nesting: number;\n markup: string;\n content: string;\n children: MarkdownToken[] | null;\n}\n\n/** The slice of markdown-it (the instance tiptap-markdown parses with) {@link TypedTextReading} configures. */\ninterface MarkdownIt {\n disable(rules: string | string[], ignoreInvalid?: boolean): unknown;\n core: {\n ruler: {\n after(\n afterName: string,\n ruleName: string,\n rule: (state: { tokens: MarkdownToken[] }) => void,\n ): void;\n };\n };\n}\n\n/** A line break tag: the one piece of HTML a composer writes, for a line break inside a table cell. */\nconst LINE_BREAK_TAG = /^<br\\s*\\/?>$/i;\n\n/**\n * The inline token a typed reading shows as the characters it was written\n * with. Raw HTML counts only when it is in the text itself (`source`, the\n * inline block's own content): a task list's checkbox is HTML markdown-it's\n * task-list rule makes, not text anyone typed.\n */\nfunction isTypedCharacters(token: MarkdownToken, source: string, inTable: boolean): boolean {\n if (token.type === \"html_inline\") {\n return (\n source.includes(token.content) && !(inTable && LINE_BREAK_TAG.test(token.content.trim()))\n );\n }\n return (\n (token.type === \"em_open\" ||\n token.type === \"em_close\" ||\n token.type === \"strong_open\" ||\n token.type === \"strong_close\") &&\n token.markup.startsWith(\"_\")\n );\n}\n\nconst typedReadingInstalled = new WeakSet<object>();\n\nfunction installTypedTextReading(markdownit: MarkdownIt): void {\n if (typedReadingInstalled.has(markdownit)) return;\n typedReadingInstalled.add(markdownit);\n markdownit.disable(\"html_block\");\n markdownit.core.ruler.after(\"inline\", \"athena_typed_text\", (state) => {\n let tables = 0;\n for (const block of state.tokens) {\n if (block.type === \"table_open\") tables += 1;\n if (block.type === \"table_close\") tables -= 1;\n for (const token of block.children ?? []) {\n if (!isTypedCharacters(token, block.content, tables > 0)) continue;\n if (token.type !== \"html_inline\") token.content = token.markup;\n token.type = \"text\";\n token.tag = \"\";\n token.nesting = 0;\n }\n }\n });\n}\n\n/**\n * How a person's typed text reads in the user bubble: the chat's Markdown,\n * except for the two readings no composer send relies on and plain text often\n * trips. Raw HTML stays the characters it was typed with (`List<T>` keeps its\n * `<T>`, `a <b>c</b>` is not bold): a composer writes a typed `<` as `<`,\n * and its only tag is a `<br>` for a line break inside a table cell, which a\n * table cell still reads as one. Underscore emphasis stays underscores\n * (`obj.__init__` keeps them, `_private_` is not italic): a composer writes\n * emphasis with `*` and escapes a typed `_`. Everything a composer does write\n * (bold, lists, code, links, mention chips, tables, and the escaped Markdown\n * of older sends) reads as the assistant's reading reads it.\n */\nconst TypedTextReading = Extension.create({\n name: \"athenaTypedTextReading\",\n addStorage() {\n return {\n markdown: {\n parse: {\n setup: (markdownit: MarkdownIt) => installTypedTextReading(markdownit),\n },\n },\n };\n },\n});\n\nlet parserEditor: Editor | undefined;\nlet typedParserEditor: Editor | undefined;\n\nfunction parseWith(editor: Editor, markdown: string) {\n const html: string = getMarkdownStorage(editor).parser.parse(markdown);\n const body = new window.DOMParser().parseFromString(html, \"text/html\").body;\n normalizeCitationAnchors(body);\n return ProseMirrorDOMParser.fromSchema(editor.schema).parse(body);\n}\n\n/**\n * A single detached parser per browser tab, never an editor per message.\n * Markdown → HTML (markdown-it, with bare URLs linkified and inline HTML kept)\n * → agora's citation anchors given their hrefs → the schema's document.\n */\nexport function parseChatText(markdown: string) {\n parserEditor ??= new Editor({\n extensions: createChatTextExtensions(),\n content: \"\",\n editable: false,\n });\n return parseWith(parserEditor, markdown);\n}\n\n/**\n * {@link parseChatText} for text a person typed (a user message): the same\n * schema and document, read with {@link TypedTextReading}.\n */\nexport function parseTypedChatText(markdown: string) {\n typedParserEditor ??= new Editor({\n extensions: [...createChatTextExtensions(), TypedTextReading],\n content: \"\",\n editable: false,\n });\n return parseWith(typedParserEditor, markdown);\n}\n\n/** Typography is shared; the composer supplies only its padding and scroll boundary. */\nexport const CHAT_TEXT_CLASS =\n \"aui-md prose prose-sm max-w-none min-w-0 break-words text-sm leading-snug text-foreground prose-p:my-1.5 prose-p:leading-snug prose-headings:mt-3 prose-headings:mb-1.5 prose-headings:font-semibold prose-h1:text-sm prose-h2:text-sm prose-h3:text-xs prose-ul:my-1.5 prose-ol:my-1.5 prose-li:my-0.5 prose-blockquote:border-l-2 prose-blockquote:border-border prose-blockquote:text-muted-foreground prose-code:rounded prose-code:bg-muted prose-code:px-1 prose-code:py-0.5 prose-code:text-xs prose-code:font-mono prose-code:before:content-none prose-code:after:content-none prose-pre:my-2 prose-pre:overflow-x-auto prose-pre:rounded-lg prose-pre:border prose-pre:border-border prose-pre:bg-muted/30 prose-pre:p-3 prose-a:text-primary prose-a:underline prose-a:decoration-primary/40 prose-a:underline-offset-2 hover:prose-a:decoration-primary prose-strong:font-semibold prose-hr:border-border [&>:first-child]:mt-0 [&>:last-child]:mb-0 [&_table]:block [&_table]:overflow-x-auto [&_td]:border [&_td]:border-border [&_td]:px-2 [&_th]:border [&_th]:border-border [&_th]:px-2 [&_ul[data-type=taskList]]:list-none [&_ul[data-type=taskList]]:pl-0 [&_li[data-type=taskItem]]:flex [&_li[data-type=taskItem]]:gap-2\";\n"],"names":["ProseMirrorDOMParser"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"chat-text-schema.js","sources":["../../../src/chat-ui/rich-text/chat-text-schema.tsx"],"sourcesContent":["import { Editor, Extension, type Extensions } from \"@tiptap/core\";\nimport { DOMParser as ProseMirrorDOMParser } from \"@tiptap/pm/model\";\nimport StarterKit from \"@tiptap/starter-kit\";\nimport CodeBlock from \"@tiptap/extension-code-block\";\nimport { ReactNodeViewRenderer } from \"@tiptap/react\";\nimport Link from \"@tiptap/extension-link\";\nimport Image from \"@tiptap/extension-image\";\nimport { Table, TableCell, TableHeader, TableRow } from \"@tiptap/extension-table\";\nimport TaskList from \"@tiptap/extension-task-list\";\nimport TaskItem from \"@tiptap/extension-task-item\";\nimport { markdownTableStorage } from \"@athenaintel/tiptap-markdown-table\";\nimport { Markdown } from \"tiptap-markdown\";\nimport { getMarkdownStorage } from \"../markdown-storage\";\nimport { MentionExtension } from \"../mentions/mention-extension\";\nimport { ChatCodeBlockNodeView, ChatMentionNodeView } from \"./chat-node-views\";\nimport { isAllowedChatHref, normalizeCitationAnchors } from \"./citation-anchors\";\n\nconst ChatMentionExtension = MentionExtension.extend({\n addNodeView: () => ReactNodeViewRenderer(ChatMentionNodeView, { as: \"span\" }),\n});\n/** Fenced code rendered through `ChatCodeBlock` (language label + copy button). */\nexport const ChatCodeBlockExtension = CodeBlock.extend({\n addNodeView: () => ReactNodeViewRenderer(ChatCodeBlockNodeView),\n});\n\n/**\n * The table node, written to Markdown through the table writer Olympus's\n * editors share (`@athenaintel/tiptap-markdown-table`), which escapes a `|`\n * inside a cell as `\\|`, so a draft's table reaches the message with the cells\n * it was typed with.\n */\nexport const ChatTableExtension = Table.extend({\n addStorage() {\n return { ...this.parent?.(), ...markdownTableStorage() };\n },\n});\n\n/**\n * The Link mark with the excerpt a citation carries (`data-excerpt`, the\n * source chip's tooltip and scroll-to-text target) and an href allow-list\n * narrower than tiptap's default: `http(s):`, `mailto:`, the screen-point\n * protocol and app-relative Spaces paths pass; every other scheme\n * (`javascript:`, `ftp:`, `data:`, protocol-relative `//host`) is dropped and\n * its label kept as text. The same rule governs the composer's autolink.\n *\n * Not inclusive (Tiptap makes an autolinking Link inclusive), so text typed at\n * a link's end, like the space after a pasted URL, stays outside the link.\n */\nexport const ChatLinkExtension = Link.extend({\n inclusive: false,\n\n addAttributes() {\n return {\n ...this.parent?.(),\n excerpt: {\n default: null,\n parseHTML: (element: HTMLElement) => element.getAttribute(\"data-excerpt\"),\n renderHTML: (attributes: Record<string, unknown>) =>\n typeof attributes.excerpt === \"string\" && attributes.excerpt\n ? { \"data-excerpt\": attributes.excerpt }\n : {},\n },\n };\n },\n});\n\n/** Both the editable draft and the static message body use this schema and parser. */\nexport function createChatTextExtensions(): Extensions {\n return [\n StarterKit.configure({\n codeBlock: false,\n // Tiptap 3 StarterKit also bundles these; chat text registers its own link and never had the rest.\n link: false,\n underline: false,\n listKeymap: false,\n trailingNode: false,\n }),\n ChatCodeBlockExtension,\n ChatLinkExtension.configure({\n openOnClick: false,\n autolink: true,\n linkOnPaste: true,\n // No `protocols`: Tiptap's Link registers them with linkifyjs in every\n // editor's onCreate, and linkifyjs accepts a scheme only before its first\n // scan — so each chat body or composer created after the first one logged\n // \"linkifyjs: already initialized\" (seen in Chrome's extension Errors\n // page). Screen points arrive as markdown links (`[label](athena-point://…)`),\n // which parse without linkify, and `isAllowedChatHref` already admits\n // the scheme; only autolinking a bare `athena-point://` string needed it.\n isAllowedUri: (url) => isAllowedChatHref(url),\n }),\n Image.configure({ inline: true }),\n ChatTableExtension.configure({ resizable: false }),\n TableRow,\n TableCell,\n TableHeader,\n TaskList,\n TaskItem.configure({ nested: true }),\n Markdown.configure({\n html: true,\n tightLists: true,\n tightListClass: \"tight\",\n bulletListMarker: \"-\",\n linkify: true,\n breaks: true,\n transformPastedText: true,\n transformCopiedText: false,\n }),\n ChatMentionExtension,\n ];\n}\n\n/** The slice of a markdown-it token {@link TypedTextReading} rewrites. */\ninterface MarkdownToken {\n type: string;\n tag: string;\n nesting: number;\n markup: string;\n content: string;\n children: MarkdownToken[] | null;\n}\n\n/** The slice of markdown-it (the instance tiptap-markdown parses with) {@link TypedTextReading} configures. */\ninterface MarkdownIt {\n disable(rules: string | string[], ignoreInvalid?: boolean): unknown;\n core: {\n ruler: {\n after(\n afterName: string,\n ruleName: string,\n rule: (state: { tokens: MarkdownToken[] }) => void,\n ): void;\n };\n };\n}\n\n/** A line break tag: the one piece of HTML a composer writes, for a line break inside a table cell. */\nconst LINE_BREAK_TAG = /^<br\\s*\\/?>$/i;\n\n/**\n * The inline token a typed reading shows as the characters it was written\n * with. Raw HTML counts only when it is in the text itself (`source`, the\n * inline block's own content): a task list's checkbox is HTML markdown-it's\n * task-list rule makes, not text anyone typed.\n */\nfunction isTypedCharacters(token: MarkdownToken, source: string, inTable: boolean): boolean {\n if (token.type === \"html_inline\") {\n return (\n source.includes(token.content) && !(inTable && LINE_BREAK_TAG.test(token.content.trim()))\n );\n }\n return (\n (token.type === \"em_open\" ||\n token.type === \"em_close\" ||\n token.type === \"strong_open\" ||\n token.type === \"strong_close\") &&\n token.markup.startsWith(\"_\")\n );\n}\n\nconst typedReadingInstalled = new WeakSet<object>();\n\nfunction installTypedTextReading(markdownit: MarkdownIt): void {\n if (typedReadingInstalled.has(markdownit)) return;\n typedReadingInstalled.add(markdownit);\n markdownit.disable(\"html_block\");\n markdownit.core.ruler.after(\"inline\", \"athena_typed_text\", (state) => {\n let tables = 0;\n for (const block of state.tokens) {\n if (block.type === \"table_open\") tables += 1;\n if (block.type === \"table_close\") tables -= 1;\n for (const token of block.children ?? []) {\n if (!isTypedCharacters(token, block.content, tables > 0)) continue;\n if (token.type !== \"html_inline\") token.content = token.markup;\n token.type = \"text\";\n token.tag = \"\";\n token.nesting = 0;\n }\n }\n });\n}\n\n/**\n * How a person's typed text reads in the user bubble: the chat's Markdown,\n * except for the two readings no composer send relies on and plain text often\n * trips. Raw HTML stays the characters it was typed with (`List<T>` keeps its\n * `<T>`, `a <b>c</b>` is not bold): a composer writes a typed `<` as `<`,\n * and its only tag is a `<br>` for a line break inside a table cell, which a\n * table cell still reads as one. Underscore emphasis stays underscores\n * (`obj.__init__` keeps them, `_private_` is not italic): a composer writes\n * emphasis with `*` and escapes a typed `_`. Everything a composer does write\n * (bold, lists, code, links, mention chips, tables, and the escaped Markdown\n * of older sends) reads as the assistant's reading reads it.\n */\nconst TypedTextReading = Extension.create({\n name: \"athenaTypedTextReading\",\n addStorage() {\n return {\n markdown: {\n parse: {\n setup: (markdownit: MarkdownIt) => installTypedTextReading(markdownit),\n },\n },\n };\n },\n});\n\nlet parserEditor: Editor | undefined;\nlet typedParserEditor: Editor | undefined;\n\nfunction parseWith(editor: Editor, markdown: string) {\n const html: string = getMarkdownStorage(editor).parser.parse(markdown);\n const body = new window.DOMParser().parseFromString(html, \"text/html\").body;\n normalizeCitationAnchors(body);\n return ProseMirrorDOMParser.fromSchema(editor.schema).parse(body);\n}\n\n/**\n * A single detached parser per browser tab, never an editor per message.\n * Markdown → HTML (markdown-it, with bare URLs linkified and inline HTML kept)\n * → agora's citation anchors given their hrefs → the schema's document.\n */\nexport function parseChatText(markdown: string) {\n parserEditor ??= new Editor({\n extensions: createChatTextExtensions(),\n content: \"\",\n editable: false,\n });\n return parseWith(parserEditor, markdown);\n}\n\n/**\n * {@link parseChatText} for text a person typed (a user message): the same\n * schema and document, read with {@link TypedTextReading}.\n */\nexport function parseTypedChatText(markdown: string) {\n typedParserEditor ??= new Editor({\n extensions: [...createChatTextExtensions(), TypedTextReading],\n content: \"\",\n editable: false,\n });\n return parseWith(typedParserEditor, markdown);\n}\n\n/** Typography is shared; the composer supplies only its padding and scroll boundary. */\nexport const CHAT_TEXT_CLASS =\n \"aui-md prose prose-sm max-w-none min-w-0 break-words text-sm leading-snug text-foreground prose-p:my-1.5 prose-p:leading-snug prose-headings:mt-3 prose-headings:mb-1.5 prose-headings:font-semibold prose-h1:text-sm prose-h2:text-sm prose-h3:text-xs prose-ul:my-1.5 prose-ol:my-1.5 prose-li:my-0.5 prose-blockquote:border-l-2 prose-blockquote:border-border prose-blockquote:text-muted-foreground prose-code:rounded prose-code:bg-muted prose-code:px-1 prose-code:py-0.5 prose-code:text-xs prose-code:font-mono prose-code:before:content-none prose-code:after:content-none prose-pre:my-2 prose-pre:overflow-x-auto prose-pre:rounded-lg prose-pre:border prose-pre:border-border prose-pre:bg-muted/30 prose-pre:p-3 prose-a:text-primary prose-a:underline prose-a:decoration-primary/40 prose-a:underline-offset-2 hover:prose-a:decoration-primary prose-strong:font-semibold prose-hr:border-border [&>:first-child]:mt-0 [&>:last-child]:mb-0 [&_table]:block [&_table]:overflow-x-auto [&_td]:border [&_td]:border-border [&_td]:px-2 [&_th]:border [&_th]:border-border [&_th]:px-2 [&_ul[data-type=taskList]]:list-none [&_ul[data-type=taskList]]:pl-0 [&_li[data-type=taskItem]]:flex [&_li[data-type=taskItem]]:gap-2\";\n"],"names":["ProseMirrorDOMParser"],"mappings":"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"}
|
|
@@ -14,6 +14,7 @@ const statewireContinueRun = require("./messages/statewire-continue-run.cjs");
|
|
|
14
14
|
const interrupts = require("../agent-runtime/src/interrupts.cjs");
|
|
15
15
|
exports.StatewireApprovalCard = StatewireApprovalCard.StatewireApprovalCard;
|
|
16
16
|
exports.useStatewireApprovalRequest = useStatewireApprovalRequest.useStatewireApprovalRequest;
|
|
17
|
+
exports.useStatewireApprovalWait = useStatewireApprovalRequest.useStatewireApprovalWait;
|
|
17
18
|
exports.RUN_START_REFUSAL_FALLBACK_MESSAGE = StatewireRunRefusalNotice.RUN_START_REFUSAL_FALLBACK_MESSAGE;
|
|
18
19
|
exports.StatewireRunRefusalNotice = StatewireRunRefusalNotice.StatewireRunRefusalNotice;
|
|
19
20
|
exports.StatewireQueuedMessages = StatewireQueuedMessages.StatewireQueuedMessages;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"statewire.cjs","sources":[],"sourcesContent":[],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"statewire.cjs","sources":[],"sourcesContent":[],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;"}
|
|
@@ -10,7 +10,7 @@
|
|
|
10
10
|
* Published as the `@athenaintel/react/chat-ui/statewire` sub-path.
|
|
11
11
|
*/
|
|
12
12
|
export { StatewireApprovalCard, type StatewireApprovalCardProps, type StatewireApprovalEditorContext, type StatewireApprovalRequestContext, } from "../chat/StatewireApprovalCard";
|
|
13
|
-
export { type StatewireApprovalRequest, type StatewireInterruptPredicate, type UseStatewireApprovalRequestOptions, useStatewireApprovalRequest, } from "../chat/use-statewire-approval-request";
|
|
13
|
+
export { type StatewireApprovalRequest, type StatewireApprovalWait, type StatewireInterruptPredicate, type UseStatewireApprovalRequestOptions, useStatewireApprovalRequest, useStatewireApprovalWait, } from "../chat/use-statewire-approval-request";
|
|
14
14
|
export { RUN_START_REFUSAL_FALLBACK_MESSAGE, StatewireRunRefusalNotice, type StatewireRunRefusalNoticeProps, } from "../chat/StatewireRunRefusalNotice";
|
|
15
15
|
export { StatewireQueuedMessages, type StatewireQueueEditorContext, type StatewireQueueEvent, type StatewireQueueRowContentContext, type StatewireQueueRowMarkerContext, type StatewireQueuedMessagesProps, } from "../chat/StatewireQueuedMessages";
|
|
16
16
|
export { HistoryEdgeRow, type HistoryEdgeRowProps, StatewireHistoryEdge, type StatewireHistoryEdgeProps, } from "./thread/statewire-history-edge";
|
|
@@ -20,4 +20,4 @@ export { RuntimeMessageCard, type RuntimeMessageCardProps } from "./messages/run
|
|
|
20
20
|
export { WakeMarkerCard, type WakeMarkerCardProps, WakeMarkerMessage, } from "./messages/wake-marker";
|
|
21
21
|
export { WaitingOnYouBanner, type WaitingOnYouBannerProps, WaitingOnYouBannerView, type WaitingOnYouBannerViewProps, } from "../chat/WaitingOnYouBanner";
|
|
22
22
|
export { type ReadStatewireTailEnding, StatewireContinueRunAffordance, StatewireContinueRunButton, type StatewireContinueRunButtonProps, StatewireRunEndedFooter, type StatewireRunEndedFooterActionsContext, type StatewireRunEndedFooterProps, type StatewireTailEnding, } from "./messages/statewire-continue-run";
|
|
23
|
-
export { HITL_PENDING_RESUME_GRACE_MS } from "
|
|
23
|
+
export { HITL_PENDING_RESUME_GRACE_MS } from "../agent-runtime/src/index";
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { StatewireApprovalCard } from "../chat/StatewireApprovalCard.js";
|
|
2
|
-
import { useStatewireApprovalRequest } from "../chat/use-statewire-approval-request.js";
|
|
2
|
+
import { useStatewireApprovalRequest, useStatewireApprovalWait } from "../chat/use-statewire-approval-request.js";
|
|
3
3
|
import { RUN_START_REFUSAL_FALLBACK_MESSAGE, StatewireRunRefusalNotice } from "../chat/StatewireRunRefusalNotice.js";
|
|
4
4
|
import { StatewireQueuedMessages } from "../chat/StatewireQueuedMessages.js";
|
|
5
5
|
import { HistoryEdgeRow, StatewireHistoryEdge } from "./thread/statewire-history-edge.js";
|
|
@@ -29,6 +29,7 @@ export {
|
|
|
29
29
|
WakeMarkerCard,
|
|
30
30
|
WakeMarkerMessage,
|
|
31
31
|
useStatewireApprovalRequest,
|
|
32
|
+
useStatewireApprovalWait,
|
|
32
33
|
useStatewireToolOutputs
|
|
33
34
|
};
|
|
34
35
|
//# sourceMappingURL=statewire.js.map
|
|
@@ -9,6 +9,7 @@ const messageComponents = require("../messages/message-components.cjs");
|
|
|
9
9
|
const ComposerSendOrStop = ({
|
|
10
10
|
composerRef,
|
|
11
11
|
hasDraft,
|
|
12
|
+
liveVoice = false,
|
|
12
13
|
disabled = false,
|
|
13
14
|
sendBlockedReason = null,
|
|
14
15
|
sendDisabledTitle,
|
|
@@ -24,7 +25,7 @@ const ComposerSendOrStop = ({
|
|
|
24
25
|
return ((_a = state.optional.thread) == null ? void 0 : _a.isRunning) ?? false;
|
|
25
26
|
}
|
|
26
27
|
);
|
|
27
|
-
const action = composerAction.resolveComposerAction({ hasDraft, isRunning });
|
|
28
|
+
const action = liveVoice && hasDraft ? "send" : composerAction.resolveComposerAction({ hasDraft, isRunning });
|
|
28
29
|
const SendButton = (components == null ? void 0 : components.SendButton) ?? messageComponents.ComposerSendButton;
|
|
29
30
|
const StopButton = (components == null ? void 0 : components.StopButton) ?? messageComponents.ComposerStopButton;
|
|
30
31
|
const cancelRun = react$1.useCallback(() => {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"composer-send-or-stop.cjs","sources":["../../../src/chat-ui/thread/composer-send-or-stop.tsx"],"sourcesContent":["import { athenaDiagnostics } from \"../../diagnostics/athena-diagnostics\";\nimport { useAui, useAuiState } from \"@assistant-ui/react\";\nimport type { FC, RefObject } from \"react\";\nimport { useCallback } from \"react\";\nimport {\n resolveComposerAction,\n type ComposerAction,\n} from \"../composer/composer-action\";\nimport {\n ComposerSendButton,\n ComposerStopButton,\n type ComposerSendButtonProps,\n type ComposerStopButtonProps,\n} from \"../messages/message-components\";\n\n/**\n * The slice of a composer handle this control needs: something whose draft\n * can be submitted. `TiptapComposerHandle` satisfies it; hosts with their own\n * editor plumbing (the SDK's AthenaChat) expose a compatible handle.\n */\nexport interface ComposerSubmitHandle {\n submit: () => void | Promise<void>;\n}\n\nexport interface ComposerStopControls {\n /**\n * Cancels the active run via the runtime. Returns false when cancellation\n * threw (e.g. the run already settled), so hosts can report whether their\n * own teardown still needs to stop backend work.\n */\n cancelRun: () => boolean;\n}\n\n/**\n * Control renderers, for hosts with their own published theming contract\n * (AthenaChat's `aui-*` class system). Defaults render the shared buttons.\n */\nexport interface ComposerSendOrStopComponents {\n SendButton?: FC<ComposerSendButtonProps>;\n StopButton?: FC<ComposerStopButtonProps>;\n}\n\nexport interface ComposerSendOrStopProps {\n composerRef: RefObject<ComposerSubmitHandle | null>;\n hasDraft: boolean;\n /** Disables both send and stop (e.g. while a conversation restores). */\n disabled?: boolean;\n /**\n * Blocks sending (not stopping) with this reason as the tooltip — e.g. a\n * broken host tunnel that would make tool calls silently fail.\n */\n sendBlockedReason?: string | null;\n /** Tooltip for the send/queue control while `disabled`. */\n sendDisabledTitle?: string;\n /** Tooltip for the stop control while `disabled`. */\n stopDisabledTitle?: string;\n /**\n * Host work to run before the draft submits (per-turn bookkeeping).\n * `action` distinguishes a fresh send from queueing into an active run.\n */\n onBeforeSend?: (context: {\n action: Extract<ComposerAction, \"send\" | \"queue\">;\n }) => void | Promise<void>;\n /**\n * Full custom stop sequence. Hosts that must tear down in-flight host-side\n * work sequence it around `controls.cancelRun()`. Default: cancel the run.\n */\n onStop?: (controls: ComposerStopControls) => void;\n components?: ComposerSendOrStopComponents;\n}\n\n/**\n * The shared send/queue/stop control: sends the composer draft, queues it as\n * a follow-up while a run is in flight, or stops the run when there is\n * nothing to queue.\n */\nexport const ComposerSendOrStop: FC<ComposerSendOrStopProps> = ({\n composerRef,\n hasDraft,\n disabled = false,\n sendBlockedReason = null,\n sendDisabledTitle,\n stopDisabledTitle,\n onBeforeSend,\n onStop,\n components,\n}) => {\n const aui = useAui();\n const isRunning = useAuiState(\n (state) => state.optional.thread?.isRunning ?? false,\n );\n const action = resolveComposerAction({ hasDraft, isRunning });\n const SendButton = components?.SendButton ?? ComposerSendButton;\n const StopButton = components?.StopButton ?? ComposerStopButton;\n\n const cancelRun = useCallback((): boolean => {\n try {\n aui.thread.cancelRun();\n return true;\n } catch (error) {\n athenaDiagnostics.emit(\"composer.cancel.error\", {\n level: \"warn\",\n data: { error: error instanceof Error ? error.message : String(error) },\n });\n return false;\n }\n }, [aui]);\n\n if (action === \"stop\") {\n return (\n <StopButton\n onStop={() => {\n if (onStop) {\n onStop({ cancelRun });\n } else {\n cancelRun();\n }\n }}\n disabled={disabled}\n title={disabled && stopDisabledTitle ? stopDisabledTitle : undefined}\n />\n );\n }\n\n const handleSend = async () => {\n await onBeforeSend?.({ action });\n await composerRef.current?.submit();\n };\n const sendTitle =\n disabled && sendDisabledTitle\n ? sendDisabledTitle\n : (sendBlockedReason ?? undefined);\n return (\n <SendButton\n action={action}\n onSend={() => void handleSend()}\n disabled={disabled || !hasDraft || sendBlockedReason != null}\n title={sendTitle}\n />\n );\n};\n"],"names":["useAui","useAuiState","resolveComposerAction","ComposerSendButton","ComposerStopButton","useCallback","athenaDiagnostics","jsx"],"mappings":";;;;;;;;
|
|
1
|
+
{"version":3,"file":"composer-send-or-stop.cjs","sources":["../../../src/chat-ui/thread/composer-send-or-stop.tsx"],"sourcesContent":["import { athenaDiagnostics } from \"../../diagnostics/athena-diagnostics\";\nimport { useAui, useAuiState } from \"@assistant-ui/react\";\nimport type { FC, RefObject } from \"react\";\nimport { useCallback } from \"react\";\nimport {\n resolveComposerAction,\n type ComposerAction,\n} from \"../composer/composer-action\";\nimport {\n ComposerSendButton,\n ComposerStopButton,\n type ComposerSendButtonProps,\n type ComposerStopButtonProps,\n} from \"../messages/message-components\";\n\n/**\n * The slice of a composer handle this control needs: something whose draft\n * can be submitted. `TiptapComposerHandle` satisfies it; hosts with their own\n * editor plumbing (the SDK's AthenaChat) expose a compatible handle.\n */\nexport interface ComposerSubmitHandle {\n submit: () => void | Promise<void>;\n}\n\nexport interface ComposerStopControls {\n /**\n * Cancels the active run via the runtime. Returns false when cancellation\n * threw (e.g. the run already settled), so hosts can report whether their\n * own teardown still needs to stop backend work.\n */\n cancelRun: () => boolean;\n}\n\n/**\n * Control renderers, for hosts with their own published theming contract\n * (AthenaChat's `aui-*` class system). Defaults render the shared buttons.\n */\nexport interface ComposerSendOrStopComponents {\n SendButton?: FC<ComposerSendButtonProps>;\n StopButton?: FC<ComposerStopButtonProps>;\n}\n\nexport interface ComposerSendOrStopProps {\n composerRef: RefObject<ComposerSubmitHandle | null>;\n hasDraft: boolean;\n /** A plain draft enters the live voice conversation instead of the run queue. */\n liveVoice?: boolean;\n /** Disables both send and stop (e.g. while a conversation restores). */\n disabled?: boolean;\n /**\n * Blocks sending (not stopping) with this reason as the tooltip — e.g. a\n * broken host tunnel that would make tool calls silently fail.\n */\n sendBlockedReason?: string | null;\n /** Tooltip for the send/queue control while `disabled`. */\n sendDisabledTitle?: string;\n /** Tooltip for the stop control while `disabled`. */\n stopDisabledTitle?: string;\n /**\n * Host work to run before the draft submits (per-turn bookkeeping).\n * `action` distinguishes a fresh send from queueing into an active run.\n */\n onBeforeSend?: (context: {\n action: Extract<ComposerAction, \"send\" | \"queue\">;\n }) => void | Promise<void>;\n /**\n * Full custom stop sequence. Hosts that must tear down in-flight host-side\n * work sequence it around `controls.cancelRun()`. Default: cancel the run.\n */\n onStop?: (controls: ComposerStopControls) => void;\n components?: ComposerSendOrStopComponents;\n}\n\n/**\n * The shared send/queue/stop control: sends the composer draft, queues it as\n * a follow-up while a run is in flight, or stops the run when there is\n * nothing to queue.\n */\nexport const ComposerSendOrStop: FC<ComposerSendOrStopProps> = ({\n composerRef,\n hasDraft,\n liveVoice = false,\n disabled = false,\n sendBlockedReason = null,\n sendDisabledTitle,\n stopDisabledTitle,\n onBeforeSend,\n onStop,\n components,\n}) => {\n const aui = useAui();\n const isRunning = useAuiState(\n (state) => state.optional.thread?.isRunning ?? false,\n );\n const action = liveVoice && hasDraft ? 'send' : resolveComposerAction({ hasDraft, isRunning });\n const SendButton = components?.SendButton ?? ComposerSendButton;\n const StopButton = components?.StopButton ?? ComposerStopButton;\n\n const cancelRun = useCallback((): boolean => {\n try {\n aui.thread.cancelRun();\n return true;\n } catch (error) {\n athenaDiagnostics.emit(\"composer.cancel.error\", {\n level: \"warn\",\n data: { error: error instanceof Error ? error.message : String(error) },\n });\n return false;\n }\n }, [aui]);\n\n if (action === \"stop\") {\n return (\n <StopButton\n onStop={() => {\n if (onStop) {\n onStop({ cancelRun });\n } else {\n cancelRun();\n }\n }}\n disabled={disabled}\n title={disabled && stopDisabledTitle ? stopDisabledTitle : undefined}\n />\n );\n }\n\n const handleSend = async () => {\n await onBeforeSend?.({ action });\n await composerRef.current?.submit();\n };\n const sendTitle =\n disabled && sendDisabledTitle\n ? sendDisabledTitle\n : (sendBlockedReason ?? undefined);\n return (\n <SendButton\n action={action}\n onSend={() => void handleSend()}\n disabled={disabled || !hasDraft || sendBlockedReason != null}\n title={sendTitle}\n />\n );\n};\n"],"names":["useAui","useAuiState","resolveComposerAction","ComposerSendButton","ComposerStopButton","useCallback","athenaDiagnostics","jsx"],"mappings":";;;;;;;;AA8EO,MAAM,qBAAkD,CAAC;AAAA,EAC9D;AAAA,EACA;AAAA,EACA,YAAY;AAAA,EACZ,WAAW;AAAA,EACX,oBAAoB;AAAA,EACpB;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AACF,MAAM;AACJ,QAAM,MAAMA,MAAAA,OAAA;AACZ,QAAM,YAAYC,MAAAA;AAAAA,IAChB,CAAC,UAAA;;AAAU,0BAAM,SAAS,WAAf,mBAAuB,cAAa;AAAA;AAAA,EAAA;AAEjD,QAAM,SAAS,aAAa,WAAW,SAASC,eAAAA,sBAAsB,EAAE,UAAU,WAAW;AAC7F,QAAM,cAAa,yCAAY,eAAcC,kBAAAA;AAC7C,QAAM,cAAa,yCAAY,eAAcC,kBAAAA;AAE7C,QAAM,YAAYC,QAAAA,YAAY,MAAe;AAC3C,QAAI;AACF,UAAI,OAAO,UAAA;AACX,aAAO;AAAA,IACT,SAAS,OAAO;AACdC,wBAAAA,kBAAkB,KAAK,yBAAyB;AAAA,QAC9C,OAAO;AAAA,QACP,MAAM,EAAE,OAAO,iBAAiB,QAAQ,MAAM,UAAU,OAAO,KAAK,EAAA;AAAA,MAAE,CACvE;AACD,aAAO;AAAA,IACT;AAAA,EACF,GAAG,CAAC,GAAG,CAAC;AAER,MAAI,WAAW,QAAQ;AACrB,WACEC,2BAAAA;AAAAA,MAAC;AAAA,MAAA;AAAA,QACC,QAAQ,MAAM;AACZ,cAAI,QAAQ;AACV,mBAAO,EAAE,WAAW;AAAA,UACtB,OAAO;AACL,sBAAA;AAAA,UACF;AAAA,QACF;AAAA,QACA;AAAA,QACA,OAAO,YAAY,oBAAoB,oBAAoB;AAAA,MAAA;AAAA,IAAA;AAAA,EAGjE;AAEA,QAAM,aAAa,YAAY;;AAC7B,WAAM,6CAAe,EAAE;AACvB,YAAM,iBAAY,YAAZ,mBAAqB;AAAA,EAC7B;AACA,QAAM,YACJ,YAAY,oBACR,oBACC,qBAAqB;AAC5B,SACEA,2BAAAA;AAAAA,IAAC;AAAA,IAAA;AAAA,MACC;AAAA,MACA,QAAQ,MAAM,KAAK,WAAA;AAAA,MACnB,UAAU,YAAY,CAAC,YAAY,qBAAqB;AAAA,MACxD,OAAO;AAAA,IAAA;AAAA,EAAA;AAGb;;"}
|
|
@@ -28,6 +28,8 @@ export interface ComposerSendOrStopComponents {
|
|
|
28
28
|
export interface ComposerSendOrStopProps {
|
|
29
29
|
composerRef: RefObject<ComposerSubmitHandle | null>;
|
|
30
30
|
hasDraft: boolean;
|
|
31
|
+
/** A plain draft enters the live voice conversation instead of the run queue. */
|
|
32
|
+
liveVoice?: boolean;
|
|
31
33
|
/** Disables both send and stop (e.g. while a conversation restores). */
|
|
32
34
|
disabled?: boolean;
|
|
33
35
|
/**
|
|
@@ -7,6 +7,7 @@ import { ComposerSendButton, ComposerStopButton } from "../messages/message-comp
|
|
|
7
7
|
const ComposerSendOrStop = ({
|
|
8
8
|
composerRef,
|
|
9
9
|
hasDraft,
|
|
10
|
+
liveVoice = false,
|
|
10
11
|
disabled = false,
|
|
11
12
|
sendBlockedReason = null,
|
|
12
13
|
sendDisabledTitle,
|
|
@@ -22,7 +23,7 @@ const ComposerSendOrStop = ({
|
|
|
22
23
|
return ((_a = state.optional.thread) == null ? void 0 : _a.isRunning) ?? false;
|
|
23
24
|
}
|
|
24
25
|
);
|
|
25
|
-
const action = resolveComposerAction({ hasDraft, isRunning });
|
|
26
|
+
const action = liveVoice && hasDraft ? "send" : resolveComposerAction({ hasDraft, isRunning });
|
|
26
27
|
const SendButton = (components == null ? void 0 : components.SendButton) ?? ComposerSendButton;
|
|
27
28
|
const StopButton = (components == null ? void 0 : components.StopButton) ?? ComposerStopButton;
|
|
28
29
|
const cancelRun = useCallback(() => {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"composer-send-or-stop.js","sources":["../../../src/chat-ui/thread/composer-send-or-stop.tsx"],"sourcesContent":["import { athenaDiagnostics } from \"../../diagnostics/athena-diagnostics\";\nimport { useAui, useAuiState } from \"@assistant-ui/react\";\nimport type { FC, RefObject } from \"react\";\nimport { useCallback } from \"react\";\nimport {\n resolveComposerAction,\n type ComposerAction,\n} from \"../composer/composer-action\";\nimport {\n ComposerSendButton,\n ComposerStopButton,\n type ComposerSendButtonProps,\n type ComposerStopButtonProps,\n} from \"../messages/message-components\";\n\n/**\n * The slice of a composer handle this control needs: something whose draft\n * can be submitted. `TiptapComposerHandle` satisfies it; hosts with their own\n * editor plumbing (the SDK's AthenaChat) expose a compatible handle.\n */\nexport interface ComposerSubmitHandle {\n submit: () => void | Promise<void>;\n}\n\nexport interface ComposerStopControls {\n /**\n * Cancels the active run via the runtime. Returns false when cancellation\n * threw (e.g. the run already settled), so hosts can report whether their\n * own teardown still needs to stop backend work.\n */\n cancelRun: () => boolean;\n}\n\n/**\n * Control renderers, for hosts with their own published theming contract\n * (AthenaChat's `aui-*` class system). Defaults render the shared buttons.\n */\nexport interface ComposerSendOrStopComponents {\n SendButton?: FC<ComposerSendButtonProps>;\n StopButton?: FC<ComposerStopButtonProps>;\n}\n\nexport interface ComposerSendOrStopProps {\n composerRef: RefObject<ComposerSubmitHandle | null>;\n hasDraft: boolean;\n /** Disables both send and stop (e.g. while a conversation restores). */\n disabled?: boolean;\n /**\n * Blocks sending (not stopping) with this reason as the tooltip — e.g. a\n * broken host tunnel that would make tool calls silently fail.\n */\n sendBlockedReason?: string | null;\n /** Tooltip for the send/queue control while `disabled`. */\n sendDisabledTitle?: string;\n /** Tooltip for the stop control while `disabled`. */\n stopDisabledTitle?: string;\n /**\n * Host work to run before the draft submits (per-turn bookkeeping).\n * `action` distinguishes a fresh send from queueing into an active run.\n */\n onBeforeSend?: (context: {\n action: Extract<ComposerAction, \"send\" | \"queue\">;\n }) => void | Promise<void>;\n /**\n * Full custom stop sequence. Hosts that must tear down in-flight host-side\n * work sequence it around `controls.cancelRun()`. Default: cancel the run.\n */\n onStop?: (controls: ComposerStopControls) => void;\n components?: ComposerSendOrStopComponents;\n}\n\n/**\n * The shared send/queue/stop control: sends the composer draft, queues it as\n * a follow-up while a run is in flight, or stops the run when there is\n * nothing to queue.\n */\nexport const ComposerSendOrStop: FC<ComposerSendOrStopProps> = ({\n composerRef,\n hasDraft,\n disabled = false,\n sendBlockedReason = null,\n sendDisabledTitle,\n stopDisabledTitle,\n onBeforeSend,\n onStop,\n components,\n}) => {\n const aui = useAui();\n const isRunning = useAuiState(\n (state) => state.optional.thread?.isRunning ?? false,\n );\n const action = resolveComposerAction({ hasDraft, isRunning });\n const SendButton = components?.SendButton ?? ComposerSendButton;\n const StopButton = components?.StopButton ?? ComposerStopButton;\n\n const cancelRun = useCallback((): boolean => {\n try {\n aui.thread.cancelRun();\n return true;\n } catch (error) {\n athenaDiagnostics.emit(\"composer.cancel.error\", {\n level: \"warn\",\n data: { error: error instanceof Error ? error.message : String(error) },\n });\n return false;\n }\n }, [aui]);\n\n if (action === \"stop\") {\n return (\n <StopButton\n onStop={() => {\n if (onStop) {\n onStop({ cancelRun });\n } else {\n cancelRun();\n }\n }}\n disabled={disabled}\n title={disabled && stopDisabledTitle ? stopDisabledTitle : undefined}\n />\n );\n }\n\n const handleSend = async () => {\n await onBeforeSend?.({ action });\n await composerRef.current?.submit();\n };\n const sendTitle =\n disabled && sendDisabledTitle\n ? sendDisabledTitle\n : (sendBlockedReason ?? undefined);\n return (\n <SendButton\n action={action}\n onSend={() => void handleSend()}\n disabled={disabled || !hasDraft || sendBlockedReason != null}\n title={sendTitle}\n />\n );\n};\n"],"names":[],"mappings":";;;;;;
|
|
1
|
+
{"version":3,"file":"composer-send-or-stop.js","sources":["../../../src/chat-ui/thread/composer-send-or-stop.tsx"],"sourcesContent":["import { athenaDiagnostics } from \"../../diagnostics/athena-diagnostics\";\nimport { useAui, useAuiState } from \"@assistant-ui/react\";\nimport type { FC, RefObject } from \"react\";\nimport { useCallback } from \"react\";\nimport {\n resolveComposerAction,\n type ComposerAction,\n} from \"../composer/composer-action\";\nimport {\n ComposerSendButton,\n ComposerStopButton,\n type ComposerSendButtonProps,\n type ComposerStopButtonProps,\n} from \"../messages/message-components\";\n\n/**\n * The slice of a composer handle this control needs: something whose draft\n * can be submitted. `TiptapComposerHandle` satisfies it; hosts with their own\n * editor plumbing (the SDK's AthenaChat) expose a compatible handle.\n */\nexport interface ComposerSubmitHandle {\n submit: () => void | Promise<void>;\n}\n\nexport interface ComposerStopControls {\n /**\n * Cancels the active run via the runtime. Returns false when cancellation\n * threw (e.g. the run already settled), so hosts can report whether their\n * own teardown still needs to stop backend work.\n */\n cancelRun: () => boolean;\n}\n\n/**\n * Control renderers, for hosts with their own published theming contract\n * (AthenaChat's `aui-*` class system). Defaults render the shared buttons.\n */\nexport interface ComposerSendOrStopComponents {\n SendButton?: FC<ComposerSendButtonProps>;\n StopButton?: FC<ComposerStopButtonProps>;\n}\n\nexport interface ComposerSendOrStopProps {\n composerRef: RefObject<ComposerSubmitHandle | null>;\n hasDraft: boolean;\n /** A plain draft enters the live voice conversation instead of the run queue. */\n liveVoice?: boolean;\n /** Disables both send and stop (e.g. while a conversation restores). */\n disabled?: boolean;\n /**\n * Blocks sending (not stopping) with this reason as the tooltip — e.g. a\n * broken host tunnel that would make tool calls silently fail.\n */\n sendBlockedReason?: string | null;\n /** Tooltip for the send/queue control while `disabled`. */\n sendDisabledTitle?: string;\n /** Tooltip for the stop control while `disabled`. */\n stopDisabledTitle?: string;\n /**\n * Host work to run before the draft submits (per-turn bookkeeping).\n * `action` distinguishes a fresh send from queueing into an active run.\n */\n onBeforeSend?: (context: {\n action: Extract<ComposerAction, \"send\" | \"queue\">;\n }) => void | Promise<void>;\n /**\n * Full custom stop sequence. Hosts that must tear down in-flight host-side\n * work sequence it around `controls.cancelRun()`. Default: cancel the run.\n */\n onStop?: (controls: ComposerStopControls) => void;\n components?: ComposerSendOrStopComponents;\n}\n\n/**\n * The shared send/queue/stop control: sends the composer draft, queues it as\n * a follow-up while a run is in flight, or stops the run when there is\n * nothing to queue.\n */\nexport const ComposerSendOrStop: FC<ComposerSendOrStopProps> = ({\n composerRef,\n hasDraft,\n liveVoice = false,\n disabled = false,\n sendBlockedReason = null,\n sendDisabledTitle,\n stopDisabledTitle,\n onBeforeSend,\n onStop,\n components,\n}) => {\n const aui = useAui();\n const isRunning = useAuiState(\n (state) => state.optional.thread?.isRunning ?? false,\n );\n const action = liveVoice && hasDraft ? 'send' : resolveComposerAction({ hasDraft, isRunning });\n const SendButton = components?.SendButton ?? ComposerSendButton;\n const StopButton = components?.StopButton ?? ComposerStopButton;\n\n const cancelRun = useCallback((): boolean => {\n try {\n aui.thread.cancelRun();\n return true;\n } catch (error) {\n athenaDiagnostics.emit(\"composer.cancel.error\", {\n level: \"warn\",\n data: { error: error instanceof Error ? error.message : String(error) },\n });\n return false;\n }\n }, [aui]);\n\n if (action === \"stop\") {\n return (\n <StopButton\n onStop={() => {\n if (onStop) {\n onStop({ cancelRun });\n } else {\n cancelRun();\n }\n }}\n disabled={disabled}\n title={disabled && stopDisabledTitle ? stopDisabledTitle : undefined}\n />\n );\n }\n\n const handleSend = async () => {\n await onBeforeSend?.({ action });\n await composerRef.current?.submit();\n };\n const sendTitle =\n disabled && sendDisabledTitle\n ? sendDisabledTitle\n : (sendBlockedReason ?? undefined);\n return (\n <SendButton\n action={action}\n onSend={() => void handleSend()}\n disabled={disabled || !hasDraft || sendBlockedReason != null}\n title={sendTitle}\n />\n );\n};\n"],"names":[],"mappings":";;;;;;AA8EO,MAAM,qBAAkD,CAAC;AAAA,EAC9D;AAAA,EACA;AAAA,EACA,YAAY;AAAA,EACZ,WAAW;AAAA,EACX,oBAAoB;AAAA,EACpB;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AACF,MAAM;AACJ,QAAM,MAAM,OAAA;AACZ,QAAM,YAAY;AAAA,IAChB,CAAC,UAAA;;AAAU,0BAAM,SAAS,WAAf,mBAAuB,cAAa;AAAA;AAAA,EAAA;AAEjD,QAAM,SAAS,aAAa,WAAW,SAAS,sBAAsB,EAAE,UAAU,WAAW;AAC7F,QAAM,cAAa,yCAAY,eAAc;AAC7C,QAAM,cAAa,yCAAY,eAAc;AAE7C,QAAM,YAAY,YAAY,MAAe;AAC3C,QAAI;AACF,UAAI,OAAO,UAAA;AACX,aAAO;AAAA,IACT,SAAS,OAAO;AACd,wBAAkB,KAAK,yBAAyB;AAAA,QAC9C,OAAO;AAAA,QACP,MAAM,EAAE,OAAO,iBAAiB,QAAQ,MAAM,UAAU,OAAO,KAAK,EAAA;AAAA,MAAE,CACvE;AACD,aAAO;AAAA,IACT;AAAA,EACF,GAAG,CAAC,GAAG,CAAC;AAER,MAAI,WAAW,QAAQ;AACrB,WACE;AAAA,MAAC;AAAA,MAAA;AAAA,QACC,QAAQ,MAAM;AACZ,cAAI,QAAQ;AACV,mBAAO,EAAE,WAAW;AAAA,UACtB,OAAO;AACL,sBAAA;AAAA,UACF;AAAA,QACF;AAAA,QACA;AAAA,QACA,OAAO,YAAY,oBAAoB,oBAAoB;AAAA,MAAA;AAAA,IAAA;AAAA,EAGjE;AAEA,QAAM,aAAa,YAAY;;AAC7B,WAAM,6CAAe,EAAE;AACvB,YAAM,iBAAY,YAAZ,mBAAqB;AAAA,EAC7B;AACA,QAAM,YACJ,YAAY,oBACR,oBACC,qBAAqB;AAC5B,SACE;AAAA,IAAC;AAAA,IAAA;AAAA,MACC;AAAA,MACA,QAAQ,MAAM,KAAK,WAAA;AAAA,MACnB,UAAU,YAAY,CAAC,YAAY,qBAAqB;AAAA,MACxD,OAAO;AAAA,IAAA;AAAA,EAAA;AAGb;"}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { type DeepAgentHistoryLoadEvent, type DeepAgentToolOutputStore } from "
|
|
1
|
+
import { type DeepAgentHistoryLoadEvent, type DeepAgentToolOutputStore } from "../../agent-runtime/src/index";
|
|
2
2
|
import type { FC } from "react";
|
|
3
3
|
/** The attribute `ChatThreadShell` stamps on the scroll viewport. */
|
|
4
4
|
export declare const THREAD_VIEWPORT_ATTR = "data-aui-thread-viewport";
|
|
@@ -7,7 +7,7 @@ const vanilla = require("zustand/vanilla");
|
|
|
7
7
|
const athenaUrls = require("../lib/athena-urls.cjs");
|
|
8
8
|
const AttachmentCtx = react.createContext(null);
|
|
9
9
|
function createAttachmentStore() {
|
|
10
|
-
return vanilla.createStore(() => ({ attachments: [], isUploading: false }));
|
|
10
|
+
return vanilla.createStore(() => ({ attachments: [], isUploading: false, notice: null }));
|
|
11
11
|
}
|
|
12
12
|
function AttachmentProvider({
|
|
13
13
|
children,
|
|
@@ -28,6 +28,7 @@ function StoreAttachmentProvider({
|
|
|
28
28
|
}) {
|
|
29
29
|
const attachments = zustand.useStore(store, (state) => state.attachments);
|
|
30
30
|
const isUploading = zustand.useStore(store, (state) => state.isUploading);
|
|
31
|
+
const notice = zustand.useStore(store, (state) => state.notice ?? null);
|
|
31
32
|
const actions = react.useMemo(
|
|
32
33
|
() => ({
|
|
33
34
|
addAttachments: (assets) => store.setState((state) => ({ attachments: [...state.attachments, ...assets] })),
|
|
@@ -35,13 +36,16 @@ function StoreAttachmentProvider({
|
|
|
35
36
|
attachments: state.attachments.filter((attachment) => attachment.id !== id)
|
|
36
37
|
})),
|
|
37
38
|
clearAttachments: () => store.setState({ attachments: [] }),
|
|
38
|
-
setIsUploading: (uploading) => store.setState({ isUploading: uploading })
|
|
39
|
+
setIsUploading: (uploading) => store.setState({ isUploading: uploading }),
|
|
40
|
+
setNotice: (next) => {
|
|
41
|
+
if ((store.getState().notice ?? null) !== next) store.setState({ notice: next });
|
|
42
|
+
}
|
|
39
43
|
}),
|
|
40
44
|
[store]
|
|
41
45
|
);
|
|
42
46
|
const value = react.useMemo(
|
|
43
|
-
() => ({ attachments, isUploading, ...actions }),
|
|
44
|
-
[attachments, isUploading, actions]
|
|
47
|
+
() => ({ attachments, isUploading, notice, ...actions }),
|
|
48
|
+
[attachments, isUploading, notice, actions]
|
|
45
49
|
);
|
|
46
50
|
return /* @__PURE__ */ jsxRuntime.jsx(AttachmentCtx.Provider, { value, children });
|
|
47
51
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"AttachmentContext.cjs","sources":["../../src/composer/AttachmentContext.tsx"],"sourcesContent":["import { createContext, useContext, useMemo, useState, type ReactNode } from 'react';\nimport { useStore } from 'zustand';\nimport { createStore, type StoreApi } from 'zustand/vanilla';\nimport { createAthenaSpacesUrl, DEFAULT_APP_URL } from '../lib/athena-urls';\nimport type { UploadedAsset } from './useFileUpload';\n\ninterface AttachmentContextValue {\n attachments: UploadedAsset[];\n addAttachments: (assets: UploadedAsset[]) => void;\n removeAttachment: (id: string) => void;\n clearAttachments: () => void;\n /** True when one or more files are currently being uploaded. */\n isUploading: boolean;\n setIsUploading: (v: boolean) => void;\n}\n\nconst AttachmentCtx = createContext<AttachmentContextValue | null>(null);\n\ninterface AttachmentStoreState {\n attachments: UploadedAsset[];\n isUploading: boolean;\n}\n\n/**\n * A composer's staged attachments, kept outside React (`createAttachmentStore`):\n * a host that shows several chats gives each its own, and keeps it while that\n * chat's `AthenaChat` remounts (a tab moving between windows).\n */\nexport type AttachmentStore = StoreApi<AttachmentStoreState>;\n\n/** An empty `AttachmentStore`, for `<AttachmentProvider store>`. */\nexport function createAttachmentStore(): AttachmentStore {\n return createStore<AttachmentStoreState>(() => ({ attachments: [], isUploading: false }));\n}\n\n/**\n * Staged attachments for the composer. With a `store`, they are that store's,\n * whatever is mounted above: one per chat when a host shows several. Without\n * one, a provider already mounted above (a host's, outliving a remounting\n * \\`AthenaChat\\` such as a tab moving between windows) is reused instead of\n * starting empty.\n */\nexport function AttachmentProvider({\n children,\n store,\n}: {\n children: ReactNode;\n store?: AttachmentStore;\n}) {\n const outer = useContext(AttachmentCtx);\n if (store) return <StoreAttachmentProvider store={store}>{children}</StoreAttachmentProvider>;\n if (outer) return <>{children}</>;\n return <OwnAttachmentProvider>{children}</OwnAttachmentProvider>;\n}\n\nfunction OwnAttachmentProvider({ children }: { children: ReactNode }) {\n const [store] = useState(createAttachmentStore);\n return <StoreAttachmentProvider store={store}>{children}</StoreAttachmentProvider>;\n}\n\nfunction StoreAttachmentProvider({\n children,\n store,\n}: {\n children: ReactNode;\n store: AttachmentStore;\n}) {\n const attachments = useStore(store, (state) => state.attachments);\n const isUploading = useStore(store, (state) => state.isUploading);\n const actions = useMemo(\n () => ({\n addAttachments: (assets: UploadedAsset[]) =>\n store.setState((state) => ({ attachments: [...state.attachments, ...assets] })),\n removeAttachment: (id: string) =>\n store.setState((state) => ({\n attachments: state.attachments.filter((attachment) => attachment.id !== id),\n })),\n clearAttachments: () => store.setState({ attachments: [] }),\n setIsUploading: (uploading: boolean) => store.setState({ isUploading: uploading }),\n }),\n [store],\n );\n const value = useMemo(\n () => ({ attachments, isUploading, ...actions }),\n [attachments, isUploading, actions],\n );\n\n return (\n <AttachmentCtx.Provider value={value}>\n {children}\n </AttachmentCtx.Provider>\n );\n}\n\nexport function useAttachments(): AttachmentContextValue {\n const ctx = useContext(AttachmentCtx);\n if (!ctx) {\n throw new Error('[AthenaSDK] useAttachments must be used within <AttachmentProvider>');\n }\n return ctx;\n}\n\n/**\n * Build the markdown references for the current attachments.\n * Returns empty string if no attachments.\n *\n * @deprecated Use `buildAttachmentMarkdownWithAppUrl` to avoid defaulting links to the production Athena app URL.\n */\nexport function buildAttachmentMarkdown(attachments: UploadedAsset[]): string {\n return buildAttachmentMarkdownWithAppUrl({ attachments });\n}\n\nexport function buildAttachmentMarkdownWithAppUrl({\n attachments,\n appUrl = DEFAULT_APP_URL,\n}: {\n attachments: UploadedAsset[];\n appUrl?: string;\n}): string {\n if (attachments.length === 0) return '';\n return attachments\n .map((attachment) => `[@${attachment.title}](${createAthenaSpacesUrl({ appUrl, assetIds: attachment.id })})`)\n .join('\\n');\n}\n"],"names":["createContext","createStore","useContext","jsx","Fragment","useState","useStore","useMemo","DEFAULT_APP_URL","createAthenaSpacesUrl"],"mappings":";;;;;;;
|
|
1
|
+
{"version":3,"file":"AttachmentContext.cjs","sources":["../../src/composer/AttachmentContext.tsx"],"sourcesContent":["import { createContext, useContext, useMemo, useState, type ReactNode } from 'react';\nimport { useStore } from 'zustand';\nimport { createStore, type StoreApi } from 'zustand/vanilla';\nimport { createAthenaSpacesUrl, DEFAULT_APP_URL } from '../lib/athena-urls';\nimport type { UploadedAsset } from './useFileUpload';\n\ninterface AttachmentContextValue {\n attachments: UploadedAsset[];\n addAttachments: (assets: UploadedAsset[]) => void;\n removeAttachment: (id: string) => void;\n clearAttachments: () => void;\n /** True when one or more files are currently being uploaded. */\n isUploading: boolean;\n setIsUploading: (v: boolean) => void;\n /**\n * Why the last files offered were not attached, for the composer to say (a file picked while\n * Athena can't be reached cannot upload), or `null`.\n */\n notice: string | null;\n setNotice: (notice: string | null) => void;\n}\n\nconst AttachmentCtx = createContext<AttachmentContextValue | null>(null);\n\ninterface AttachmentStoreState {\n attachments: UploadedAsset[];\n isUploading: boolean;\n notice?: string | null;\n}\n\n/**\n * A composer's staged attachments, kept outside React (`createAttachmentStore`):\n * a host that shows several chats gives each its own, and keeps it while that\n * chat's `AthenaChat` remounts (a tab moving between windows).\n */\nexport type AttachmentStore = StoreApi<AttachmentStoreState>;\n\n/** An empty `AttachmentStore`, for `<AttachmentProvider store>`. */\nexport function createAttachmentStore(): AttachmentStore {\n return createStore<AttachmentStoreState>(() => ({ attachments: [], isUploading: false, notice: null }));\n}\n\n/**\n * Staged attachments for the composer. With a `store`, they are that store's,\n * whatever is mounted above: one per chat when a host shows several. Without\n * one, a provider already mounted above (a host's, outliving a remounting\n * \\`AthenaChat\\` such as a tab moving between windows) is reused instead of\n * starting empty.\n */\nexport function AttachmentProvider({\n children,\n store,\n}: {\n children: ReactNode;\n store?: AttachmentStore;\n}) {\n const outer = useContext(AttachmentCtx);\n if (store) return <StoreAttachmentProvider store={store}>{children}</StoreAttachmentProvider>;\n if (outer) return <>{children}</>;\n return <OwnAttachmentProvider>{children}</OwnAttachmentProvider>;\n}\n\nfunction OwnAttachmentProvider({ children }: { children: ReactNode }) {\n const [store] = useState(createAttachmentStore);\n return <StoreAttachmentProvider store={store}>{children}</StoreAttachmentProvider>;\n}\n\nfunction StoreAttachmentProvider({\n children,\n store,\n}: {\n children: ReactNode;\n store: AttachmentStore;\n}) {\n const attachments = useStore(store, (state) => state.attachments);\n const isUploading = useStore(store, (state) => state.isUploading);\n const notice = useStore(store, (state) => state.notice ?? null);\n const actions = useMemo(\n () => ({\n addAttachments: (assets: UploadedAsset[]) =>\n store.setState((state) => ({ attachments: [...state.attachments, ...assets] })),\n removeAttachment: (id: string) =>\n store.setState((state) => ({\n attachments: state.attachments.filter((attachment) => attachment.id !== id),\n })),\n clearAttachments: () => store.setState({ attachments: [] }),\n setIsUploading: (uploading: boolean) => store.setState({ isUploading: uploading }),\n setNotice: (next: string | null) => {\n if ((store.getState().notice ?? null) !== next) store.setState({ notice: next });\n },\n }),\n [store],\n );\n const value = useMemo(\n () => ({ attachments, isUploading, notice, ...actions }),\n [attachments, isUploading, notice, actions],\n );\n\n return (\n <AttachmentCtx.Provider value={value}>\n {children}\n </AttachmentCtx.Provider>\n );\n}\n\nexport function useAttachments(): AttachmentContextValue {\n const ctx = useContext(AttachmentCtx);\n if (!ctx) {\n throw new Error('[AthenaSDK] useAttachments must be used within <AttachmentProvider>');\n }\n return ctx;\n}\n\n/**\n * Build the markdown references for the current attachments.\n * Returns empty string if no attachments.\n *\n * @deprecated Use `buildAttachmentMarkdownWithAppUrl` to avoid defaulting links to the production Athena app URL.\n */\nexport function buildAttachmentMarkdown(attachments: UploadedAsset[]): string {\n return buildAttachmentMarkdownWithAppUrl({ attachments });\n}\n\nexport function buildAttachmentMarkdownWithAppUrl({\n attachments,\n appUrl = DEFAULT_APP_URL,\n}: {\n attachments: UploadedAsset[];\n appUrl?: string;\n}): string {\n if (attachments.length === 0) return '';\n return attachments\n .map((attachment) => `[@${attachment.title}](${createAthenaSpacesUrl({ appUrl, assetIds: attachment.id })})`)\n .join('\\n');\n}\n"],"names":["createContext","createStore","useContext","jsx","Fragment","useState","useStore","useMemo","DEFAULT_APP_URL","createAthenaSpacesUrl"],"mappings":";;;;;;;AAsBA,MAAM,gBAAgBA,MAAAA,cAA6C,IAAI;AAgBhE,SAAS,wBAAyC;AACvD,SAAOC,QAAAA,YAAkC,OAAO,EAAE,aAAa,CAAA,GAAI,aAAa,OAAO,QAAQ,KAAA,EAAO;AACxG;AASO,SAAS,mBAAmB;AAAA,EACjC;AAAA,EACA;AACF,GAGG;AACD,QAAM,QAAQC,MAAAA,WAAW,aAAa;AACtC,MAAI,MAAO,QAAOC,2BAAAA,IAAC,yBAAA,EAAwB,OAAe,UAAS;AACnE,MAAI,MAAO,QAAOA,2BAAAA,IAAAC,WAAAA,UAAA,EAAG,SAAA,CAAS;AAC9B,SAAOD,+BAAC,yBAAuB,UAAS;AAC1C;AAEA,SAAS,sBAAsB,EAAE,YAAqC;AACpE,QAAM,CAAC,KAAK,IAAIE,MAAAA,SAAS,qBAAqB;AAC9C,SAAOF,2BAAAA,IAAC,yBAAA,EAAwB,OAAe,SAAA,CAAS;AAC1D;AAEA,SAAS,wBAAwB;AAAA,EAC/B;AAAA,EACA;AACF,GAGG;AACD,QAAM,cAAcG,QAAAA,SAAS,OAAO,CAAC,UAAU,MAAM,WAAW;AAChE,QAAM,cAAcA,QAAAA,SAAS,OAAO,CAAC,UAAU,MAAM,WAAW;AAChE,QAAM,SAASA,QAAAA,SAAS,OAAO,CAAC,UAAU,MAAM,UAAU,IAAI;AAC9D,QAAM,UAAUC,MAAAA;AAAAA,IACd,OAAO;AAAA,MACL,gBAAgB,CAAC,WACf,MAAM,SAAS,CAAC,WAAW,EAAE,aAAa,CAAC,GAAG,MAAM,aAAa,GAAG,MAAM,IAAI;AAAA,MAChF,kBAAkB,CAAC,OACjB,MAAM,SAAS,CAAC,WAAW;AAAA,QACzB,aAAa,MAAM,YAAY,OAAO,CAAC,eAAe,WAAW,OAAO,EAAE;AAAA,MAAA,EAC1E;AAAA,MACJ,kBAAkB,MAAM,MAAM,SAAS,EAAE,aAAa,CAAA,GAAI;AAAA,MAC1D,gBAAgB,CAAC,cAAuB,MAAM,SAAS,EAAE,aAAa,WAAW;AAAA,MACjF,WAAW,CAAC,SAAwB;AAClC,aAAK,MAAM,SAAA,EAAW,UAAU,UAAU,KAAM,OAAM,SAAS,EAAE,QAAQ,KAAA,CAAM;AAAA,MACjF;AAAA,IAAA;AAAA,IAEF,CAAC,KAAK;AAAA,EAAA;AAER,QAAM,QAAQA,MAAAA;AAAAA,IACZ,OAAO,EAAE,aAAa,aAAa,QAAQ,GAAG,QAAA;AAAA,IAC9C,CAAC,aAAa,aAAa,QAAQ,OAAO;AAAA,EAAA;AAG5C,SACEJ,2BAAAA,IAAC,cAAc,UAAd,EAAuB,OACrB,SAAA,CACH;AAEJ;AAEO,SAAS,iBAAyC;AACvD,QAAM,MAAMD,MAAAA,WAAW,aAAa;AACpC,MAAI,CAAC,KAAK;AACR,UAAM,IAAI,MAAM,qEAAqE;AAAA,EACvF;AACA,SAAO;AACT;AAYO,SAAS,kCAAkC;AAAA,EAChD;AAAA,EACA,SAASM,WAAAA;AACX,GAGW;AACT,MAAI,YAAY,WAAW,EAAG,QAAO;AACrC,SAAO,YACJ,IAAI,CAAC,eAAe,KAAK,WAAW,KAAK,KAAKC,WAAAA,sBAAsB,EAAE,QAAQ,UAAU,WAAW,GAAA,CAAI,CAAC,GAAG,EAC3G,KAAK,IAAI;AACd;;;;;"}
|
|
@@ -9,10 +9,17 @@ interface AttachmentContextValue {
|
|
|
9
9
|
/** True when one or more files are currently being uploaded. */
|
|
10
10
|
isUploading: boolean;
|
|
11
11
|
setIsUploading: (v: boolean) => void;
|
|
12
|
+
/**
|
|
13
|
+
* Why the last files offered were not attached, for the composer to say (a file picked while
|
|
14
|
+
* Athena can't be reached cannot upload), or `null`.
|
|
15
|
+
*/
|
|
16
|
+
notice: string | null;
|
|
17
|
+
setNotice: (notice: string | null) => void;
|
|
12
18
|
}
|
|
13
19
|
interface AttachmentStoreState {
|
|
14
20
|
attachments: UploadedAsset[];
|
|
15
21
|
isUploading: boolean;
|
|
22
|
+
notice?: string | null;
|
|
16
23
|
}
|
|
17
24
|
/**
|
|
18
25
|
* A composer's staged attachments, kept outside React (`createAttachmentStore`):
|
|
@@ -5,7 +5,7 @@ import { createStore } from "zustand/vanilla";
|
|
|
5
5
|
import { createAthenaSpacesUrl, DEFAULT_APP_URL } from "../lib/athena-urls.js";
|
|
6
6
|
const AttachmentCtx = createContext(null);
|
|
7
7
|
function createAttachmentStore() {
|
|
8
|
-
return createStore(() => ({ attachments: [], isUploading: false }));
|
|
8
|
+
return createStore(() => ({ attachments: [], isUploading: false, notice: null }));
|
|
9
9
|
}
|
|
10
10
|
function AttachmentProvider({
|
|
11
11
|
children,
|
|
@@ -26,6 +26,7 @@ function StoreAttachmentProvider({
|
|
|
26
26
|
}) {
|
|
27
27
|
const attachments = useStore(store, (state) => state.attachments);
|
|
28
28
|
const isUploading = useStore(store, (state) => state.isUploading);
|
|
29
|
+
const notice = useStore(store, (state) => state.notice ?? null);
|
|
29
30
|
const actions = useMemo(
|
|
30
31
|
() => ({
|
|
31
32
|
addAttachments: (assets) => store.setState((state) => ({ attachments: [...state.attachments, ...assets] })),
|
|
@@ -33,13 +34,16 @@ function StoreAttachmentProvider({
|
|
|
33
34
|
attachments: state.attachments.filter((attachment) => attachment.id !== id)
|
|
34
35
|
})),
|
|
35
36
|
clearAttachments: () => store.setState({ attachments: [] }),
|
|
36
|
-
setIsUploading: (uploading) => store.setState({ isUploading: uploading })
|
|
37
|
+
setIsUploading: (uploading) => store.setState({ isUploading: uploading }),
|
|
38
|
+
setNotice: (next) => {
|
|
39
|
+
if ((store.getState().notice ?? null) !== next) store.setState({ notice: next });
|
|
40
|
+
}
|
|
37
41
|
}),
|
|
38
42
|
[store]
|
|
39
43
|
);
|
|
40
44
|
const value = useMemo(
|
|
41
|
-
() => ({ attachments, isUploading, ...actions }),
|
|
42
|
-
[attachments, isUploading, actions]
|
|
45
|
+
() => ({ attachments, isUploading, notice, ...actions }),
|
|
46
|
+
[attachments, isUploading, notice, actions]
|
|
43
47
|
);
|
|
44
48
|
return /* @__PURE__ */ jsx(AttachmentCtx.Provider, { value, children });
|
|
45
49
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"AttachmentContext.js","sources":["../../src/composer/AttachmentContext.tsx"],"sourcesContent":["import { createContext, useContext, useMemo, useState, type ReactNode } from 'react';\nimport { useStore } from 'zustand';\nimport { createStore, type StoreApi } from 'zustand/vanilla';\nimport { createAthenaSpacesUrl, DEFAULT_APP_URL } from '../lib/athena-urls';\nimport type { UploadedAsset } from './useFileUpload';\n\ninterface AttachmentContextValue {\n attachments: UploadedAsset[];\n addAttachments: (assets: UploadedAsset[]) => void;\n removeAttachment: (id: string) => void;\n clearAttachments: () => void;\n /** True when one or more files are currently being uploaded. */\n isUploading: boolean;\n setIsUploading: (v: boolean) => void;\n}\n\nconst AttachmentCtx = createContext<AttachmentContextValue | null>(null);\n\ninterface AttachmentStoreState {\n attachments: UploadedAsset[];\n isUploading: boolean;\n}\n\n/**\n * A composer's staged attachments, kept outside React (`createAttachmentStore`):\n * a host that shows several chats gives each its own, and keeps it while that\n * chat's `AthenaChat` remounts (a tab moving between windows).\n */\nexport type AttachmentStore = StoreApi<AttachmentStoreState>;\n\n/** An empty `AttachmentStore`, for `<AttachmentProvider store>`. */\nexport function createAttachmentStore(): AttachmentStore {\n return createStore<AttachmentStoreState>(() => ({ attachments: [], isUploading: false }));\n}\n\n/**\n * Staged attachments for the composer. With a `store`, they are that store's,\n * whatever is mounted above: one per chat when a host shows several. Without\n * one, a provider already mounted above (a host's, outliving a remounting\n * \\`AthenaChat\\` such as a tab moving between windows) is reused instead of\n * starting empty.\n */\nexport function AttachmentProvider({\n children,\n store,\n}: {\n children: ReactNode;\n store?: AttachmentStore;\n}) {\n const outer = useContext(AttachmentCtx);\n if (store) return <StoreAttachmentProvider store={store}>{children}</StoreAttachmentProvider>;\n if (outer) return <>{children}</>;\n return <OwnAttachmentProvider>{children}</OwnAttachmentProvider>;\n}\n\nfunction OwnAttachmentProvider({ children }: { children: ReactNode }) {\n const [store] = useState(createAttachmentStore);\n return <StoreAttachmentProvider store={store}>{children}</StoreAttachmentProvider>;\n}\n\nfunction StoreAttachmentProvider({\n children,\n store,\n}: {\n children: ReactNode;\n store: AttachmentStore;\n}) {\n const attachments = useStore(store, (state) => state.attachments);\n const isUploading = useStore(store, (state) => state.isUploading);\n const actions = useMemo(\n () => ({\n addAttachments: (assets: UploadedAsset[]) =>\n store.setState((state) => ({ attachments: [...state.attachments, ...assets] })),\n removeAttachment: (id: string) =>\n store.setState((state) => ({\n attachments: state.attachments.filter((attachment) => attachment.id !== id),\n })),\n clearAttachments: () => store.setState({ attachments: [] }),\n setIsUploading: (uploading: boolean) => store.setState({ isUploading: uploading }),\n }),\n [store],\n );\n const value = useMemo(\n () => ({ attachments, isUploading, ...actions }),\n [attachments, isUploading, actions],\n );\n\n return (\n <AttachmentCtx.Provider value={value}>\n {children}\n </AttachmentCtx.Provider>\n );\n}\n\nexport function useAttachments(): AttachmentContextValue {\n const ctx = useContext(AttachmentCtx);\n if (!ctx) {\n throw new Error('[AthenaSDK] useAttachments must be used within <AttachmentProvider>');\n }\n return ctx;\n}\n\n/**\n * Build the markdown references for the current attachments.\n * Returns empty string if no attachments.\n *\n * @deprecated Use `buildAttachmentMarkdownWithAppUrl` to avoid defaulting links to the production Athena app URL.\n */\nexport function buildAttachmentMarkdown(attachments: UploadedAsset[]): string {\n return buildAttachmentMarkdownWithAppUrl({ attachments });\n}\n\nexport function buildAttachmentMarkdownWithAppUrl({\n attachments,\n appUrl = DEFAULT_APP_URL,\n}: {\n attachments: UploadedAsset[];\n appUrl?: string;\n}): string {\n if (attachments.length === 0) return '';\n return attachments\n .map((attachment) => `[@${attachment.title}](${createAthenaSpacesUrl({ appUrl, assetIds: attachment.id })})`)\n .join('\\n');\n}\n"],"names":[],"mappings":";;;;;
|
|
1
|
+
{"version":3,"file":"AttachmentContext.js","sources":["../../src/composer/AttachmentContext.tsx"],"sourcesContent":["import { createContext, useContext, useMemo, useState, type ReactNode } from 'react';\nimport { useStore } from 'zustand';\nimport { createStore, type StoreApi } from 'zustand/vanilla';\nimport { createAthenaSpacesUrl, DEFAULT_APP_URL } from '../lib/athena-urls';\nimport type { UploadedAsset } from './useFileUpload';\n\ninterface AttachmentContextValue {\n attachments: UploadedAsset[];\n addAttachments: (assets: UploadedAsset[]) => void;\n removeAttachment: (id: string) => void;\n clearAttachments: () => void;\n /** True when one or more files are currently being uploaded. */\n isUploading: boolean;\n setIsUploading: (v: boolean) => void;\n /**\n * Why the last files offered were not attached, for the composer to say (a file picked while\n * Athena can't be reached cannot upload), or `null`.\n */\n notice: string | null;\n setNotice: (notice: string | null) => void;\n}\n\nconst AttachmentCtx = createContext<AttachmentContextValue | null>(null);\n\ninterface AttachmentStoreState {\n attachments: UploadedAsset[];\n isUploading: boolean;\n notice?: string | null;\n}\n\n/**\n * A composer's staged attachments, kept outside React (`createAttachmentStore`):\n * a host that shows several chats gives each its own, and keeps it while that\n * chat's `AthenaChat` remounts (a tab moving between windows).\n */\nexport type AttachmentStore = StoreApi<AttachmentStoreState>;\n\n/** An empty `AttachmentStore`, for `<AttachmentProvider store>`. */\nexport function createAttachmentStore(): AttachmentStore {\n return createStore<AttachmentStoreState>(() => ({ attachments: [], isUploading: false, notice: null }));\n}\n\n/**\n * Staged attachments for the composer. With a `store`, they are that store's,\n * whatever is mounted above: one per chat when a host shows several. Without\n * one, a provider already mounted above (a host's, outliving a remounting\n * \\`AthenaChat\\` such as a tab moving between windows) is reused instead of\n * starting empty.\n */\nexport function AttachmentProvider({\n children,\n store,\n}: {\n children: ReactNode;\n store?: AttachmentStore;\n}) {\n const outer = useContext(AttachmentCtx);\n if (store) return <StoreAttachmentProvider store={store}>{children}</StoreAttachmentProvider>;\n if (outer) return <>{children}</>;\n return <OwnAttachmentProvider>{children}</OwnAttachmentProvider>;\n}\n\nfunction OwnAttachmentProvider({ children }: { children: ReactNode }) {\n const [store] = useState(createAttachmentStore);\n return <StoreAttachmentProvider store={store}>{children}</StoreAttachmentProvider>;\n}\n\nfunction StoreAttachmentProvider({\n children,\n store,\n}: {\n children: ReactNode;\n store: AttachmentStore;\n}) {\n const attachments = useStore(store, (state) => state.attachments);\n const isUploading = useStore(store, (state) => state.isUploading);\n const notice = useStore(store, (state) => state.notice ?? null);\n const actions = useMemo(\n () => ({\n addAttachments: (assets: UploadedAsset[]) =>\n store.setState((state) => ({ attachments: [...state.attachments, ...assets] })),\n removeAttachment: (id: string) =>\n store.setState((state) => ({\n attachments: state.attachments.filter((attachment) => attachment.id !== id),\n })),\n clearAttachments: () => store.setState({ attachments: [] }),\n setIsUploading: (uploading: boolean) => store.setState({ isUploading: uploading }),\n setNotice: (next: string | null) => {\n if ((store.getState().notice ?? null) !== next) store.setState({ notice: next });\n },\n }),\n [store],\n );\n const value = useMemo(\n () => ({ attachments, isUploading, notice, ...actions }),\n [attachments, isUploading, notice, actions],\n );\n\n return (\n <AttachmentCtx.Provider value={value}>\n {children}\n </AttachmentCtx.Provider>\n );\n}\n\nexport function useAttachments(): AttachmentContextValue {\n const ctx = useContext(AttachmentCtx);\n if (!ctx) {\n throw new Error('[AthenaSDK] useAttachments must be used within <AttachmentProvider>');\n }\n return ctx;\n}\n\n/**\n * Build the markdown references for the current attachments.\n * Returns empty string if no attachments.\n *\n * @deprecated Use `buildAttachmentMarkdownWithAppUrl` to avoid defaulting links to the production Athena app URL.\n */\nexport function buildAttachmentMarkdown(attachments: UploadedAsset[]): string {\n return buildAttachmentMarkdownWithAppUrl({ attachments });\n}\n\nexport function buildAttachmentMarkdownWithAppUrl({\n attachments,\n appUrl = DEFAULT_APP_URL,\n}: {\n attachments: UploadedAsset[];\n appUrl?: string;\n}): string {\n if (attachments.length === 0) return '';\n return attachments\n .map((attachment) => `[@${attachment.title}](${createAthenaSpacesUrl({ appUrl, assetIds: attachment.id })})`)\n .join('\\n');\n}\n"],"names":[],"mappings":";;;;;AAsBA,MAAM,gBAAgB,cAA6C,IAAI;AAgBhE,SAAS,wBAAyC;AACvD,SAAO,YAAkC,OAAO,EAAE,aAAa,CAAA,GAAI,aAAa,OAAO,QAAQ,KAAA,EAAO;AACxG;AASO,SAAS,mBAAmB;AAAA,EACjC;AAAA,EACA;AACF,GAGG;AACD,QAAM,QAAQ,WAAW,aAAa;AACtC,MAAI,MAAO,QAAO,oBAAC,yBAAA,EAAwB,OAAe,UAAS;AACnE,MAAI,MAAO,QAAO,oBAAA,UAAA,EAAG,SAAA,CAAS;AAC9B,SAAO,oBAAC,yBAAuB,UAAS;AAC1C;AAEA,SAAS,sBAAsB,EAAE,YAAqC;AACpE,QAAM,CAAC,KAAK,IAAI,SAAS,qBAAqB;AAC9C,SAAO,oBAAC,yBAAA,EAAwB,OAAe,SAAA,CAAS;AAC1D;AAEA,SAAS,wBAAwB;AAAA,EAC/B;AAAA,EACA;AACF,GAGG;AACD,QAAM,cAAc,SAAS,OAAO,CAAC,UAAU,MAAM,WAAW;AAChE,QAAM,cAAc,SAAS,OAAO,CAAC,UAAU,MAAM,WAAW;AAChE,QAAM,SAAS,SAAS,OAAO,CAAC,UAAU,MAAM,UAAU,IAAI;AAC9D,QAAM,UAAU;AAAA,IACd,OAAO;AAAA,MACL,gBAAgB,CAAC,WACf,MAAM,SAAS,CAAC,WAAW,EAAE,aAAa,CAAC,GAAG,MAAM,aAAa,GAAG,MAAM,IAAI;AAAA,MAChF,kBAAkB,CAAC,OACjB,MAAM,SAAS,CAAC,WAAW;AAAA,QACzB,aAAa,MAAM,YAAY,OAAO,CAAC,eAAe,WAAW,OAAO,EAAE;AAAA,MAAA,EAC1E;AAAA,MACJ,kBAAkB,MAAM,MAAM,SAAS,EAAE,aAAa,CAAA,GAAI;AAAA,MAC1D,gBAAgB,CAAC,cAAuB,MAAM,SAAS,EAAE,aAAa,WAAW;AAAA,MACjF,WAAW,CAAC,SAAwB;AAClC,aAAK,MAAM,SAAA,EAAW,UAAU,UAAU,KAAM,OAAM,SAAS,EAAE,QAAQ,KAAA,CAAM;AAAA,MACjF;AAAA,IAAA;AAAA,IAEF,CAAC,KAAK;AAAA,EAAA;AAER,QAAM,QAAQ;AAAA,IACZ,OAAO,EAAE,aAAa,aAAa,QAAQ,GAAG,QAAA;AAAA,IAC9C,CAAC,aAAa,aAAa,QAAQ,OAAO;AAAA,EAAA;AAG5C,SACE,oBAAC,cAAc,UAAd,EAAuB,OACrB,SAAA,CACH;AAEJ;AAEO,SAAS,iBAAyC;AACvD,QAAM,MAAM,WAAW,aAAa;AACpC,MAAI,CAAC,KAAK;AACR,UAAM,IAAI,MAAM,qEAAqE;AAAA,EACvF;AACA,SAAO;AACT;AAYO,SAAS,kCAAkC;AAAA,EAChD;AAAA,EACA,SAAS;AACX,GAGW;AACT,MAAI,YAAY,WAAW,EAAG,QAAO;AACrC,SAAO,YACJ,IAAI,CAAC,eAAe,KAAK,WAAW,KAAK,KAAK,sBAAsB,EAAE,QAAQ,UAAU,WAAW,GAAA,CAAI,CAAC,GAAG,EAC3G,KAAK,IAAI;AACd;"}
|
|
@@ -2,6 +2,7 @@
|
|
|
2
2
|
Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
|
|
3
3
|
const AttachmentContext = require("./AttachmentContext.cjs");
|
|
4
4
|
const composerMessage = require("../chat-ui/composer/composer-message.cjs");
|
|
5
|
+
const composerMarkdown = require("../agent-runtime/src/composer-markdown.cjs");
|
|
5
6
|
function buildComposedMessage(opts) {
|
|
6
7
|
var _a;
|
|
7
8
|
const parts = [];
|
|
@@ -47,6 +48,39 @@ function buildComposedSend({
|
|
|
47
48
|
});
|
|
48
49
|
return { text, draftMarkdown };
|
|
49
50
|
}
|
|
51
|
+
function holdComposedSend({
|
|
52
|
+
outbox,
|
|
53
|
+
attachments,
|
|
54
|
+
carried = [],
|
|
55
|
+
quote,
|
|
56
|
+
send,
|
|
57
|
+
appUrl
|
|
58
|
+
}) {
|
|
59
|
+
const composed = buildComposedSend({ attachments, quote, send, appUrl });
|
|
60
|
+
if (!composed) return null;
|
|
61
|
+
const named = /* @__PURE__ */ new Map();
|
|
62
|
+
for (const attachment of attachments ?? []) {
|
|
63
|
+
named.set(attachment.id, {
|
|
64
|
+
assetId: attachment.id,
|
|
65
|
+
title: attachment.title,
|
|
66
|
+
...attachment.mediaType && { mediaType: attachment.mediaType }
|
|
67
|
+
});
|
|
68
|
+
}
|
|
69
|
+
for (const attachment of carried) {
|
|
70
|
+
if (!named.has(attachment.assetId)) named.set(attachment.assetId, attachment);
|
|
71
|
+
}
|
|
72
|
+
return outbox.hold({
|
|
73
|
+
text: composed.text,
|
|
74
|
+
composerMarkdown: composed.draftMarkdown,
|
|
75
|
+
metadata: composerMarkdown.withDeepAgentComposerMarkdown({
|
|
76
|
+
metadata: void 0,
|
|
77
|
+
text: composed.text,
|
|
78
|
+
markdown: composed.draftMarkdown
|
|
79
|
+
}),
|
|
80
|
+
attachments: [...named.values()]
|
|
81
|
+
});
|
|
82
|
+
}
|
|
50
83
|
exports.buildComposedMessage = buildComposedMessage;
|
|
51
84
|
exports.buildComposedSend = buildComposedSend;
|
|
85
|
+
exports.holdComposedSend = holdComposedSend;
|
|
52
86
|
//# sourceMappingURL=build-composed-message.cjs.map
|