diff --git a/src/gateway/server-methods/chat.ts b/src/gateway/server-methods/chat.ts index 660d3eedf4e..5f7bd493f64 100644 --- a/src/gateway/server-methods/chat.ts +++ b/src/gateway/server-methods/chat.ts @@ -21,7 +21,10 @@ import { normalizeInputProvenance, type InputProvenance } from "../../sessions/i import { resolveSendPolicy } from "../../sessions/send-policy.js"; import { parseAgentSessionKey } from "../../sessions/session-key-utils.js"; import { emitSessionTranscriptUpdate } from "../../sessions/transcript-events.js"; -import { resolveAssistantMessagePhase } from "../../shared/chat-message-content.js"; +import { + parseAssistantTextSignature, + resolveAssistantMessagePhase, +} from "../../shared/chat-message-content.js"; import { stripInlineDirectiveTagsForDisplay, stripInlineDirectiveTagsFromMessageForDisplay, @@ -685,6 +688,38 @@ function sanitizeChatHistoryContentBlock( return { block: changed ? entry : block, changed }; } +function sanitizeAssistantPhasedContentBlocks(content: unknown[]): { + content: unknown[]; + changed: boolean; +} { + const hasExplicitPhasedText = content.some((block) => { + if (!block || typeof block !== "object") { + return false; + } + const entry = block as { type?: unknown; textSignature?: unknown }; + return ( + entry.type === "text" && Boolean(parseAssistantTextSignature(entry.textSignature)?.phase) + ); + }); + if (!hasExplicitPhasedText) { + return { content, changed: false }; + } + const filtered = content.filter((block) => { + if (!block || typeof block !== "object") { + return true; + } + const entry = block as { type?: unknown; textSignature?: unknown }; + if (entry.type !== "text") { + return true; + } + return parseAssistantTextSignature(entry.textSignature)?.phase === "final_answer"; + }); + return { + content: filtered, + changed: filtered.length !== content.length, + }; +} + /** * Validate that a value is a finite number, returning undefined otherwise. */ @@ -823,6 +858,13 @@ function sanitizeChatHistoryMessage( entry.content = updated.map((item) => item.block); changed = true; } + if (entry.role === "assistant" && Array.isArray(entry.content)) { + const sanitizedPhases = sanitizeAssistantPhasedContentBlocks(entry.content); + if (sanitizedPhases.changed) { + entry.content = sanitizedPhases.content; + changed = true; + } + } } if (typeof entry.text === "string") {