invoke-ai/InvokeAI · warning · ExternalProviderRateLimitError
Gemini rate limit exceeded. {f'Retry after {retry_after:.0f}
Error message
Gemini rate limit exceeded. {f'Retry after {retry_after:.0f}s.' if retry_after else 'Please try again later.'} What it means
ExternalProviderRateLimitError raised by GeminiProvider.generate when Google's Gemini API responds with HTTP 429. The provider parses the Retry-After header (via _parse_retry_after) and includes a human-readable 'Retry after Ns' hint when available; otherwise it says 'Please try again later.' The retry_after value is attached to the exception for programmatic backoff.
Source
Thrown at invokeai/app/services/external_generation/providers/gemini.py:116
payload: dict[str, object] = {
"systemInstruction": {"parts": [{"text": system_instruction}]},
"contents": [{"role": "user", "parts": request_parts}],
"generationConfig": generation_config,
}
if "thinking_level" in opts:
payload["thinkingConfig"] = {"thinkingLevel": opts["thinking_level"].upper()}
response = requests.post(
endpoint,
params={"key": api_key},
json=payload,
timeout=120,
)
if not response.ok:
if response.status_code == 429:
retry_after = _parse_retry_after(response.headers.get("retry-after"))
raise ExternalProviderRateLimitError(
f"Gemini rate limit exceeded. {f'Retry after {retry_after:.0f}s.' if retry_after else 'Please try again later.'}",
retry_after=retry_after,
)
raise ExternalProviderRequestError(
f"Gemini request failed with status {response.status_code} for model '{model_id}': {response.text}"
)
data = response.json()
if not isinstance(data, dict):
raise ExternalProviderRequestError("Gemini response payload was not a JSON object")
images: list[ExternalGeneratedImage] = []
text_parts: list[str] = []
finish_messages: list[str] = []
candidates = data.get("candidates")
if not isinstance(candidates, list):
raise ExternalProviderRequestError("Gemini response payload missing candidates")
for candidate in candidates:
if not isinstance(candidate, dict):View on GitHub (pinned to 0b6a024f2f)
Solutions
- Catch ExternalProviderRateLimitError and wait at least e.retry_after seconds before retrying (exponential backoff if unset).
- Reduce request rate: serialize generations, add delays, or lower candidateCount/num_images per request.
- Upgrade the Google AI Studio plan or request a quota increase for the generateContent/image quota.
- Rotate to a different API key or region if multiple clients share one quota.
Example fix
// before: blind retry amplifies 429s
while True:
try:
return provider.generate(request)
except Exception:
continue
// after: honor Retry-After from the typed rate-limit error
import time
try:
return provider.generate(request)
except ExternalProviderRateLimitError as e:
time.sleep(e.retry_after if e.retry_after else 30)
return provider.generate(request) Defensive patterns
Strategy: retry
Try / catch
import time
for attempt in range(3):
try:
return provider.generate(request)
except ExternalProviderRateLimitError as e:
wait = e.retry_after if e.retry_after else 2 ** attempt * 5
time.sleep(wait)
raise # give up after 3 attempts Prevention
- Throttle generation requests below your Gemini quota (requests/min).
- Queue image generations instead of firing them in parallel loops.
- Monitor quota usage in Google AI Studio and request increases proactively.
- Handle the typed ExternalProviderRateLimitError separately from generic request errors so Retry-After is honored.
When it happens
Trigger: POST to {base_url}/models/{model_id}:generateContent returns status 429. Happens when per-minute/per-day quotas for the API key are exhausted, free-tier RPM limits are hit, or the model (e.g. image-generation models) has stricter quotas than the account allows.
Common situations: Batch generating many images in a loop; free-tier Gemini key with low RPM; multiple InvokeAI clients sharing one API key; image models with very low quota; burst of retrying clients amplifying load.
Related errors
- Rate limit exceeded after all retries
- Gemini API key is not configured
- Gemini request failed with status {response.status_code} for
- Gemini response payload was not a JSON object
- Gemini response payload missing candidates
AI-assisted analysis of invoke-ai/InvokeAI@0b6a024f2f (2026-08-29).
Data as JSON: /api/errors/b3f409c2a8b5cc4b.
Report an issue: GitHub.