From 5d3e7d5aaa8a5301fa5937bcd1bd7d3557c60c6f Mon Sep 17 00:00:00 2001 From: Mario Zechner Date: Fri, 16 Jan 2026 23:42:39 +0100 Subject: [PATCH] fix(ai): preserve unsigned tool call context for Gemini 3 with anti-mimicry note Instead of skipping unsigned tool calls entirely (which lobotomizes context), convert them to text with an explicit note telling the model this is historical context from a different model and not a format to mimic. This preserves tool call/result context when switching from providers without thought signatures (e.g. Claude via Antigravity) to Gemini 3. --- packages/ai/src/providers/google-shared.ts | 3 ++- .../ai/test/google-shared-gemini3-unsigned-tool-call.test.ts | 5 ++++- 2 files changed, 6 insertions(+), 2 deletions(-) diff --git a/packages/ai/src/providers/google-shared.ts b/packages/ai/src/providers/google-shared.ts index deb920d4..583c0d97 100644 --- a/packages/ai/src/providers/google-shared.ts +++ b/packages/ai/src/providers/google-shared.ts @@ -135,11 +135,12 @@ export function convertMessages(model: Model, contex // Gemini 3 requires thoughtSignature on all function calls when thinking mode is enabled. // When replaying history from providers without thought signatures (e.g. Claude via Antigravity), // convert unsigned function calls to text to avoid API validation errors. + // We include a note telling the model this is historical context to prevent mimicry. const isGemini3 = model.id.toLowerCase().includes("gemini-3"); if (isGemini3 && !thoughtSignature) { const argsStr = JSON.stringify(block.arguments, null, 2); parts.push({ - text: `[Tool Call: ${block.name}]\nArguments: ${argsStr}`, + text: `[Historical context: a different model called tool "${block.name}" with arguments: ${argsStr}. Do not mimic this format - use proper function calling.]`, }); } else { const part: Part = { diff --git a/packages/ai/test/google-shared-gemini3-unsigned-tool-call.test.ts b/packages/ai/test/google-shared-gemini3-unsigned-tool-call.test.ts index d0f4b43b..e773a6a6 100644 --- a/packages/ai/test/google-shared-gemini3-unsigned-tool-call.test.ts +++ b/packages/ai/test/google-shared-gemini3-unsigned-tool-call.test.ts @@ -63,7 +63,10 @@ describe("google-shared convertMessages", () => { expect(toolTurn?.parts?.some((p) => p.functionCall !== undefined)).toBe(false); const text = toolTurn?.parts?.map((p) => p.text ?? "").join("\n"); - expect(text).toContain("[Tool Call: bash]"); + // Should contain historical context note to prevent mimicry + expect(text).toContain("Historical context"); + expect(text).toContain("bash"); expect(text).toContain("ls -la"); + expect(text).toContain("Do not mimic this format"); }); });