Nano Banana 2 常见错误如 429 RESOURCE_EXHAUSTED 和 502 Bad Gateway 影响 Gemini 3.1 Flash Image API(gemini-3.1-flash-image-preview)。429 错误约占所有故障的 70%,表示您已超出速率限制 — RPM 限制等待 60 秒即可重置,RPD 配额在太平洋时间午夜重置。502 错误表示 Google 服务器返回了无效响应,通常在 5-15 分钟内自行恢复。本指南涵盖所有 Nano Banana 2 错误代码,提供经过验证的速率限制数据、真实错误响应示例以及 Python 和 TypeScript 的生产级修复代码。
Nano Banana 2 与 Nano Banana Pro 错误的关键区别
如果您一直在调试 Nano Banana 错误并参考为 Nano Banana Pro 编写的指南,那么您可能正在将错误的解决方案应用于自己的问题。Nano Banana 2(模型 ID:gemini-3.1-flash-image-preview)和 Nano Banana Pro(模型 ID:gemini-3-pro-image-preview)是两个根本不同的模型,具有不同的定价结构、速率限制和错误行为。理解这些差异是正确修复错误、避免浪费调试时间的第一步。
最关键的区别在于定价。Nano Banana 2 的输入成本为每百万 token $0.25,图像生成输出成本为每百万 token $60,而 Nano Banana Pro 的输入价格为每百万 token $2.00,输出价格为每百万 token $120(ai.google.dev/pricing,2026 年 3 月 2 日验证)。这意味着 NB2 在每 token 成本上比 Pro 便宜 50-87%,单张 1K 分辨率图像使用 NB2 大约花费 $0.067,而 Pro 则需要 $0.134。这个定价差异对错误处理非常重要,因为重试策略在不同模型上的成本影响完全不同。如需了解Nano Banana 2 与 Pro 的详细对比,我们有一篇专门的文章涵盖所有技术差异。
第二个关键区别是 Nano Banana 2 被归类为"preview"(预览版)模型,这意味着它的速率限制比正式模型更严格。Google 官方文档明确指出"实验性和预览版模型具有更低的速率限制"(ai.google.dev/docs/rate-limits,2026 年 3 月 2 日)。在实际使用中,这意味着您的 Tier 1 账户在 NB2 图像生成上可能只有 10 RPM,而非预览版模型的限制可能更高。NB2 和 Pro 都没有免费的图像生成额度 — 如果您在免费层账户上看到 RESOURCE_EXHAUSTED 错误,这意味着在未启用计费的情况下,图像生成功能根本不可用。
一个让许多开发者措手不及的技术细节是多轮对话中的 thought_signature 要求。当您在对话场景中使用 Nano Banana 2,且模型在多个回合中同时生成文本和图像时,您必须在下一个请求中包含来自上一个响应的 thought_signature。如果不这样做,会导致 400 Bad Request 错误,如果您不了解这个要求,错误信息会令人困惑。这个行为在 NB2 和 Pro 上是相同的,但由于 NB2 较新,覆盖此问题的教程较少。
30 秒内诊断您的 Nano Banana 2 错误

