{"record":{"id":"781fb9e75d79d51b","repo":"NousResearch/hermes-agent","slug":"gemini-invalid-json","errorCode":"gemini_invalid_json","errorMessage":"Invalid JSON from Gemini native API: {exc}","messagePattern":"Invalid JSON from Gemini native API: (.+?)","errorType":"exception","errorClass":"GeminiAPIError","httpStatus":null,"severity":"error","filePath":"agent/gemini_native_adapter.py","lineNumber":1064,"sourceCode":"            temperature=temperature,\n            max_tokens=max_tokens,\n            top_p=top_p,\n            stop=stop,\n            thinking_config=thinking_config,\n        )\n\n        model = bare_gemini_model_id(model)\n        if stream:\n            return self._stream_completion(model=model, request=request, timeout=timeout)\n\n        url = f\"{self.base_url}/models/{model}:generateContent\"\n        response = self._http.post(url, json=request, headers=self._headers(), timeout=timeout)\n        if response.status_code != 200:\n            raise gemini_http_error(response)\n        try:\n            payload = response.json()\n        except ValueError as exc:\n            raise GeminiAPIError(\n                f\"Invalid JSON from Gemini native API: {exc}\",\n                code=\"gemini_invalid_json\",\n                status_code=response.status_code,\n                response=response,\n            ) from exc\n        return translate_gemini_response(payload, model=model)\n\n    def _stream_completion(self, *, model: str, request: Dict[str, Any], timeout: Any = None) -> Iterator[_GeminiStreamChunk]:\n        url = f\"{self.base_url}/models/{model}:streamGenerateContent?alt=sse\"\n        stream_headers = dict(self._headers())\n        stream_headers[\"Accept\"] = \"text/event-stream\"\n\n        def _generator() -> Iterator[_GeminiStreamChunk]:\n            try:\n                with self._http.stream(\"POST\", url, json=request, headers=stream_headers, timeout=timeout) as response:\n                    if response.status_code != 200:\n                        body_text = read_streaming_error_body(response)\n                        raise gemini_http_error(response, body_text=body_text)","sourceCodeStart":1046,"sourceCodeEnd":1082,"githubUrl":"https://github.com/NousResearch/hermes-agent/blob/c896c09c42910c584c4c7d2325b58c14713ea42c/agent/gemini_native_adapter.py#L1046-L1082","documentation":"A non-streaming call to the Gemini native generateContent endpoint returned HTTP 200 but the body was not valid JSON (response.json() raised ValueError). This is wrapped in GeminiAPIError with code 'gemini_invalid_json' and carries the HTTP status and response, distinguishing a malformed-payload failure from transport or HTTP-status errors.","triggerScenarios":"POST {base_url}/models/{model}:generateContent returns 200 with a non-JSON body — e.g. an HTML error page from a proxy, a truncated body, or an intermediary (corporate proxy, custom base_url endpoint) that mangles responses.","commonSituations":"Custom base_url pointing at a gateway/relay that returns HTML on some paths; Captcha/auth-wall pages from intercepted networks; transient truncated responses; wrong endpoint configuration routing to a web UI instead of the API.","solutions":["If using a custom base_url for Gemini, verify it points at a Generative Language-compatible API, not a web UI.","Retry once — truncated/transient malformed bodies are occasionally one-off network faults.","Inspect the captured response (on GeminiAPIError.response) to see what was actually returned (often an HTML error page naming the culprit).","Bypass intermediaries (VPN, corporate proxy) to confirm they are not rewriting responses."],"exampleFix":null,"handlingStrategy":"retry","validationCode":null,"typeGuard":null,"tryCatchPattern":"from agent.gemini_native_adapter import GeminiAPIError\n\ntry:\n    result = client.chat.completions.create(model=m, messages=msgs)\nexcept GeminiAPIError as e:\n    if e.code == 'gemini_invalid_json':\n        # inspect e.response (often an HTML proxy page); fix base_url or retry once\n        ...","preventionTips":["Point custom base_url at a real Gemini-compatible API endpoint","Watch for corporate proxies returning HTML on API paths","Check e.response content on first occurrence to identify the intermediary"],"tags":["gemini","json","http","proxy"],"backgroundTag":null,"analyzedSha":"c896c09c42910c584c4c7d2325b58c14713ea42c","analyzedAt":"2026-08-14T17:18:01.089Z","schemaVersion":2},"datasetVersion":"2026-08-15T22:17:37.221Z"}