Skip to content

Antigravity+Gemini 400s on propertyNames; MCP initialized notification carries an id #754

Description

@kombalarasoftware-cmd

Two independent defects found on a Windows v0.66.0 (b45bb9b52) install running Antigravity + Gemini with @playwright/mcp and serena attached. Both reproduce on master. Patch at the bottom is built and verified locally.

1. Antigravity + Gemini rejects every turn (HTTP 400)

Antigravity generateContent failed (HTTP 400 Bad Request):
"Invalid JSON payload received. Unknown name \"propertyNames\" at
 'request.tools[0].function_declarations[32].parameters.properties[0].value':
 Cannot find field."

antigravity_compatible_schema returns Gemini schemas unchanged:

// crates/jcode-provider-antigravity/src/lib.rs
/// Gemini is the backend's native path and accepts every JSON Schema construct
/// jcode emits, so no schema rewriting is needed for these models.
pub fn antigravity_compatible_schema(schema: &Value, model: &str) -> Value {
    if model_is_gemini(model) {
        return schema.clone();
    }

That premise does not hold — generateContent rejects propertyNames. Since one bad tool fails the entire request, any MCP server exposing such a schema breaks every turn on Antigravity + Gemini. @playwright/mcp's browser_drop is one:

"data": {
  "type": "object",
  "additionalProperties": {"type": "string"},
  "propertyNames": {"type": "string"},
  "description": "Data to drop, as a map of MIME type to string value..."
}

The native Gemini provider has the same gap — GEMINI_UNSUPPORTED_SCHEMA_KEYS in crates/jcode-provider-gemini/src/lib.rs strips additionalProperties, $schema, $id, $ref, $defs, definitions, $comment, but not propertyNames.

I kept the new key list deliberately narrow. Across the 61 MCP tools on this install, additionalProperties appears 29 times and $schema is present; both are accepted by this endpoint in live requests, so only the keyword actually observed to 400 is stripped.

Related: #687 (same class of problem, OpenAI + uniqueItems).

2. notifications/initialized is sent with id: 0

// crates/jcode-base/src/mcp/client.rs:315
let notif = JsonRpcRequest::new(0, "notifications/initialized", None);

JsonRpcRequest.id is a plain u64 (protocol.rs:10), not Option, so it always serializes. jcode puts this on the wire:

{"jsonrpc":"2.0","id":0,"method":"notifications/initialized"}

A JSON-RPC notification must not carry an id. Servers on the Python MCP SDK parse it as a request and fail validation against every ClientRequest variant:

WARNING root:_receive_loop - Failed to validate request: 15 validation errors for ClientRequest
Input should be 'tools/list' [type=literal_error, input_value='notifications/initialized', input_type=str]
Input should be 'tools/call' [type=literal_error, input_value='notifications/initialized', input_type=str]
Field required [type=missing, input_value={'method': 'notifications...sonrpc': '2.0', 'id': 0}]
...

Non-fatal — serena still serves its tools — but it is ~130 log lines per connection, and a stricter server would be entitled to reject the handshake. This is the only notifications/ send site in the tree.

Verification

Built both fixes on top of v0.66.0 and ran against the real backend with browser_drop re-enabled and a forced mcp__serena__get_current_config call so serena fully initializes:

before after
HTTP 400 every turn 0
literal_error (serena validation) ~130 per connect 0
Failed to validate request every connect 0

cargo build --release clean.

Patch

I could not open a PR (this repo limits PRs to collaborators), so the branch is
on a fork if it is useful as a reference:

master...kombalarasoftware-cmd:jcode:local/mcp-notification-and-gemini-schema

crates/jcode-base/src/mcp/client.rs          | 10 ++++++--
crates/jcode-provider-antigravity/src/lib.rs | 38 +++++++++++++++++++++++-----
crates/jcode-provider-gemini/src/lib.rs      |  1 +

Per CONTRIBUTING.md I am treating this as a reference rather than a change to
merge — the Antigravity + Gemini half is environment-specific (Windows, a
Gemini-backed Antigravity account, an MCP server exposing propertyNames), so
the branch mainly documents the behavior in the environment where it occurs.
Happy to add a unit test for strip_gemini_unsupported_keys and a
serialization assertion for the notification if that helps.

Metadata

Metadata

Assignees

No one assigned

    Labels

    autonomous: clearHands-off: unambiguous bug, obvious fix, no decisions. Don't even look - an agent can fully solve.bugSomething isn't workingpriority: highP1 - important bug or impactful feature, fix soonrecurring-themePart of a recurring class of bugs across issues; worth a deeper look at the root causetriage: reproducibleClear repro + clear fix path

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions