Skip to content

fix(google_genai): strip id from FunctionCall/FunctionResponse wire format#1582

Merged
RealKai42 merged 3 commits intoMoonshotAI:mainfrom
n-WN:fix/gemini-strip-function-call-id
Mar 25, 2026
Merged

fix(google_genai): strip id from FunctionCall/FunctionResponse wire format#1582
RealKai42 merged 3 commits intoMoonshotAI:mainfrom
n-WN:fix/gemini-strip-function-call-id

Conversation

@n-WN
Copy link
Copy Markdown
Collaborator

@n-WN n-WN commented Mar 25, 2026

Related Issue

N/A — discovered through manual testing with Gemini models via third-party proxy endpoints.

Description

Gemini API returns HTTP 400 when id is included in FunctionCall or FunctionResponse parts of the request body. This causes all Gemini models to crash after the first tool call — the first step succeeds, but the second step (which replays the conversation history containing function_call with id) is rejected by the API.

Root Cause

message_to_google_genai() and _tool_message_to_function_response_part() passed id=... to FunctionCall() / FunctionResponse() constructors. The google-genai SDK accepts the kwarg, but the Gemini REST API rejects it on the wire:

400: Invalid JSON payload received.
  Unknown name "id" at 'contents[1].parts[0].function_call': Cannot find field.
  Unknown name "id" at 'contents[2].parts[0].function_response': Cannot find field.

Gemini matches function calls to responses by array position, not by id (unlike OpenAI). The internal tool_call_id tracking in kosong's Message objects is unaffected — only the outbound wire format changes.

Fix

Remove id=... from FunctionCall and FunctionResponse constructors (2 lines). The SDK's model_dump(exclude_none=True) serialization automatically omits None fields, so the id key no longer appears in the wire JSON.

Manual Verification

Tested on a machine with 6 Gemini model configurations through qianxun proxy:

Model Provider Before After
gemini-3-pro-preview google_genai ❌ 400
gemini-2.5-pro google_genai ❌ 400
gemini-2.5-flash google_genai ❌ 400
gemini-3-flash-preview google_genai ❌ 400
gemini-3-pro vertexai ✅ (unaffected)
gemini-3-flash vertexai ✅ (unaffected)

Checklist

  • I have read the CONTRIBUTING document.
  • I have linked the related issue, if any.
  • I have added tests that prove my fix is effective or that my feature works.
  • I have run make gen-changelog to update the changelog.

… format

Gemini API returns HTTP 400 when `id` is included in `function_call` or
`function_response` parts. Unlike OpenAI, Gemini uses positional matching
rather than explicit IDs to pair calls with responses.

Remove `id=tool_call.id` from `FunctionCall()` and
`id=message.tool_call_id` from `FunctionResponse()` in the outbound
message conversion. The internal kosong `tool_call_id` tracking is
unchanged; only the wire format sent to Gemini is affected.

Add a dedicated test asserting neither field appears in the request body.
Copy link
Copy Markdown
Contributor

@devin-ai-integration devin-ai-integration bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

✅ Devin Review: No Issues Found

Devin Review analyzed this PR and found no potential bugs to report.

View in Devin Review to see 1 additional finding.

Open in Devin Review

@RealKai42 RealKai42 merged commit 328ef96 into MoonshotAI:main Mar 25, 2026
18 checks passed
x5iu pushed a commit to x5iu/kimi-cli that referenced this pull request Mar 25, 2026
… format (MoonshotAI#1582)

Signed-off-by: Kai <me@kaiyi.cool>
Co-authored-by: Kai <me@kaiyi.cool>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants