diff --git a/ui/suite/chat/chat.html b/ui/suite/chat/chat.html
index 8aafb39..0986036 100644
--- a/ui/suite/chat/chat.html
+++ b/ui/suite/chat/chat.html
@@ -816,33 +816,36 @@ function finalizeStreaming() {
}
function processMessage(data) {
- // If content is a JSON string or contains it, try to intercept internal signals
- if (data.content && typeof data.content === "string") {
- var jsonStart = data.content.indexOf('{"type":"thinking');
- if (jsonStart !== -1) {
+ // If content contains JSON signals, extract and handle them
+ if (data.content && typeof data.content === "string" && data.content.includes('{')) {
+ var signalRegex = /\{[^{}]*"type"\s*:\s*"(thinking|thinking_clear)"[^{}]*\}/g;
+ var match;
+ var hasAnySignal = false;
+
+ while ((match = signalRegex.exec(data.content)) !== null) {
try {
- // Extract only the JSON part
- var remaining = data.content.substring(jsonStart);
- var jsonEnd = remaining.indexOf("}") + 1;
- if (jsonEnd > 0) {
- var jsonStr = remaining.substring(0, jsonEnd);
- var inner = JSON.parse(jsonStr);
-
- if (inner.type === "thinking") {
- showThinkingIndicator(inner.content);
- // If there is text before or after, keep processing that as content
- data.content = data.content.replace(jsonStr, "").trim();
- if (data.content === "") return;
- } else if (inner.type === "thinking_clear") {
- hideThinkingIndicator();
- data.content = data.content.replace(jsonStr, "").trim();
- if (data.content === "") return;
- }
+ var jsonStr = match[0];
+ var inner = JSON.parse(jsonStr);
+ hasAnySignal = true;
+
+ if (inner.type === "thinking") {
+ showThinkingIndicator(inner.content);
+ } else if (inner.type === "thinking_clear") {
+ hideThinkingIndicator();
}
+
+ // Remove this signal from the content
+ data.content = data.content.replace(jsonStr, "");
+ // Reset regex index since we modified the string
+ signalRegex.lastIndex = 0;
} catch (e) {
- console.error("Failed to parse embedded signal:", e);
+ console.error("Failed to parse signal:", e);
}
}
+
+ if (hasAnySignal && data.content.trim() === "" && !data.is_complete) {
+ return;
+ }
}
// Fallback for direct type matches