fixed chat
This commit is contained in:
+29
-24
@@ -44,9 +44,9 @@ export default function Chat() {
|
||||
const [input, setInput] = useState("");
|
||||
const [loading, setLoading] = useState(false);
|
||||
const [streaming, setStreaming] = useState("");
|
||||
const [pendingPhase, setPendingPhase] = useState<"thinking" | "preparing" | "generating">(
|
||||
"thinking",
|
||||
);
|
||||
const [pendingPhase, setPendingPhase] = useState<
|
||||
"thinking" | "preparing" | "generating" | "tools"
|
||||
>("thinking");
|
||||
const [liveNotices, setLiveNotices] = useState<string[]>([]);
|
||||
const [chatError, setChatError] = useState<string | null>(null);
|
||||
const messagesRef = useRef<HTMLDivElement>(null);
|
||||
@@ -54,6 +54,7 @@ export default function Chat() {
|
||||
const scrollRafRef = useRef<number | null>(null);
|
||||
const { status: pomodoroStatus, refresh: refreshPomodoro } = usePomodoro();
|
||||
const [lastNotifySeq, setLastNotifySeq] = useState(0);
|
||||
const pendingHistoryReload = useRef(false);
|
||||
|
||||
const loadSessions = async () => {
|
||||
const data = await api.listSessions();
|
||||
@@ -108,22 +109,27 @@ export default function Chat() {
|
||||
|
||||
const waitingForStream = loading && !streaming;
|
||||
const pendingLabel =
|
||||
liveNotices.length > 0
|
||||
? "Обрабатываю…"
|
||||
: pendingPhase === "preparing"
|
||||
? "Собираю контекст…"
|
||||
: pendingPhase === "generating"
|
||||
? "Генерирую ответ…"
|
||||
: "Думаю…";
|
||||
pendingPhase === "tools"
|
||||
? "Выполняю команды…"
|
||||
: liveNotices.length > 0
|
||||
? "Обрабатываю…"
|
||||
: pendingPhase === "preparing"
|
||||
? "Собираю контекст…"
|
||||
: pendingPhase === "generating"
|
||||
? "Генерирую ответ…"
|
||||
: "Думаю…";
|
||||
|
||||
useEffect(() => {
|
||||
const seq = pomodoroStatus?.cycle?.chat_notify_seq ?? 0;
|
||||
if (seq > lastNotifySeq) {
|
||||
setLastNotifySeq(seq);
|
||||
refreshPomodoro().catch(console.error);
|
||||
// Не перезагружать историю во время стрима — ломает UI и сбивает ответ.
|
||||
if (activeId && !loading) {
|
||||
loadMessages(activeId).catch(console.error);
|
||||
if (activeId) {
|
||||
if (loading) {
|
||||
pendingHistoryReload.current = true;
|
||||
} else {
|
||||
loadMessages(activeId).catch(console.error);
|
||||
}
|
||||
}
|
||||
}
|
||||
}, [pomodoroStatus?.cycle?.chat_notify_seq, activeId, lastNotifySeq, refreshPomodoro, loading]);
|
||||
@@ -178,9 +184,15 @@ export default function Chat() {
|
||||
if (chunk.data.phase === "generating") {
|
||||
setPendingPhase("generating");
|
||||
}
|
||||
if (chunk.data.phase === "tools") {
|
||||
setPendingPhase("tools");
|
||||
assistantText = "";
|
||||
setStreaming("");
|
||||
}
|
||||
}
|
||||
if (chunk.event === "token") {
|
||||
assistantText += chunk.data.content;
|
||||
setPendingPhase("generating");
|
||||
setStreaming(assistantText);
|
||||
}
|
||||
if (chunk.event === "notice") {
|
||||
@@ -196,17 +208,6 @@ export default function Chat() {
|
||||
setStreaming("");
|
||||
setLiveNotices([]);
|
||||
setChatError(null);
|
||||
if (assistantText.trim()) {
|
||||
setMessages((prev) => [
|
||||
...prev,
|
||||
{
|
||||
id: Date.now(),
|
||||
role: "assistant",
|
||||
content: assistantText,
|
||||
created_at: new Date().toISOString(),
|
||||
},
|
||||
]);
|
||||
}
|
||||
await loadMessages(activeId);
|
||||
await loadSessions();
|
||||
}
|
||||
@@ -224,6 +225,10 @@ export default function Chat() {
|
||||
}
|
||||
} finally {
|
||||
setLoading(false);
|
||||
if (pendingHistoryReload.current && activeId) {
|
||||
pendingHistoryReload.current = false;
|
||||
loadMessages(activeId).catch(console.error);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
Reference in New Issue
Block a user