在深入研究详细解决方案之前,请使用下面的快速参考表将您的确切错误匹配到正确的修复方法。每个 Nano Banana 2 错误都属于以下两个类别之一:可重试错误(应实现自动重试逻辑)和不可重试错误(需要先修复请求中的问题再重试)。识别您的错误属于哪个类别可以避免在错误的方向上浪费时间。
| HTTP 状态码 | 错误类型 | 原因 | 可重试? | 恢复时间 |
|---|---|---|---|---|
| 429 | RESOURCE_EXHAUSTED | 超出速率限制(RPM/RPD/TPM/IPM) | 是 | 60秒(RPM)或午夜 PT(RPD) |
| 502 | Bad Gateway | Google 上游服务器故障 | 是 | 5-15 分钟 |
| 503 | Service Unavailable | 服务器过载(高峰时段) | 是 | 30-60 分钟 |
| 500 | Internal Server Error | 意外的服务器故障 | 是 | 不定 |
| 400 | Bad Request | 参数无效或缺少 thought_signature | 否 | 修复请求内容 |
| 403 | Forbidden | API 密钥无效或地区限制 | 否 | 修复凭据 |
| 200 | IMAGE_SAFETY | 内容被安全系统过滤 | 否 | 改写提示词 |
最重要的一点是,失败的请求(返回 429、502 或 503 的请求)不会被 Google 计费。您只需为成功的图像生成付费。这意味着实现重试逻辑没有额外的成本风险,对于担心预算在错误场景中失控的开发者来说,这是一个重要的好消息。如果您的应用在重试期间遇到大量 429 错误,您的账单与这些重试从未发生时完全相同。如需了解所有 Nano Banana 模型的错误处理概览,请参阅我们的完整 Nano Banana 错误排查指南。
修复 429 RESOURCE_EXHAUSTED 错误 — 最常见的 Nano Banana 2 错误
429 RESOURCE_EXHAUSTED 是您在使用 Nano Banana 2 时遇到的最常见错误,约占所有 API 故障的 70%。此错误意味着您已达到 Google 对图像生成请求强制执行的四个速率限制维度之一。了解您具体命中了哪个限制至关重要,因为每个限制都有不同的恢复策略和等待时间。
当您收到 429 错误时,API 返回的 JSON 响应如下所示:
json{ "error": { "code": 429, "message": "Resource has been exhausted (e.g. check quota).", "status": "RESOURCE_EXHAUSTED", "details": [ { "@type": "type.googleapis.com/google.rpc.ErrorInfo", "reason": "RATE_LIMIT_EXCEEDED", "metadata": { "consumer": "projects/YOUR_PROJECT_ID", "quota_limit": "GenerateContentRequestsPerMinutePerProjectPerModel", "quota_limit_value": "10" } } ] } }
错误响应中的 metadata 字段是您最有价值的调试工具。quota_limit 字段会告诉您具体超出了哪个限制。Nano Banana 2 图像生成的四个速率限制维度是 RPM(每分钟请求数)、TPM(每分钟 token 数)、RPD(每天请求数)和 IPM(每分钟图像数)。每个维度独立运作,因此命中一个不会影响其他维度。您的 Tier 1 账户可能有 10 RPM 但 1,000 RPD — 一旦用完每日配额,您必须等到太平洋时间午夜 RPD 计数器重置,无论您还剩多少 RPM 额度。
RPM 相关 429 错误的最快修复方法是简单地等待 60 秒。RPM 计数器基于滚动一分钟窗口重置,因此在 60 秒无请求后,您的完整 RPM 配额将再次可用。然而对于 RPD 限制,等待时间要长得多 — 计数器在太平洋时间午夜(UTC-8 或夏令时 UTC-7)重置。如果您在太平洋时间上午 9 点达到 RPD 限制,除非升级您的层级,否则需要等待 15 小时。
一个常见错误是尽可能快地发送请求,依赖重试逻辑来处理 429 错误。虽然这在技术上可行(因为失败的请求不计费),但效率低下并给 Google 服务器造成不必要的负载。更好的方法是在您这边实现主动速率限制。如果您知道 Tier 1 限制是 10 RPM,将请求间隔至少 6 秒以安全地保持在限制以下。这可以在 429 错误发生之前消除大部分。关于Nano Banana Pro 429 错误排查的特定策略,许多相同的原则适用于 NB2,只是速率限制数字不同。
实现指数退避是处理任何剩余 429 错误的标准解决方案。从第一次失败后的 1 秒延迟开始,每次后续重试加倍(2秒、4秒、8秒、16秒),并添加小的随机抖动以防止多个客户端同时重试时的"惊群效应"。将最大重试延迟上限设为 60 秒用于 RPM 相关限制,如果限制似乎是基于 RPD 而非 RPM,则考虑在 5-6 次重试后放弃。
修复 502 Bad Gateway 和 503 Service Unavailable 错误
502 Bad Gateway 和 503 Service Unavailable 是服务器端错误,表明问题出在 Google 的基础设施上,而非您的请求。这些错误与 429 根本不同,因为您的代码或速率限制使用没有任何问题 — Google 的服务器要么返回了无效响应(502),要么因过载无法处理您的请求(503)。对这两种错误的正确响应是耐心等待和系统化的重试逻辑。
当您遇到 502 Bad Gateway 时,响应通常如下所示:
json{ "error": { "code": 502, "message": "Bad Gateway", "status": "UNAVAILABLE" } }
502 错误意味着位于 Google Gemini API 前端的反向代理或负载均衡器从处理您请求的上游服务器收到了无效响应。这可能在服务器部署、基础设施更新或 Google 数据中心内的瞬时网络问题期间发生。关键的认识是 502 错误几乎总是暂时性的 — 通常在 5 到 15 分钟内无需任何操作即可恢复。如果您看到持续超过 30 分钟的 502 错误,请检查 Google Cloud 状态仪表板是否有影响 Gemini API 的正在进行的服务事件。
503 Service Unavailable 遵循不同的模式。虽然 502 错误通常是短暂的瞬时故障,但 503 错误往往表明持续的服务器过载,这在高峰使用时段更常见。根据社区报告和我们自己的测试,Nano Banana 2 的峰值错误率倾向于集中在工作日 UTC 10:00 至 14:00 之间,这对应于美国早晨和欧洲下午工作时间的重叠。如果您的应用不是时间敏感型的,将图像生成请求安排在非高峰时段(UTC 凌晨或周末)可以显著降低 503 错误率。
503 响应体与 502 类似,但通常包含更多关于服务器容量的具体信息:
json{ "error": { "code": 503, "message": "The model is overloaded. Please try again later.", "status": "UNAVAILABLE" } }
对于通过 Cherry Studio、Claude Code 或 Dify 等工具使用 MCP(模型上下文协议)访问 Nano Banana 2 的用户,这些服务器端错误可能以令人困惑的方式出现,因为 MCP 层会添加自己的错误包装。如果您在 MCP 客户端中看到"upstream connection error"或"model not responding"等错误,根本原因很可能是来自 Gemini API 的 502 或 503。修复方法相同:等待并重试。Cherry Studio 用户尤其应该检查服务器日志(通常在 ~/.cherry-studio/logs/)以查看 API 的实际 HTTP 状态码,这有助于区分 MCP 层问题和实际 API 故障。
502 和 503 错误都应该使用比 429 错误更长的初始延迟的重试策略来处理。第一次重试从 5 秒延迟开始,增加到 15 秒,然后 30 秒,上限为 60 秒。由于这些错误表明服务器端压力,激进的重试实际上可能使情况更糟。在优雅地失败并向用户显示友好的错误消息(建议几分钟后重试)之前,最多允许 3-4 次重试。
修复客户端错误 — 400 Bad Request、403 Forbidden 和 IMAGE_SAFETY
客户端错误与我们上面介绍的服务器端错误根本不同,因为它们表明您的请求存在问题,重试无法修复。将同一个格式错误的请求发送一百次,会得到同样的错误一百次。您需要在再次尝试之前识别并修复请求负载、凭据或提示词中的问题。
400 Bad Request 是最多样化的客户端错误,因为它涵盖多种故障模式。对于 Nano Banana 2 来说,最常见的原因是多轮对话中缺少 thought_signature。当 NB2 返回包含思考 token 的响应时(即使您将思考可见性设置为"off"也会发生 — 无论您的偏好如何,思考 token 始终会计费),响应中包含一个 thought_signature 字段,您必须在同一对话的下一个请求中传回。以下是缺少签名时的错误示例:
json{ "error": { "code": 400, "message": "Request contains an invalid argument: thought_signature is required for multi-turn conversations with this model.", "status": "INVALID_ARGUMENT" } }
修复方法很简单但容易遗漏:从模型的响应中提取 thought_signature 并将其包含在下一个请求的 generation_config 中。如果您使用的框架或 SDK 管理对话历史,请确保它在各轮次之间保留此字段。许多流行框架(包括 LangChain 和一些 MCP 服务器实现)尚未自动处理此问题,因此您可能需要添加自定义逻辑来提取和注入签名。
其他 400 错误原因包括无效的宽高比(NB2 支持特定比例如 1:1、3:4、4:3、9:16、16:9 等 — 请查看官方文档获取完整列表)、请求不支持的图像尺寸,或发送过多的参考图像。Nano Banana 2 支持最多 14 张参考图像(10 个物体或 6 个物体加 5 个角色),超出此限制会产生带有描述性消息的 400 错误。
403 Forbidden 错误通常意味着三件事之一:您的 API 密钥无效或已被撤销、您的 Google Cloud 项目未启用 Gemini API,或者您的地理区域被限制访问该服务。修复取决于具体原因。首先,通过简单的纯文本请求(不需要计费)验证您的 API 密钥是否正确。如果文本请求有效但图像生成失败,您可能需要在项目上启用计费 — 请记住,Nano Banana 2 没有免费的图像生成层。
IMAGE_SAFETY 拦截是一个特殊类别。从传统意义上讲,这不是 HTTP 错误 — API 返回 200 OK 状态码,但响应体表明生成的图像被 Google 的安全过滤器拦截了。响应如下所示:
json{ "candidates": [ { "finishReason": "IMAGE_SAFETY", "safetyRatings": [ { "category": "HARM_CATEGORY_SEXUALLY_EXPLICIT", "probability": "HIGH", "blocked": true } ] } ] }
当此情况发生时,模型尝试生成了图像,但输出在交付前被标记。被安全拦截的生成不会收费。要解决此问题,请改写您的提示词以避免触发安全过滤器的内容。添加明确的风格指导,如"专业照片"、"编辑风格"或"简洁的插图"可以帮助引导模型远离可能被标记的内容。避免使用可能被多种方式解读的模糊语言,因为安全系统偏向于谨慎处理。
Nano Banana 2 速率限制详解 — 每个层级和限制

