{"record":{"id":"8cf39d491d159b64","repo":"Mintplex-Labs/anything-llm","slug":"gemini-error-this-lasterrormessage","errorCode":null,"errorMessage":"Gemini error: ${this._lastErrorMessage}","messagePattern":"Gemini error: (.+?)","errorType":"exception","errorClass":"RetryError","httpStatus":null,"severity":"warning","filePath":"server/utils/agents/aibitat/providers/gemini.js","lineNumber":355,"sourceCode":"      return {\n        textResponse: completion.content,\n        functionCall: null,\n        cost: this.getCost(),\n        uuid: msgUUID,\n      };\n    } catch (error) {\n      this.#logAPIError(error);\n      const errorMsg = this._lastErrorMessage\n        ? `Gemini error: ${this._lastErrorMessage}`\n        : error.message;\n      this._lastErrorMessage = null;\n      if (error instanceof OpenAI.AuthenticationError) throw error;\n      if (\n        error instanceof OpenAI.RateLimitError ||\n        error instanceof OpenAI.InternalServerError ||\n        error instanceof OpenAI.APIError // Also will catch AuthenticationError!!!\n      ) {\n        throw new RetryError(errorMsg);\n      }\n\n      throw error;\n    }\n  }\n\n  /**\n   * Create a completion based on the received messages.\n   *\n   * @param messages A list of messages to send to the Gemini API.\n   * @param functions\n   * @returns The completion.\n   */\n  async complete(messages, functions = []) {\n    if (!this.supportsToolCalling)\n      throw new Error(`Gemini: ${this.model} does not support tool calling.`);\n    this.providerLog(\"Gemini.complete - will process this chat completion.\");\n    this.resetUsage();","sourceCodeStart":337,"sourceCodeEnd":373,"githubUrl":"https://github.com/Mintplex-Labs/anything-llm/blob/526360e320da9d1b36074be5ed64fe76e5bbfbbd/server/utils/agents/aibitat/providers/gemini.js#L337-L373","documentation":"GeminiProvider.stream() catch block (gemini.js:343-356) builds errorMsg from _lastErrorMessage captured by the custom fetch wrapper (gemini.js:22-40, which parses the non-2xx response body), prefixes it with \"Gemini error: \", and throws RetryError for RateLimitError/InternalServerError/APIError. AuthenticationError is rethrown verbatim so credential failures do not retry. RetryError signals the AIbitat loop to re-attempt.","triggerScenarios":"Gemini returns 429 (quota/rate limit), 500/503, or a 400 APIError such as a missing thought_signature (extra_content) on a multi-turn tool result. The fetch wrapper captured the body message, which is what surfaces here.","commonSituations":"Free-tier quota exhaustion, high request rate, sending tool results back without the Gemini-required thought_signature, or a malformed tool payload that Gemini rejects with APIError.","solutions":["Read the full \"Gemini error: ...\" text and _lastErrorMessage to find the exact upstream cause.","Reduce request rate or add backoff when the cause is 429/quota.","Verify billing/quota status in the Google AI console.","For multi-turn tool calls, ensure the thought_signature (extra_content) from the prior call is passed back in #formatMessages.","Let the AIbitat retry loop handle transient 5xx cases."],"exampleFix":null,"handlingStrategy":"retry","validationCode":"// Before streaming, sanity-check the API key and tool payload shape.\nif (!process.env.GEMINI_API_KEY) throw new Error(\"GEMINI_API_KEY is not set.\");\nfor (const f of functions) {\n  if (!f.name || !/^[A-Za-z]/.test(f.name))\n    throw new Error(`Tool name ${f.name} is invalid for Gemini.`);\n}","typeGuard":null,"tryCatchPattern":"const { RetryError } = require(\"./server/utils/agents/aibitat/error.js\");\ntry {\n  return await provider.stream(messages, functions, handler);\n} catch (e) {\n  if (e instanceof RetryError && /quota|rate/i.test(e.message)) {\n    await new Promise((r) => setTimeout(r, 2000));\n    return await provider.stream(messages, functions, handler);\n  }\n  throw e;\n}","preventionTips":["Pass the Gemini thought_signature (extra_content) back on every tool result.","Keep tool names alphabetic-leading (the gtc__ prefix handles this).","Watch quota in the Google AI console to avoid surprise 429s.","Log _lastErrorMessage so the real upstream cause is recoverable."],"tags":["gemini","retry","rate-limit","quota","api-error"],"backgroundTag":null,"analyzedSha":"526360e320da9d1b36074be5ed64fe76e5bbfbbd","analyzedAt":"2026-08-13T01:45:47.170Z","schemaVersion":2},"datasetVersion":"2026-08-13T04:17:16.726Z"}