@xinghunm/ai-chat 0.2.0 → 0.2.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.js +93 -40
- package/dist/index.mjs +113 -60
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -729,6 +729,64 @@ var getNextDisplayedUnitCount = ({
|
|
|
729
729
|
var splitMarkdownBlocks = (content) => content.split(/\n{2,}/).map((block) => block.trim()).filter(Boolean);
|
|
730
730
|
|
|
731
731
|
// src/components/chat-thread/hooks/use-chat-message-reveal.ts
|
|
732
|
+
var createRevealState = ({
|
|
733
|
+
isAssistantStreaming,
|
|
734
|
+
targetUnitCount
|
|
735
|
+
}) => {
|
|
736
|
+
const initialDisplayedUnitCount = isAssistantStreaming ? 0 : targetUnitCount;
|
|
737
|
+
return {
|
|
738
|
+
batchedTargetUnitCount: initialDisplayedUnitCount,
|
|
739
|
+
displayedUnitCount: initialDisplayedUnitCount,
|
|
740
|
+
isFreshBlockActive: false
|
|
741
|
+
};
|
|
742
|
+
};
|
|
743
|
+
var revealReducer = (state, action) => {
|
|
744
|
+
switch (action.type) {
|
|
745
|
+
case "reset-message":
|
|
746
|
+
return createRevealState(action);
|
|
747
|
+
case "commit-batched-target": {
|
|
748
|
+
const nextDisplayedUnitCount = action.role === "assistant" ? getNextDisplayedUnitCount({
|
|
749
|
+
currentUnits: state.displayedUnitCount,
|
|
750
|
+
targetUnits: action.nextTargetUnitCount,
|
|
751
|
+
isStreaming: action.isAssistantStreaming,
|
|
752
|
+
minimumStep: state.displayedUnitCount > 0 && action.isAssistantStreaming ? 2 : 1
|
|
753
|
+
}) : action.nextTargetUnitCount;
|
|
754
|
+
return {
|
|
755
|
+
...state,
|
|
756
|
+
batchedTargetUnitCount: action.nextTargetUnitCount,
|
|
757
|
+
displayedUnitCount: nextDisplayedUnitCount
|
|
758
|
+
};
|
|
759
|
+
}
|
|
760
|
+
case "set-fresh-block-active":
|
|
761
|
+
return state.isFreshBlockActive === action.isActive ? state : {
|
|
762
|
+
...state,
|
|
763
|
+
isFreshBlockActive: action.isActive
|
|
764
|
+
};
|
|
765
|
+
case "sync-displayed-target":
|
|
766
|
+
return state.displayedUnitCount === state.batchedTargetUnitCount ? state : {
|
|
767
|
+
...state,
|
|
768
|
+
displayedUnitCount: state.batchedTargetUnitCount
|
|
769
|
+
};
|
|
770
|
+
case "advance-reveal": {
|
|
771
|
+
if (state.displayedUnitCount >= state.batchedTargetUnitCount) {
|
|
772
|
+
return state;
|
|
773
|
+
}
|
|
774
|
+
return {
|
|
775
|
+
...state,
|
|
776
|
+
displayedUnitCount: Math.min(
|
|
777
|
+
state.batchedTargetUnitCount,
|
|
778
|
+
getNextDisplayedUnitCount({
|
|
779
|
+
currentUnits: state.displayedUnitCount,
|
|
780
|
+
targetUnits: state.batchedTargetUnitCount,
|
|
781
|
+
isStreaming: action.isAssistantStreaming
|
|
782
|
+
})
|
|
783
|
+
)
|
|
784
|
+
};
|
|
785
|
+
}
|
|
786
|
+
default:
|
|
787
|
+
return state;
|
|
788
|
+
}
|
|
789
|
+
};
|
|
732
790
|
var useChatMessageReveal = (message) => {
|
|
733
791
|
const isAssistantStreaming = message.role === "assistant" && message.status === "streaming";
|
|
734
792
|
const targetContent = message.content || "";
|
|
@@ -736,41 +794,47 @@ var useChatMessageReveal = (message) => {
|
|
|
736
794
|
const pendingTargetUnitCountRef = (0, import_react5.useRef)(targetUnits.length);
|
|
737
795
|
const batchedTargetUnitCountRef = (0, import_react5.useRef)(isAssistantStreaming ? 0 : targetUnits.length);
|
|
738
796
|
const inputBatchTimeoutRef = (0, import_react5.useRef)(null);
|
|
739
|
-
const [batchedTargetUnitCount, setBatchedTargetUnitCount] = (0, import_react5.useState)(
|
|
740
|
-
() => isAssistantStreaming ? 0 : targetUnits.length
|
|
741
|
-
);
|
|
742
797
|
const lastDisplayedBlockCountRef = (0, import_react5.useRef)(0);
|
|
743
|
-
const
|
|
744
|
-
|
|
798
|
+
const previousMessageIdRef = (0, import_react5.useRef)(message.id);
|
|
799
|
+
const [state, dispatch] = (0, import_react5.useReducer)(
|
|
800
|
+
revealReducer,
|
|
801
|
+
{
|
|
802
|
+
isAssistantStreaming,
|
|
803
|
+
targetUnitCount: targetUnits.length
|
|
804
|
+
},
|
|
805
|
+
createRevealState
|
|
745
806
|
);
|
|
746
|
-
const
|
|
807
|
+
const { batchedTargetUnitCount, displayedUnitCount, isFreshBlockActive } = state;
|
|
747
808
|
const commitBatchedTargetUnitCount = (0, import_react5.useCallback)(
|
|
748
809
|
(nextTargetUnitCount) => {
|
|
749
810
|
batchedTargetUnitCountRef.current = nextTargetUnitCount;
|
|
750
|
-
|
|
751
|
-
|
|
752
|
-
|
|
753
|
-
|
|
754
|
-
|
|
755
|
-
|
|
756
|
-
minimumStep: current > 0 && isAssistantStreaming ? 2 : 1
|
|
757
|
-
}) : nextTargetUnitCount
|
|
758
|
-
);
|
|
811
|
+
dispatch({
|
|
812
|
+
type: "commit-batched-target",
|
|
813
|
+
isAssistantStreaming,
|
|
814
|
+
nextTargetUnitCount,
|
|
815
|
+
role: message.role
|
|
816
|
+
});
|
|
759
817
|
},
|
|
760
818
|
[isAssistantStreaming, message.role]
|
|
761
819
|
);
|
|
762
820
|
(0, import_react5.useEffect)(() => {
|
|
821
|
+
if (previousMessageIdRef.current === message.id) {
|
|
822
|
+
return;
|
|
823
|
+
}
|
|
824
|
+
previousMessageIdRef.current = message.id;
|
|
763
825
|
pendingTargetUnitCountRef.current = targetUnits.length;
|
|
764
826
|
batchedTargetUnitCountRef.current = isAssistantStreaming ? 0 : targetUnits.length;
|
|
765
|
-
setBatchedTargetUnitCount(batchedTargetUnitCountRef.current);
|
|
766
|
-
setDisplayedUnitCount(isAssistantStreaming ? 0 : targetUnits.length);
|
|
767
827
|
lastDisplayedBlockCountRef.current = 0;
|
|
768
828
|
if (inputBatchTimeoutRef.current !== null) {
|
|
769
829
|
window.clearTimeout(inputBatchTimeoutRef.current);
|
|
770
830
|
inputBatchTimeoutRef.current = null;
|
|
771
831
|
}
|
|
772
|
-
|
|
773
|
-
|
|
832
|
+
dispatch({
|
|
833
|
+
type: "reset-message",
|
|
834
|
+
isAssistantStreaming,
|
|
835
|
+
targetUnitCount: targetUnits.length
|
|
836
|
+
});
|
|
837
|
+
}, [isAssistantStreaming, message.id, targetUnits.length]);
|
|
774
838
|
(0, import_react5.useEffect)(() => {
|
|
775
839
|
pendingTargetUnitCountRef.current = targetUnits.length;
|
|
776
840
|
if (message.role !== "assistant" || !isAssistantStreaming) {
|
|
@@ -813,9 +877,9 @@ var useChatMessageReveal = (message) => {
|
|
|
813
877
|
if (!hasNewDisplayedBlock) {
|
|
814
878
|
return;
|
|
815
879
|
}
|
|
816
|
-
|
|
880
|
+
dispatch({ type: "set-fresh-block-active", isActive: true });
|
|
817
881
|
const timer = window.setTimeout(() => {
|
|
818
|
-
|
|
882
|
+
dispatch({ type: "set-fresh-block-active", isActive: false });
|
|
819
883
|
}, STREAM_FRESH_BLOCK_SETTLE_MS);
|
|
820
884
|
return () => {
|
|
821
885
|
window.clearTimeout(timer);
|
|
@@ -825,32 +889,19 @@ var useChatMessageReveal = (message) => {
|
|
|
825
889
|
const shouldAnimateReveal = message.role === "assistant" && displayedUnitCount < batchedTargetUnitCount && (isAssistantStreaming || displayedUnitCount > 0);
|
|
826
890
|
if (!shouldAnimateReveal) {
|
|
827
891
|
if (displayedUnitCount !== batchedTargetUnitCount) {
|
|
828
|
-
|
|
892
|
+
dispatch({ type: "sync-displayed-target" });
|
|
829
893
|
}
|
|
830
894
|
return;
|
|
831
895
|
}
|
|
832
896
|
const timer = window.setInterval(() => {
|
|
833
|
-
|
|
834
|
-
if (current >= batchedTargetUnitCount) {
|
|
835
|
-
window.clearInterval(timer);
|
|
836
|
-
return current;
|
|
837
|
-
}
|
|
838
|
-
return Math.min(
|
|
839
|
-
batchedTargetUnitCount,
|
|
840
|
-
getNextDisplayedUnitCount({
|
|
841
|
-
currentUnits: current,
|
|
842
|
-
targetUnits: batchedTargetUnitCount,
|
|
843
|
-
isStreaming: isAssistantStreaming
|
|
844
|
-
})
|
|
845
|
-
);
|
|
846
|
-
});
|
|
897
|
+
dispatch({ type: "advance-reveal", isAssistantStreaming });
|
|
847
898
|
}, STREAM_REVEAL_TICK_MS);
|
|
848
899
|
return () => {
|
|
849
900
|
window.clearInterval(timer);
|
|
850
901
|
};
|
|
851
902
|
}, [batchedTargetUnitCount, displayedUnitCount, isAssistantStreaming, message.role]);
|
|
852
903
|
const settledContent = isFreshBlockActive ? contentBlocks.slice(0, -1).join("\n\n") : displayedContent;
|
|
853
|
-
const freshContent = isFreshBlockActive ? contentBlocks.
|
|
904
|
+
const freshContent = isFreshBlockActive ? contentBlocks[contentBlocks.length - 1] ?? "" : "";
|
|
854
905
|
return {
|
|
855
906
|
isAssistantStreaming,
|
|
856
907
|
displayedContent,
|
|
@@ -1808,11 +1859,13 @@ var ChatMessageItemView = ({
|
|
|
1808
1859
|
const attachments = message.attachments ?? [];
|
|
1809
1860
|
const blocks = message.blocks ?? [];
|
|
1810
1861
|
const hasStructuredBlocks = blocks.length > 0;
|
|
1862
|
+
const hasMarkdownOnlyBlocks = hasStructuredBlocks && blocks.every((block) => block.type === "markdown");
|
|
1811
1863
|
const hasTextContent = Boolean(settledContent || freshContent || displayedContent);
|
|
1864
|
+
const shouldRenderStructuredBlocks = hasStructuredBlocks && !(isAssistantStreaming && hasMarkdownOnlyBlocks && hasTextContent);
|
|
1812
1865
|
const isPlanMode = mode === "plan";
|
|
1813
1866
|
const canSubmitConfirmation = isPlanMode && typeof onConfirmationSubmit === "function";
|
|
1814
1867
|
const canSubmitQuestionnaire = isPlanMode && typeof onQuestionnaireSubmit === "function";
|
|
1815
|
-
const shouldShowStreamingCaret = isAssistantStreaming && (!
|
|
1868
|
+
const shouldShowStreamingCaret = isAssistantStreaming && (!shouldRenderStructuredBlocks || hasTextContent);
|
|
1816
1869
|
const renderChatMessageBlock = (block, index) => {
|
|
1817
1870
|
switch (block.type) {
|
|
1818
1871
|
case "markdown":
|
|
@@ -1892,8 +1945,8 @@ var ChatMessageItemView = ({
|
|
|
1892
1945
|
isStoppedAssistant ? /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(StatusTag, { "data-testid": "chat-message-stopped-tag", children: labels.stoppedResponse }) : null
|
|
1893
1946
|
] }),
|
|
1894
1947
|
/* @__PURE__ */ (0, import_jsx_runtime8.jsxs)(Content, { "data-testid": "chat-message-content", children: [
|
|
1895
|
-
|
|
1896
|
-
|
|
1948
|
+
shouldRenderStructuredBlocks || hasTextContent ? /* @__PURE__ */ (0, import_jsx_runtime8.jsxs)(ContentStack, { "data-testid": "chat-message-body-stack", children: [
|
|
1949
|
+
shouldRenderStructuredBlocks ? blocks.map((block, index) => /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(
|
|
1897
1950
|
ContentSegment,
|
|
1898
1951
|
{
|
|
1899
1952
|
"data-testid": "chat-message-content-segment",
|
package/dist/index.mjs
CHANGED
|
@@ -590,7 +590,7 @@ var AiChatProvider = (props) => {
|
|
|
590
590
|
};
|
|
591
591
|
|
|
592
592
|
// src/components/chat-thread/index.tsx
|
|
593
|
-
import { useCallback as useCallback2, useLayoutEffect, useMemo as useMemo3, useRef as useRef4, useState as
|
|
593
|
+
import { useCallback as useCallback2, useLayoutEffect, useMemo as useMemo3, useRef as useRef4, useState as useState4 } from "react";
|
|
594
594
|
import styled10 from "@emotion/styled";
|
|
595
595
|
|
|
596
596
|
// src/context/use-chat-context.ts
|
|
@@ -627,7 +627,7 @@ var calculateChatThreadScrollSpacerHeight = ({
|
|
|
627
627
|
);
|
|
628
628
|
|
|
629
629
|
// src/components/chat-thread/components/chat-message-item.tsx
|
|
630
|
-
import { Fragment, memo, useState as
|
|
630
|
+
import { Fragment, memo, useState as useState3 } from "react";
|
|
631
631
|
import styled7 from "@emotion/styled";
|
|
632
632
|
import { keyframes } from "@emotion/react";
|
|
633
633
|
import ReactMarkdown from "react-markdown";
|
|
@@ -636,7 +636,7 @@ import remarkMath from "remark-math";
|
|
|
636
636
|
import rehypeKatex from "rehype-katex";
|
|
637
637
|
|
|
638
638
|
// src/components/chat-thread/hooks/use-chat-message-reveal.ts
|
|
639
|
-
import { useCallback, useEffect, useMemo as useMemo2, useRef as useRef2
|
|
639
|
+
import { useCallback, useEffect, useMemo as useMemo2, useReducer, useRef as useRef2 } from "react";
|
|
640
640
|
|
|
641
641
|
// src/components/chat-thread/lib/message-reveal.ts
|
|
642
642
|
var STREAM_REVEAL_TICK_MS = 36;
|
|
@@ -683,6 +683,64 @@ var getNextDisplayedUnitCount = ({
|
|
|
683
683
|
var splitMarkdownBlocks = (content) => content.split(/\n{2,}/).map((block) => block.trim()).filter(Boolean);
|
|
684
684
|
|
|
685
685
|
// src/components/chat-thread/hooks/use-chat-message-reveal.ts
|
|
686
|
+
var createRevealState = ({
|
|
687
|
+
isAssistantStreaming,
|
|
688
|
+
targetUnitCount
|
|
689
|
+
}) => {
|
|
690
|
+
const initialDisplayedUnitCount = isAssistantStreaming ? 0 : targetUnitCount;
|
|
691
|
+
return {
|
|
692
|
+
batchedTargetUnitCount: initialDisplayedUnitCount,
|
|
693
|
+
displayedUnitCount: initialDisplayedUnitCount,
|
|
694
|
+
isFreshBlockActive: false
|
|
695
|
+
};
|
|
696
|
+
};
|
|
697
|
+
var revealReducer = (state, action) => {
|
|
698
|
+
switch (action.type) {
|
|
699
|
+
case "reset-message":
|
|
700
|
+
return createRevealState(action);
|
|
701
|
+
case "commit-batched-target": {
|
|
702
|
+
const nextDisplayedUnitCount = action.role === "assistant" ? getNextDisplayedUnitCount({
|
|
703
|
+
currentUnits: state.displayedUnitCount,
|
|
704
|
+
targetUnits: action.nextTargetUnitCount,
|
|
705
|
+
isStreaming: action.isAssistantStreaming,
|
|
706
|
+
minimumStep: state.displayedUnitCount > 0 && action.isAssistantStreaming ? 2 : 1
|
|
707
|
+
}) : action.nextTargetUnitCount;
|
|
708
|
+
return {
|
|
709
|
+
...state,
|
|
710
|
+
batchedTargetUnitCount: action.nextTargetUnitCount,
|
|
711
|
+
displayedUnitCount: nextDisplayedUnitCount
|
|
712
|
+
};
|
|
713
|
+
}
|
|
714
|
+
case "set-fresh-block-active":
|
|
715
|
+
return state.isFreshBlockActive === action.isActive ? state : {
|
|
716
|
+
...state,
|
|
717
|
+
isFreshBlockActive: action.isActive
|
|
718
|
+
};
|
|
719
|
+
case "sync-displayed-target":
|
|
720
|
+
return state.displayedUnitCount === state.batchedTargetUnitCount ? state : {
|
|
721
|
+
...state,
|
|
722
|
+
displayedUnitCount: state.batchedTargetUnitCount
|
|
723
|
+
};
|
|
724
|
+
case "advance-reveal": {
|
|
725
|
+
if (state.displayedUnitCount >= state.batchedTargetUnitCount) {
|
|
726
|
+
return state;
|
|
727
|
+
}
|
|
728
|
+
return {
|
|
729
|
+
...state,
|
|
730
|
+
displayedUnitCount: Math.min(
|
|
731
|
+
state.batchedTargetUnitCount,
|
|
732
|
+
getNextDisplayedUnitCount({
|
|
733
|
+
currentUnits: state.displayedUnitCount,
|
|
734
|
+
targetUnits: state.batchedTargetUnitCount,
|
|
735
|
+
isStreaming: action.isAssistantStreaming
|
|
736
|
+
})
|
|
737
|
+
)
|
|
738
|
+
};
|
|
739
|
+
}
|
|
740
|
+
default:
|
|
741
|
+
return state;
|
|
742
|
+
}
|
|
743
|
+
};
|
|
686
744
|
var useChatMessageReveal = (message) => {
|
|
687
745
|
const isAssistantStreaming = message.role === "assistant" && message.status === "streaming";
|
|
688
746
|
const targetContent = message.content || "";
|
|
@@ -690,41 +748,47 @@ var useChatMessageReveal = (message) => {
|
|
|
690
748
|
const pendingTargetUnitCountRef = useRef2(targetUnits.length);
|
|
691
749
|
const batchedTargetUnitCountRef = useRef2(isAssistantStreaming ? 0 : targetUnits.length);
|
|
692
750
|
const inputBatchTimeoutRef = useRef2(null);
|
|
693
|
-
const [batchedTargetUnitCount, setBatchedTargetUnitCount] = useState2(
|
|
694
|
-
() => isAssistantStreaming ? 0 : targetUnits.length
|
|
695
|
-
);
|
|
696
751
|
const lastDisplayedBlockCountRef = useRef2(0);
|
|
697
|
-
const
|
|
698
|
-
|
|
752
|
+
const previousMessageIdRef = useRef2(message.id);
|
|
753
|
+
const [state, dispatch] = useReducer(
|
|
754
|
+
revealReducer,
|
|
755
|
+
{
|
|
756
|
+
isAssistantStreaming,
|
|
757
|
+
targetUnitCount: targetUnits.length
|
|
758
|
+
},
|
|
759
|
+
createRevealState
|
|
699
760
|
);
|
|
700
|
-
const
|
|
761
|
+
const { batchedTargetUnitCount, displayedUnitCount, isFreshBlockActive } = state;
|
|
701
762
|
const commitBatchedTargetUnitCount = useCallback(
|
|
702
763
|
(nextTargetUnitCount) => {
|
|
703
764
|
batchedTargetUnitCountRef.current = nextTargetUnitCount;
|
|
704
|
-
|
|
705
|
-
|
|
706
|
-
|
|
707
|
-
|
|
708
|
-
|
|
709
|
-
|
|
710
|
-
minimumStep: current > 0 && isAssistantStreaming ? 2 : 1
|
|
711
|
-
}) : nextTargetUnitCount
|
|
712
|
-
);
|
|
765
|
+
dispatch({
|
|
766
|
+
type: "commit-batched-target",
|
|
767
|
+
isAssistantStreaming,
|
|
768
|
+
nextTargetUnitCount,
|
|
769
|
+
role: message.role
|
|
770
|
+
});
|
|
713
771
|
},
|
|
714
772
|
[isAssistantStreaming, message.role]
|
|
715
773
|
);
|
|
716
774
|
useEffect(() => {
|
|
775
|
+
if (previousMessageIdRef.current === message.id) {
|
|
776
|
+
return;
|
|
777
|
+
}
|
|
778
|
+
previousMessageIdRef.current = message.id;
|
|
717
779
|
pendingTargetUnitCountRef.current = targetUnits.length;
|
|
718
780
|
batchedTargetUnitCountRef.current = isAssistantStreaming ? 0 : targetUnits.length;
|
|
719
|
-
setBatchedTargetUnitCount(batchedTargetUnitCountRef.current);
|
|
720
|
-
setDisplayedUnitCount(isAssistantStreaming ? 0 : targetUnits.length);
|
|
721
781
|
lastDisplayedBlockCountRef.current = 0;
|
|
722
782
|
if (inputBatchTimeoutRef.current !== null) {
|
|
723
783
|
window.clearTimeout(inputBatchTimeoutRef.current);
|
|
724
784
|
inputBatchTimeoutRef.current = null;
|
|
725
785
|
}
|
|
726
|
-
|
|
727
|
-
|
|
786
|
+
dispatch({
|
|
787
|
+
type: "reset-message",
|
|
788
|
+
isAssistantStreaming,
|
|
789
|
+
targetUnitCount: targetUnits.length
|
|
790
|
+
});
|
|
791
|
+
}, [isAssistantStreaming, message.id, targetUnits.length]);
|
|
728
792
|
useEffect(() => {
|
|
729
793
|
pendingTargetUnitCountRef.current = targetUnits.length;
|
|
730
794
|
if (message.role !== "assistant" || !isAssistantStreaming) {
|
|
@@ -767,9 +831,9 @@ var useChatMessageReveal = (message) => {
|
|
|
767
831
|
if (!hasNewDisplayedBlock) {
|
|
768
832
|
return;
|
|
769
833
|
}
|
|
770
|
-
|
|
834
|
+
dispatch({ type: "set-fresh-block-active", isActive: true });
|
|
771
835
|
const timer = window.setTimeout(() => {
|
|
772
|
-
|
|
836
|
+
dispatch({ type: "set-fresh-block-active", isActive: false });
|
|
773
837
|
}, STREAM_FRESH_BLOCK_SETTLE_MS);
|
|
774
838
|
return () => {
|
|
775
839
|
window.clearTimeout(timer);
|
|
@@ -779,32 +843,19 @@ var useChatMessageReveal = (message) => {
|
|
|
779
843
|
const shouldAnimateReveal = message.role === "assistant" && displayedUnitCount < batchedTargetUnitCount && (isAssistantStreaming || displayedUnitCount > 0);
|
|
780
844
|
if (!shouldAnimateReveal) {
|
|
781
845
|
if (displayedUnitCount !== batchedTargetUnitCount) {
|
|
782
|
-
|
|
846
|
+
dispatch({ type: "sync-displayed-target" });
|
|
783
847
|
}
|
|
784
848
|
return;
|
|
785
849
|
}
|
|
786
850
|
const timer = window.setInterval(() => {
|
|
787
|
-
|
|
788
|
-
if (current >= batchedTargetUnitCount) {
|
|
789
|
-
window.clearInterval(timer);
|
|
790
|
-
return current;
|
|
791
|
-
}
|
|
792
|
-
return Math.min(
|
|
793
|
-
batchedTargetUnitCount,
|
|
794
|
-
getNextDisplayedUnitCount({
|
|
795
|
-
currentUnits: current,
|
|
796
|
-
targetUnits: batchedTargetUnitCount,
|
|
797
|
-
isStreaming: isAssistantStreaming
|
|
798
|
-
})
|
|
799
|
-
);
|
|
800
|
-
});
|
|
851
|
+
dispatch({ type: "advance-reveal", isAssistantStreaming });
|
|
801
852
|
}, STREAM_REVEAL_TICK_MS);
|
|
802
853
|
return () => {
|
|
803
854
|
window.clearInterval(timer);
|
|
804
855
|
};
|
|
805
856
|
}, [batchedTargetUnitCount, displayedUnitCount, isAssistantStreaming, message.role]);
|
|
806
857
|
const settledContent = isFreshBlockActive ? contentBlocks.slice(0, -1).join("\n\n") : displayedContent;
|
|
807
|
-
const freshContent = isFreshBlockActive ? contentBlocks.
|
|
858
|
+
const freshContent = isFreshBlockActive ? contentBlocks[contentBlocks.length - 1] ?? "" : "";
|
|
808
859
|
return {
|
|
809
860
|
isAssistantStreaming,
|
|
810
861
|
displayedContent,
|
|
@@ -1023,7 +1074,7 @@ var Value = styled3.span`
|
|
|
1023
1074
|
`;
|
|
1024
1075
|
|
|
1025
1076
|
// src/components/chat-thread/components/pde-ai-questionnaire-card.tsx
|
|
1026
|
-
import { useState as
|
|
1077
|
+
import { useState as useState2 } from "react";
|
|
1027
1078
|
import styled4 from "@emotion/styled";
|
|
1028
1079
|
import { jsx as jsx5, jsxs as jsxs3 } from "@emotion/react/jsx-runtime";
|
|
1029
1080
|
var OTHER_OPTION_VALUE = "__other__";
|
|
@@ -1125,10 +1176,10 @@ var PDEAIQuestionnaireCardInner = ({
|
|
|
1125
1176
|
interactive = false,
|
|
1126
1177
|
onSubmit
|
|
1127
1178
|
}) => {
|
|
1128
|
-
const [answers, setAnswers] =
|
|
1179
|
+
const [answers, setAnswers] = useState2(
|
|
1129
1180
|
() => createInitialAnswers(questionnaire)
|
|
1130
1181
|
);
|
|
1131
|
-
const [errorMessage, setErrorMessage] =
|
|
1182
|
+
const [errorMessage, setErrorMessage] = useState2(null);
|
|
1132
1183
|
const handleSubmit = () => {
|
|
1133
1184
|
const missingQuestions = questionnaire.questions.filter(
|
|
1134
1185
|
(question) => question.required && isMissingRequiredAnswer(question, answers)
|
|
@@ -1756,17 +1807,19 @@ var ChatMessageItemView = ({
|
|
|
1756
1807
|
renderMessageBlock
|
|
1757
1808
|
}) => {
|
|
1758
1809
|
const { labels } = useChatContext();
|
|
1759
|
-
const [activeImage, setActiveImage] =
|
|
1810
|
+
const [activeImage, setActiveImage] = useState3(void 0);
|
|
1760
1811
|
const { displayedContent, freshContent, isAssistantStreaming, settledContent } = useChatMessageReveal(message);
|
|
1761
1812
|
const isStoppedAssistant = message.role === "assistant" && message.status === "stopped";
|
|
1762
1813
|
const attachments = message.attachments ?? [];
|
|
1763
1814
|
const blocks = message.blocks ?? [];
|
|
1764
1815
|
const hasStructuredBlocks = blocks.length > 0;
|
|
1816
|
+
const hasMarkdownOnlyBlocks = hasStructuredBlocks && blocks.every((block) => block.type === "markdown");
|
|
1765
1817
|
const hasTextContent = Boolean(settledContent || freshContent || displayedContent);
|
|
1818
|
+
const shouldRenderStructuredBlocks = hasStructuredBlocks && !(isAssistantStreaming && hasMarkdownOnlyBlocks && hasTextContent);
|
|
1766
1819
|
const isPlanMode = mode === "plan";
|
|
1767
1820
|
const canSubmitConfirmation = isPlanMode && typeof onConfirmationSubmit === "function";
|
|
1768
1821
|
const canSubmitQuestionnaire = isPlanMode && typeof onQuestionnaireSubmit === "function";
|
|
1769
|
-
const shouldShowStreamingCaret = isAssistantStreaming && (!
|
|
1822
|
+
const shouldShowStreamingCaret = isAssistantStreaming && (!shouldRenderStructuredBlocks || hasTextContent);
|
|
1770
1823
|
const renderChatMessageBlock = (block, index) => {
|
|
1771
1824
|
switch (block.type) {
|
|
1772
1825
|
case "markdown":
|
|
@@ -1846,8 +1899,8 @@ var ChatMessageItemView = ({
|
|
|
1846
1899
|
isStoppedAssistant ? /* @__PURE__ */ jsx8(StatusTag, { "data-testid": "chat-message-stopped-tag", children: labels.stoppedResponse }) : null
|
|
1847
1900
|
] }),
|
|
1848
1901
|
/* @__PURE__ */ jsxs5(Content, { "data-testid": "chat-message-content", children: [
|
|
1849
|
-
|
|
1850
|
-
|
|
1902
|
+
shouldRenderStructuredBlocks || hasTextContent ? /* @__PURE__ */ jsxs5(ContentStack, { "data-testid": "chat-message-body-stack", children: [
|
|
1903
|
+
shouldRenderStructuredBlocks ? blocks.map((block, index) => /* @__PURE__ */ jsx8(
|
|
1851
1904
|
ContentSegment,
|
|
1852
1905
|
{
|
|
1853
1906
|
"data-testid": "chat-message-content-segment",
|
|
@@ -2233,7 +2286,7 @@ var ChatThreadView = ({
|
|
|
2233
2286
|
const latestUserMessageRef = useRef4(null);
|
|
2234
2287
|
const pendingScrollUserMessageIdRef = useRef4(void 0);
|
|
2235
2288
|
const reservedSpaceFrameRef = useRef4(null);
|
|
2236
|
-
const [latestUserMessageReservedSpace, setLatestUserMessageReservedSpace] =
|
|
2289
|
+
const [latestUserMessageReservedSpace, setLatestUserMessageReservedSpace] = useState4({ messageId: void 0, value: 0 });
|
|
2237
2290
|
const reservedPaddingBottom = 24 + (latestUserMessageReservedSpace.messageId === latestUserMessageId ? latestUserMessageReservedSpace.value : 0);
|
|
2238
2291
|
const measureLatestUserMessageReservedSpace = useCallback2((messageId) => {
|
|
2239
2292
|
const container = containerRef.current;
|
|
@@ -2559,10 +2612,10 @@ var resolveSendSession = ({
|
|
|
2559
2612
|
};
|
|
2560
2613
|
|
|
2561
2614
|
// src/components/chat-composer/hooks/use-chat-composer.ts
|
|
2562
|
-
import { useCallback as useCallback3, useEffect as useEffect4, useRef as useRef6, useState as
|
|
2615
|
+
import { useCallback as useCallback3, useEffect as useEffect4, useRef as useRef6, useState as useState6 } from "react";
|
|
2563
2616
|
|
|
2564
2617
|
// src/components/chat-composer/hooks/use-composer-attachments.ts
|
|
2565
|
-
import { useEffect as useEffect3, useRef as useRef5, useState as
|
|
2618
|
+
import { useEffect as useEffect3, useRef as useRef5, useState as useState5 } from "react";
|
|
2566
2619
|
var SUPPORTED_IMAGE_MIME_TYPES = /* @__PURE__ */ new Set(["image/png", "image/jpeg", "image/webp"]);
|
|
2567
2620
|
var MAX_COMPOSER_ATTACHMENTS = 10;
|
|
2568
2621
|
var createObjectUrl = (file) => typeof URL !== "undefined" && typeof URL.createObjectURL === "function" ? URL.createObjectURL(file) : "";
|
|
@@ -2576,7 +2629,7 @@ var releaseComposerAttachments = (attachments) => {
|
|
|
2576
2629
|
attachments.forEach((attachment) => revokeObjectUrl(attachment.previewUrl));
|
|
2577
2630
|
};
|
|
2578
2631
|
var useComposerAttachments = () => {
|
|
2579
|
-
const [attachments, setAttachments] =
|
|
2632
|
+
const [attachments, setAttachments] = useState5([]);
|
|
2580
2633
|
const attachmentsRef = useRef5([]);
|
|
2581
2634
|
useEffect3(() => {
|
|
2582
2635
|
attachmentsRef.current = attachments;
|
|
@@ -2694,9 +2747,9 @@ var useChatComposer = () => {
|
|
|
2694
2747
|
const clearSessionError = useChatStore((s) => s.clearSessionError);
|
|
2695
2748
|
const setPreferredMode = useChatStore((s) => s.setPreferredMode);
|
|
2696
2749
|
const setSessionMode = useChatStore((s) => s.setSessionMode);
|
|
2697
|
-
const [availableModels, setAvailableModels] =
|
|
2698
|
-
const [isModelsLoading, setIsModelsLoading] =
|
|
2699
|
-
const [isModelsError, setIsModelsError] =
|
|
2750
|
+
const [availableModels, setAvailableModels] = useState6([]);
|
|
2751
|
+
const [isModelsLoading, setIsModelsLoading] = useState6(true);
|
|
2752
|
+
const [isModelsError, setIsModelsError] = useState6(false);
|
|
2700
2753
|
const fetchModels = useCallback3(async () => {
|
|
2701
2754
|
setIsModelsLoading(true);
|
|
2702
2755
|
setIsModelsError(false);
|
|
@@ -2713,10 +2766,10 @@ var useChatComposer = () => {
|
|
|
2713
2766
|
void fetchModels();
|
|
2714
2767
|
}, [fetchModels]);
|
|
2715
2768
|
const hasModels = availableModels.length > 0;
|
|
2716
|
-
const [value, setValue] =
|
|
2717
|
-
const [selectedModel, setSelectedModel] =
|
|
2718
|
-
const [selectedMode, setSelectedModeLocal] =
|
|
2719
|
-
const [attachmentNotice, setAttachmentNotice] =
|
|
2769
|
+
const [value, setValue] = useState6("");
|
|
2770
|
+
const [selectedModel, setSelectedModel] = useState6("");
|
|
2771
|
+
const [selectedMode, setSelectedModeLocal] = useState6(DEFAULT_CHAT_AGENT_MODE);
|
|
2772
|
+
const [attachmentNotice, setAttachmentNotice] = useState6(null);
|
|
2720
2773
|
const { attachments, appendFiles, removeAttachment, takeMessageAttachments } = useComposerAttachments();
|
|
2721
2774
|
const abortControllerRef = useRef6(null);
|
|
2722
2775
|
const stopRequestRef = useRef6(null);
|
|
@@ -3012,14 +3065,14 @@ var useChatComposer = () => {
|
|
|
3012
3065
|
};
|
|
3013
3066
|
|
|
3014
3067
|
// src/components/chat-composer/components/chat-composer-attachment-list.tsx
|
|
3015
|
-
import { useState as
|
|
3068
|
+
import { useState as useState7 } from "react";
|
|
3016
3069
|
import styled11 from "@emotion/styled";
|
|
3017
3070
|
import { Fragment as Fragment3, jsx as jsx12, jsxs as jsxs8 } from "@emotion/react/jsx-runtime";
|
|
3018
3071
|
var ChatComposerAttachmentList = ({
|
|
3019
3072
|
attachments,
|
|
3020
3073
|
onRemoveAttachment
|
|
3021
3074
|
}) => {
|
|
3022
|
-
const [activeImage, setActiveImage] =
|
|
3075
|
+
const [activeImage, setActiveImage] = useState7(null);
|
|
3023
3076
|
if (!attachments.length) {
|
|
3024
3077
|
return null;
|
|
3025
3078
|
}
|