理解完整的速率限制系统对于在错误发生前预防它们至关重要。Google 将 Nano Banana 2 的速率限制分为四个维度和四个层级,每个组合都有一个特定的数值限制,决定您的项目可以发出多少请求。所有这些数据均于 2026 年 3 月 2 日从 ai.google.dev/gemini-api/docs/rate-limits 直接验证。如需了解所有 Gemini 模型的全面分析,请参阅我们的完整 Gemini API 速率限制按层级分析。
四个速率限制维度独立运作。RPM(每分钟请求数)限制 API 调用的数量,不论其大小。TPM(每分钟 token 数)限制所有请求的总 token 吞吐量。RPD(每天请求数)设置每日上限,在太平洋时间午夜重置。IPM(每分钟图像数)专门限制图像生成输出。您可以命中其中任一限制而不影响其他限制 — 例如,您可能还有 RPM 余量但已用尽该分钟的 IPM 配额。
速率限制按 Google Cloud 项目而非 API 密钥执行。这是许多开发者遗漏的关键区别。如果您在同一项目下创建多个 API 密钥,希望以此倍增速率限制,这是行不通的。同一项目下的所有密钥共享相同的速率限制池。要真正增加有效速率限制,您需要创建独立的 Google Cloud 项目,但这种方法在计费管理方面有其自身的复杂性,除非您有特定的架构原因,否则通常不推荐。
Google 的层级系统从免费版开始,经过 Tier 1、Tier 2 和 Tier 3。免费层完全不支持 Nano Banana 2 图像生成 — 如果您在未启用计费的情况下尝试生成图像,会立即收到 429 错误。Tier 1 在启用计费时激活,提供基础图像生成限制。Tier 2 要求过去 30 天内累计消费 $250 或以上,Tier 3 要求 $1,000 或以上。每次层级升级都会显著提高所有四个维度的限制。
对于 Tier 1 账户,实际意义是您可以每分钟生成约 10 张图像,每天最多 1,000 张。如果您的应用实时处理用户请求,这意味着您可以大约每 6 秒持续处理一个图像请求,或者短暂突发最多 10 个同时请求后进入强制冷却期。对于批量处理图像的应用(例如生成产品目录或社交媒体内容),每天 1,000 张的 RPD 限制通常是约束条件而非 RPM。
批处理 API 为高流量工作负载提供了替代方案。Nano Banana 2 支持批处理,队列限制为 100 万 token(Tier 1)、2.5 亿 token(Tier 2)和 7.5 亿 token(Tier 3)。批处理请求以较低优先级异步处理,但不受同步请求的相同 RPM 限制约束。如果您的用例不需要实时图像生成,批处理 API 可以在无需层级升级的情况下大幅提升吞吐量。像 laozhang.ai 这样的服务提供 Nano Banana 2 访问,速率限制宽松,每张图像约 $0.05,对于需要更高吞吐量但不想管理多个 Google Cloud 项目或等待层级升级的开发者来说,这是一个实用的替代方案。
Nano Banana 2 生产级错误处理代码

