{"record":{"id":"2ac67e7e5970ff87","repo":"thedotmack/claude-mem","slug":"gemini-http-error-status-response-status","errorCode":null,"errorMessage":"Gemini HTTP error (status ${response.status})","messagePattern":"Gemini HTTP error \\(status (.+?)\\)","errorType":"exception","errorClass":"ServerClassifiedProviderError","httpStatus":null,"severity":"error","filePath":"src/server/generation/providers/GeminiObservationProvider.ts","lineNumber":175,"sourceCode":"        modelId: this.model,\n      };\n    }\n\n    const url = `${GEMINI_API_URL}/${encodeURIComponent(this.model)}:generateContent?key=${encodeURIComponent(this.apiKey)}`;\n\n    let response: Response;\n    try {\n      response = await this.postGenerateContent(url, prompt, signal);\n    } catch (networkError) {\n      const err = networkError instanceof Error ? networkError : new Error(String(networkError));\n      throw classifyGeminiServerError({\n        cause: err,\n      });\n    }\n\n    if (!response.ok) {\n      const bodyText = await safeReadBody(response);\n      throw classifyGeminiServerError({\n        status: response.status,\n        bodyText,\n        headers: response.headers,\n        cause: new Error(`Gemini HTTP error (status ${response.status})`),\n      });\n    }\n\n    let data: GeminiResponse;\n    try {\n      data = (await response.json()) as GeminiResponse;\n    } catch (parseError) {\n      const err = parseError instanceof Error ? parseError : new Error(String(parseError));\n      throw new ServerClassifiedProviderError('Gemini returned invalid JSON', {\n        kind: 'parse_error',\n        cause: err,\n      });\n    }\n","sourceCodeStart":157,"sourceCodeEnd":193,"githubUrl":"https://github.com/thedotmack/claude-mem/blob/d8bc9755e74915e5c3b999181e10a67c889bce2a/src/server/generation/providers/GeminiObservationProvider.ts#L157-L193","documentation":"The Gemini generateContent endpoint returned a non-2xx status. GeminiObservationProvider reads the body and calls classifyGeminiServerError with status/bodyText/headers and cause `Gemini HTTP error (status <status>)`. The Gemini classifier adds special handling: 400 without quota markers becomes 'unrecoverable' with a categorized bad-request message, and quota bodies map to rate-limit handling.","triggerScenarios":"`response.ok` is false after postGenerateContent: 400 invalid API version/model/payload, 403 key restricted, 429 quota exceeded, 5xx Google-side errors — thrown at GeminiObservationProvider.ts:172-179.","commonSituations":"Calling v1 instead of required v1beta API version, invalid or region-locked API key, exhausting free-tier requests-per-minute or per-day quota, sending unsupported payload fields.","solutions":["Check status: 429/quota → honor Retry-After and back off; 400 → fix model name and request payload (must use v1beta for Gemini 3.x models).","Verify the GEMINI/GOOGLE API key and its region/permission settings.","Reduce request rate or request a quota increase for the project.","Inspect the bodyText in the cause for Google's exact error message."],"exampleFix":"// before\nurl = 'https://generativelanguage.googleapis.com/v1/models/...';\n// after\nurl = 'https://generativelanguage.googleapis.com/v1beta/models/...';","handlingStrategy":"retry","validationCode":"if (!process.env.GEMINI_API_KEY) throw new Error('GEMINI_API_KEY not set');\nif (!/v1beta/.test(baseUrl)) throw new Error('Gemini requires v1beta API version');","typeGuard":"function isRetryableProviderError(e: unknown): boolean {\n  return typeof e === 'object' && e !== null && 'kind' in e && (e as {kind: string}).kind === 'retryable';\n}","tryCatchPattern":"try {\n  result = await geminiProvider.generate(prompt, signal);\n} catch (e) {\n  if (e.kind === 'retryable' && e.retryAfterMs) return sleep(e.retryAfterMs).then(call);\n  throw e;\n}","preventionTips":["Always use the v1beta endpoint for current Gemini models.","Track quota usage; back off on 429 and respect Retry-After.","Verify API key region eligibility and billing enabled on the project.","Read bodyText in the cause for Google's specific error message."],"tags":["gemini","google","http","api-error","quota"],"backgroundTag":"http-error-response","analyzedSha":"d8bc9755e74915e5c3b999181e10a67c889bce2a","analyzedAt":"2026-09-17T16:40:26.182Z","contentChangedAt":"2026-09-17T16:40:26.182Z","schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}