Conversation
…alid 200s (diegosouzapw#14160) An empty completion from antigravity's Gemini can be a real answer: some prompts legitimately produce no text, and the upstream reports a normal terminal finish reason (STOP -> "stop"). The fake-success guard in isEmptyContentResponse flagged these regardless, so the non-streaming leg rewrote them into synthetic 502s that fed model lockout — a few hundred such "failures" a day kept most of the reporter's 22-connection pool excluded and starved unrelated clients. The guard exists for free-tier/scraping providers whose failure mode is an empty 200 shell (diegosouzapw#13461), so scope the exemption the same way the repo scopes classifyFakeSuccessBody: a trusted-provider allowlist. On antigravity, an empty completion with a normal stop reason (openai "stop", claude "end_turn") now passes through as a valid 200; every other provider keeps the existing guard, and antigravity responses with no terminal stop reason are still flagged.
This was referenced Sep 20, 2026
Open
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
What
An empty (but successful) completion from antigravity's Gemini is treated as a provider failure: the client gets
502 Provider returned empty contentand the model is locked out on that account. The reporter sees ~400 of these a day from a single observer prompt the model legitimately answers with no text, which keeps most of a 22-connection pool excluded and starves unrelated clients (their words: a cheap harmless request was starving the expensive ones).The fake-success guard exists for free-tier/scraping providers whose failure mode is an empty 200 shell (#13461). Antigravity is Google's first-party Gemini API: an empty candidate with
finishReason: STOPis a real result, and retrying the same prompt on the next account returns the same empty answer anyway.Changes
isEmptyContentResponse()gains an optionalproviderand aTRUSTED_EMPTY_STOP_PROVIDERSallowlist (same pattern as the provider-allowlistedclassifyFakeSuccessBodyfrom [BUG] Gateway returning bad response #13461). On antigravity, an empty completion with a normal terminal stop reason (openaistop, claudeend_turn) is no longer flagged.providerthrough, so these completions flow to the client as a valid 200 with empty content instead of a synthetic 502. No failure accounting, no model lockout, and no retrying the same prompt on the next account to get the same empty answer.Unchanged: every other provider keeps the guard, including on empty stop completions; antigravity responses with no terminal stop reason are still flagged; the existing legit-empty carve-outs (
length,tool_calls,content_filter,max_tokens,tool_use) are untouched.Verification
tests/unit/14160-antigravity-empty-stop-completion.test.ts, 5 cases: antigravity empty+stop and empty+end_turn pass through; untrusted providers and the no-provider call keep flagging them; an antigravity empty shell with no finish reason is still flagged; existing carve-outs unchanged.combo-empty-content-failover-5085,diagnostics-fake-success-13461,copilot-m365-web-silent-empty-7858,zai-web-silent-empty-repro).prettier --check,eslint,typecheck:coreclean on all touched files.Out of scope: the streaming variant (#13600) is a different code path (
streamEmptyChoices.ts) and is not touched here. If you'd rather have the passthrough behind a settings toggle, happy to add one.Fixes #14160