实现健壮的错误处理不仅仅是将 API 调用包装在 try-catch 块中。生产级解决方案应包括带抖动的指数退避、避免反复请求失败服务的断路器模式,以及主动保持在速率限制内的请求队列。以下是 Python 和 TypeScript 的完整实现,您可以将其适配到您的 Nano Banana 2 集成中。
Python 实现
pythonimport time import random import google.generativeai as genai from collections import deque from threading import Lock class NanoBanana2Client: """Production error handler for Nano Banana 2 (gemini-3.1-flash-image-preview)""" MODEL_ID = "gemini-3.1-flash-image-preview" def __init__(self, api_key: str, max_rpm: int = 10): genai.configure(api_key=api_key) self.model = genai.GenerativeModel(self.MODEL_ID) self.max_rpm = max_rpm self.request_timestamps = deque() self.lock = Lock() self.circuit_open = False self.circuit_failures = 0 self.circuit_threshold = 5 self.circuit_reset_time = 0 def _wait_for_rate_limit(self): """Proactive rate limiting - prevent 429 before it happens""" with self.lock: now = time.time() # Remove timestamps older than 60 seconds while self.request_timestamps and self.request_timestamps[0] < now - 60: self.request_timestamps.popleft() if len(self.request_timestamps) >= self.max_rpm: wait_time = 60 - (now - self.request_timestamps[0]) + 0.1 if wait_time > 0: time.sleep(wait_time) self.request_timestamps.append(time.time()) def _check_circuit_breaker(self): """Circuit breaker - stop hammering a failing service""" if self.circuit_open: if time.time() > self.circuit_reset_time: self.circuit_open = False self.circuit_failures = 0 else: raise Exception( f"Circuit breaker open. Retry after " f"{int(self.circuit_reset_time - time.time())}s" ) def generate_image(self, prompt: str, max_retries: int = 5, **kwargs): """Generate image with full error handling""" self._check_circuit_breaker() self._wait_for_rate_limit() for attempt in range(max_retries): try: response = self.model.generate_content( prompt, generation_config=genai.types.GenerationConfig( response_mime_type="image/png", **kwargs ) ) # Check for IMAGE_SAFETY block if hasattr(response, 'candidates') and response.candidates: candidate = response.candidates[0] if hasattr(candidate, 'finish_reason'): if candidate.finish_reason.name == "IMAGE_SAFETY": return {"error": "IMAGE_SAFETY", "retryable": False, "message": "Content blocked by safety filter"} # Success - reset circuit breaker self.circuit_failures = 0 return {"success": True, "response": response} except Exception as e: error_code = getattr(e, 'code', None) or self._extract_code(str(e)) if error_code == 429: # Rate limit - exponential backoff with jitter delay = min(60, (2 ** attempt) + random.uniform(0, 1)) time.sleep(delay) continue elif error_code in (502, 503): # Server error - longer backoff self.circuit_failures += 1 if self.circuit_failures >= self.circuit_threshold: self.circuit_open = True self.circuit_reset_time = time.time() + 120 delay = min(60, 5 * (2 ** attempt) + random.uniform(0, 2)) time.sleep(delay) continue elif error_code in (400, 403): # Client error - do not retry return {"error": error_code, "retryable": False, "message": str(e)} else: # Unknown error return {"error": "UNKNOWN", "retryable": False, "message": str(e)} return {"error": "MAX_RETRIES", "retryable": True, "message": f"Failed after {max_retries} attempts"} def _extract_code(self, error_str: str) -> int: for code in [429, 502, 503, 500, 400, 403]: if str(code) in error_str: return code return 0
TypeScript / Node.js 实现
typescriptimport { GoogleGenerativeAI } from "@google/generative-ai"; interface GenerationResult { success: boolean; response?: any; error?: string; retryable?: boolean; message?: string; } class NanoBanana2Client { private static MODEL_ID = "gemini-3.1-flash-image-preview"; private model: any; private requestTimestamps: number[] = []; private maxRpm: number; private circuitOpen = false; private circuitFailures = 0; private circuitThreshold = 5; private circuitResetTime = 0; constructor(apiKey: string, maxRpm = 10) { const genAI = new GoogleGenerativeAI(apiKey); this.model = genAI.getGenerativeModel({ model: NanoBanana2Client.MODEL_ID }); this.maxRpm = maxRpm; } private async waitForRateLimit(): Promise<void> { const now = Date.now(); this.requestTimestamps = this.requestTimestamps .filter(ts => ts > now - 60000); if (this.requestTimestamps.length >= this.maxRpm) { const waitMs = 60000 - (now - this.requestTimestamps[0]) + 100; if (waitMs > 0) await this.sleep(waitMs); } this.requestTimestamps.push(Date.now()); } async generateImage( prompt: string, maxRetries = 5 ): Promise<GenerationResult> { if (this.circuitOpen) { if (Date.now() > this.circuitResetTime) { this.circuitOpen = false; this.circuitFailures = 0; } else { const waitSec = Math.ceil( (this.circuitResetTime - Date.now()) / 1000 ); return { success: false, error: "CIRCUIT_OPEN", retryable: true, message: `Circuit breaker open. Retry in ${waitSec}s` }; } } await this.waitForRateLimit(); for (let attempt = 0; attempt < maxRetries; attempt++) { try { const result = await this.model.generateContent({ contents: [{ role: "user", parts: [{ text: prompt }] }], generationConfig: { responseMimeType: "image/png" }, }); const candidate = result.response?.candidates?.[0]; if (candidate?.finishReason === "IMAGE_SAFETY") { return { success: false, error: "IMAGE_SAFETY", retryable: false, message: "Content blocked by safety filter" }; } this.circuitFailures = 0; return { success: true, response: result.response }; } catch (err: any) { const code = err?.status || err?.code || this.extractCode(err.message); if (code === 429) { const delay = Math.min(60000, (2 ** attempt) * 1000 + Math.random() * 1000); await this.sleep(delay); continue; } if (code === 502 || code === 503) { this.circuitFailures++; if (this.circuitFailures >= this.circuitThreshold) { this.circuitOpen = true; this.circuitResetTime = Date.now() + 120000; } const delay = Math.min(60000, 5000 * (2 ** attempt) + Math.random() * 2000); await this.sleep(delay); continue; } if (code === 400 || code === 403) { return { success: false, error: String(code), retryable: false, message: err.message }; } return { success: false, error: "UNKNOWN", retryable: false, message: err.message }; } } return { success: false, error: "MAX_RETRIES", retryable: true, message: `Failed after ${maxRetries} attempts` }; } private sleep(ms: number): Promise<void> { return new Promise(resolve => setTimeout(resolve, ms)); } private extractCode(msg: string): number { for (const code of [429, 502, 503, 500, 400, 403]) { if (msg?.includes(String(code))) return code; } return 0; } }
两种实现共享三个关键架构模式,使它们适合生产使用。首先,主动速率限制跟踪请求时间戳,在新请求命中 Google 的速率限制之前进行延迟,从而在大多数 429 错误发生之前就将其阻止。其次,断路器模式检测到服务器处于降级状态时(连续 5 次失败后)暂时停止发送请求 2 分钟,给服务器恢复时间而不是加重过载。第三,带抖动的指数退避策略在重试之间使用逐渐增长的延迟,同时添加随机性以防止多个客户端同步重试。
错误持续出现时的替代方案和成本优化
如果您已实现上述所有错误处理策略但仍然经常遇到速率限制,问题可能是架构性的而非技术性的。您已经超出了当前层级的容量,有三条实际的前进路径:升级 Google Cloud 层级、优化请求模式,或使用提供更高限制的 API 代理服务。
升级层级是最直接的解决方案,但需要满足 Google 的消费门槛。从 Tier 1 升级到 Tier 2 需要 30 天内累计消费 $250,这将使您的 RPM 从 10 增加到 30,RPD 从 1,000 增加到 5,000。对于许多生产应用来说,Tier 2 的限制已经足够。Tier 3(30 天内消费 $1,000 以上)将所有限制再翻倍至 60 RPM 和 10,000 RPD,可以处理大量工作负载。当您满足消费门槛时,过渡是自动的 — 不需要申请流程或人工审批。
优化请求模式通常可以推迟或消除层级升级的需要。考虑实现一个请求队列,将图像生成任务批量化并以刚好低于 RPM 限制的稳定速率处理。缓存已生成的图像,确保同一提示词不会重复生成。对于非时间敏感的工作负载使用批处理 API,它不受标准 RPM 限制约束。如果您要生成多种分辨率的图像,先以 512px(每张 $0.045)生成预览,仅对确认选择的图像生成更高分辨率。
API 代理服务提供了第三条路径,将更高的速率限制与潜在的成本节约相结合。像 laozhang.ai 这样的服务提供 Nano Banana 2 访问,每张图像约 $0.05,没有速率限制约束,与 Google 在 1K 分辨率层级的直接定价($0.067)相比具有竞争力,且远低于更高分辨率的价格。如需了解最便宜的 Nano Banana 2 API 替代方案,我们有一篇专门的对比文章涵盖所有主要提供商。代理服务的权衡是它们增加了一个网络跳转和对第三方提供商的依赖,因此最适合非关键工作负载或作为主要 Google Cloud 配额耗尽时的后备方案。
以下是在 1K 分辨率下每天生成 1,000 张图像的实际成本对比:
| 提供商 | 单张成本 | 日成本(1K 张) | 速率限制 | 最适用于 |
|---|---|---|---|---|
| Google 直接(Tier 1) | $0.067 | $67.00 | 10 RPM / 1,000 RPD | 开发、低流量 |
| Google 直接(Tier 2) | $0.067 | $67.00 | 30 RPM / 5,000 RPD | 生产、中等流量 |
| Google 直接(Tier 3) | $0.067 | $67.00 | 60 RPM / 10,000 RPD | 企业、高流量 |
| laozhang.ai | ~$0.05 | ~$50.00 | 无严格 RPM 限制 | 成本敏感、高流量 |
Google 的定价在所有层级上相同 — 层级仅影响速率限制,不影响单张成本。这意味着层级升级的价值纯粹在于吞吐量容量,而非单位经济。如果成本是您的首要关注点,且您对代理服务感到满意,您可以每张图像节省约 25%,同时获得实际上无限的速率限制。文档可在 docs.laozhang.ai 获取,您也可以在 images.laozhang.ai 测试图像生成。
常见问题
如何修复 Nano Banana 2 的 429 错误?
429 RESOURCE_EXHAUSTED 错误意味着您已超出四个速率限制之一:RPM(每分钟请求数)、TPM(每分钟 token 数)、RPD(每天请求数)或 IPM(每分钟图像数)。RPM 限制的最快修复是等待 60 秒。RPD 限制则必须等到太平洋时间午夜。在代码中实现指数退避,从 1 秒延迟开始,每次重试加倍,最大 60 秒。主动间隔您的请求以保持在限制以下 — 对于 Tier 1 账户,这意味着图像生成每分钟不超过 10 个请求。
Nano Banana 2 的速率限制是多少?
Nano Banana 2(gemini-3.1-flash-image-preview)的速率限制因层级而异。Tier 1(启用计费)允许 10 RPM、4M TPM、1,000 RPD 和 10 IPM 用于图像生成。Tier 2(30 天内消费 $250 以上)允许 30 RPM、10M TPM、5,000 RPD 和 30 IPM。Tier 3(消费 $1,000 以上)允许 60 RPM、20M TPM、10,000 RPD 和 60 IPM。免费层不支持图像生成。这些限制按项目而非按 API 密钥计算,数据于 2026 年 3 月 2 日从 ai.google.dev 验证。
为什么 Nano Banana 2 持续出现 502 错误?
502 Bad Gateway 错误表明 Google 服务器端存在问题,与您的代码无关。这些错误通常在 5-15 分钟内恢复。它们在高峰使用时段(UTC 10:00-14:00)最常见。实现从 5 秒初始延迟开始的重试逻辑,逐步增加到 30-60 秒。如果 502 错误持续超过 30 分钟,请检查 Google Cloud 状态仪表板是否有服务事件。失败的 502 请求不会被计费。
Nano Banana 2 可以免费使用吗?
Nano Banana 2 的纯文本请求可以在免费层使用,但图像生成需要启用计费(Tier 1 或以上)。NB2 图像生成没有免费层。单张图像成本从 $0.045(512px)到 $0.151(4K 分辨率)不等。输入 token 每百万 $0.25,图像输出 token 每百万 $60,数据于 2026 年 3 月 2 日从 Google 官方定价页面验证。
Nano Banana 2 中的 thought_signature 错误是什么?
thought_signature 错误(400 Bad Request)发生在多轮对话中,当您未包含模型前一次响应中的 thought_signature 时触发。即使您将思考可见性设置为"off",NB2 仍然会生成思考 token 并包含必须在后续轮次中传回的签名。从 API 响应中提取 thought_signature 字段并将其包含在下一个请求的 generation_config 中即可解决此错误。
Nano Banana 2 和 Pro 的错误有什么区别?
Nano Banana 2 和 Pro 共享相同的错误代码(429、502、503、400、403、IMAGE_SAFETY),但在速率限制和定价上有所不同。NB2 每 token 便宜 50-87%,但作为预览版模型具有更严格的速率限制。NB2 输入价格为 $0.25/1M token,而 Pro 为 $2.00/1M;NB2 输出价格为 $60/1M,而 Pro 为 $120/1M。两者都没有免费的图像生成层。在错误恢复能力方面,Pro 由于其非预览状态,在同一层级可能具有略微宽松的限制。
