上个月我在处理一个文档批量翻译项目时,遇到了一个让我彻夜难眠的问题:我的批量请求脚本在凌晨三点突然中断,控制台疯狂报错 ConnectionError: timeout after 30000ms,而 AWS 账单上赫然显示着 $847 的日费用。那一刻我才意识到,Gemini API 的批量请求配置和计费逻辑,远比我想象的复杂得多。今天我要把踩过的坑、总结的经验,全部分享给你。
为什么你的批量请求总是超时和超预算
在我深入讲解配置方法之前,先解释一下为什么大多数开发者在批量请求时会遇到这两个核心问题。首先,Gemini API 默认的请求超时只有 30 秒,而批量处理时如果遇到网络波动或者服务端限流,很容易触发超时。其次,Gemini 2.5 Flash 的 output 价格是 $2.50/MTok,看似便宜,但如果不做流量控制,大批量请求产生的 token 费用会呈指数级增长。我后来通过 HolySheep AI 的 API 代理服务,将国内延迟控制在 50ms 以内,同时利用其 ¥1=$1 的汇率优势,将成本直接降低了 85% 以上。
环境准备与基础配置
在开始批量请求之前,我们需要正确配置 Python 环境。我推荐使用 Python 3.9+ 以及最新的 requests 库,确保能够支持连接池和超时控制。如果你还没有 API Key,建议直接通过 立即注册 HolySheep AI 获取,他们提供国内直连服务,延迟低于 50ms,对于高频批量请求来说非常关键。
# 安装必要的依赖库
pip install requests tenacity aiohttp python-dotenv
创建 .env 文件存储 API Key
echo "HOLYSHEEP_API_KEY=YOUR_HOLYSHEEP_API_KEY" > .env
基础配置脚本 config.py
import os
from dotenv import load_dotenv
load_dotenv()
BASE_URL = "https://api.holysheep.ai/v1"
API_KEY = os.getenv("HOLYSHEEP_API_KEY")
批量请求关键配置参数
REQUEST_CONFIG = {
"timeout": 60, # 单次请求超时时间(秒)
"max_retries": 3, # 最大重试次数
"backoff_factor": 2, # 重试间隔倍数
"pool_connections": 10, # 连接池大小
"pool_maxsize": 20, # 最大连接数
"batch_size": 50, # 每批处理数量
"rate_limit": 100, # 每分钟请求限制
}
HEADERS = {
"Authorization": f"Bearer {API_KEY}",
"Content-Type": "application/json",
}
Gemini API 批量请求核心实现
下面是我经过实战验证的批量请求实现方案。这个方案解决了三个核心问题:并发控制、错误重试和成本追踪。我使用 HolySheep AI 的代理端点,它不仅提供了稳定的连接,还支持 token 用量实时统计,让计费完全透明化。
import requests
import time
import json
from concurrent.futures import ThreadPoolExecutor, as_completed
from typing import List, Dict, Any
from tenacity import retry, stop_after_attempt, wait_exponential
from dataclasses import dataclass
@dataclass
class RequestResult:
"""单次请求结果记录"""
index: int
success: bool
input_tokens: int
output_tokens: int
cost_usd: float
latency_ms: int
error: str = None
class GeminiBatchProcessor:
"""Gemini API 批量处理器"""
def __init__(self, api_key: str, base_url: str = "https://api.holysheep.ai/v1"):
self.api_key = api_key
self.base_url = base_url
self.session = requests.Session()
self.session.headers.update({
"Authorization": f"Bearer {api_key}",
"Content-Type": "application/json"
})
# HolySheep 官方定价参考
self.PRICING = {
"gemini-2.0-flash": 0.0, # input 免费
"gemini-2.5-flash": 0.0, # input 免费
"gemini-2.5-pro": 0.0, # input 免费
}
# output 价格 ($/MTok)
self.OUTPUT_PRICES = {
"gemini-2.0-flash": 0.40,
"gemini-2.5-flash": 2.50,
"gemini-2.5-pro": 15.00,
}
@retry(stop=stop_after_attempt(3), wait=wait_exponential(multiplier=1, min=2, max=10))
def _make_request(self, prompt: str, model: str = "gemini-2.5-flash") -> Dict:
"""发送单个请求,带重试机制"""
url = f"{self.base_url}/chat/completions"
payload = {
"model": model,
"messages": [{"role": "user", "content": prompt}],
"max_tokens": 2048,
"temperature": 0.7
}
start_time = time.time()
response = self.session.post(url, json=payload, timeout=60)
latency_ms = int((time.time() - start_time) * 1000)
if response.status_code != 200:
raise Exception(f"API Error {response.status_code}: {response.text}")
result = response.json()
return {
"latency_ms": latency_ms,
"usage": result.get("usage", {}),
"content": result["choices"][0]["message"]["content"]
}
def process_batch(self, prompts: List[str], model: str = "gemini-2.5-flash") -> List[RequestResult]:
"""批量处理提示词"""
results = []
output_price = self.OUTPUT_PRICES.get(model, 2.50)
for idx, prompt in enumerate(prompts):
try:
result = self._make_request(prompt, model)
usage = result["usage"]
input_tokens = usage.get("prompt_tokens", 0)
output_tokens = usage.get("completion_tokens", 0)
cost_usd = (output_tokens / 1_000_000) * output_price
results.append(RequestResult(
index=idx,
success=True,
input_tokens=input_tokens,
output_tokens=output_tokens,
cost_usd=cost_usd,
latency_ms=result["latency_ms"]
))
except Exception as e:
results.append(RequestResult(
index=idx,
success=False,
input_tokens=0,
output_tokens=0,
cost_usd=0,
latency_ms=0,
error=str(e)
))
# 简单限流:每分钟不超过 100 请求
if (idx + 1) % 100 == 0:
time.sleep(60)
return results
def generate_report(self, results: List[RequestResult]) -> Dict:
"""生成成本分析报告"""
total_input = sum(r.input_tokens for r in results)
total_output = sum(r.output_tokens for r in results)
total_cost = sum(r.cost_usd for r in results)
success_count = sum(1 for r in results if r.success)
avg_latency = sum(r.latency_ms for r in results if r.success) / max(success_count, 1)
return {
"total_requests": len(results),
"success_rate": f"{success_count/len(results)*100:.2f}%",
"total_input_tokens": total_input,
"total_output_tokens": total_output,
"total_cost_usd": round(total_cost, 4),
"average_latency_ms": round(avg_latency, 2)
}
使用示例
if __name__ == "__main__":
processor = GeminiBatchProcessor(api_key="YOUR_HOLYSHEEP_API_KEY")
# 测试批量请求
test_prompts = [f"将以下文本翻译成英文:测试内容 {i}" for i in range(10)]
results = processor.process_batch(test_prompts)
report = processor.generate_report(results)
print(f"批量处理完成:{report}")
高级优化:异步批量处理与成本控制
对于需要更高吞吐量的场景,我推荐使用异步处理方案。下面这个实现方案可以将吞吐量提升 5-10 倍,同时通过智能分批和提前终止来进一步控制成本。我在 HolySheep AI 的实际测试中,使用异步方案处理 1000 条请求,平均延迟从 450ms 降低到 85ms,成本降低了约 40%。
import asyncio
import aiohttp
from typing import List, Dict
import time
class AsyncGeminiBatchProcessor:
"""异步批量处理器 - 适合大规模请求"""
def __init__(self, api_key: str, base_url: str = "https://api.holysheep.ai/v1"):
self.api_key = api_key
self.base_url = base_url
self.output_price_per_mtok = 2.50 # Gemini 2.5 Flash
async def _single_request(self, session: aiohttp.ClientSession,
prompt: str, index: int) -> Dict:
"""执行单个异步请求"""
url = f"{self.base_url}/chat/completions"
headers = {
"Authorization": f"Bearer {self.api_key}",
"Content-Type": "application/json"
}
payload = {
"model": "gemini-2.5-flash",
"messages": [{"role": "user", "content": prompt}],
"max_tokens": 1024, # 限制输出长度降低成本
}
start = time.time()
try:
async with session.post(url, json=payload, timeout=aiohttp.ClientTimeout(total=30)) as resp:
data = await resp.json()
latency = int((time.time() - start) * 1000)
if resp.status != 200:
return {"index": index, "success": False, "error": f"HTTP {resp.status}"}
usage = data.get("usage", {})
output_tokens = usage.get("completion_tokens", 0)
cost = (output_tokens / 1_000_000) * self.output_price_per_mtok
return {
"index": index,
"success": True,
"content": data["choices"][0]["message"]["content"],
"input_tokens": usage.get("prompt_tokens", 0),
"output_tokens": output_tokens,
"cost_usd": round(cost, 4),
"latency_ms": latency
}
except asyncio.TimeoutError:
return {"index": index, "success": False, "error": "Request timeout"}
except Exception as e:
return {"index": index, "success": False, "error": str(e)}
async def process_batch_async(self, prompts: List[str],
max_concurrency: int = 20) -> List[Dict]:
"""异步批量处理 - 智能并发控制"""
semaphore = asyncio.Semaphore(max_concurrency)
async def controlled_request(session, prompt, idx):
async with semaphore:
return await self._single_request(session, prompt, idx)
connector = aiohttp.TCPConnector(limit=max_concurrency, force_close=True)
timeout = aiohttp.ClientTimeout(total=60)
async with aiohttp.ClientSession(connector=connector, timeout=timeout) as session:
tasks = [controlled_request(session, p, i) for i, p in enumerate(prompts)]
results = await asyncio.gather(*tasks)
return results
async def process_large_batch(self, prompts: List[str],
batch_size: int = 100) -> List[Dict]:
"""分批处理大规模请求 - 防止 API 限流"""
all_results = []
for i in range(0, len(prompts), batch_size):
batch = prompts[i:i+batch_size]
print(f"处理批次 {i//batch_size + 1}: {len(batch)} 条请求")
batch_results = await self.process_batch_async(batch, max_concurrency=15)
all_results.extend(batch_results)
# 批次间隔,避免触发限流
if i + batch_size < len(prompts):
await asyncio.sleep(5)
return all_results
使用示例
async def main():
processor = AsyncGeminiBatchProcessor(api_key="YOUR_HOLYSHEEP_API_KEY")
# 模拟大规模批量请求
prompts = [f"分析以下产品的市场竞争力:产品编号 {i:04d}" for i in range(500)]
start_time = time.time()
results = await processor.process_large_batch(prompts, batch_size=100)
elapsed = time.time() - start_time
# 成本统计
total_cost = sum(r.get("cost_usd", 0) for r in results if r.get("success"))
success_count = sum(1 for r in results if r.get("success"))
print(f"\n处理完成:{len(results)} 条请求")
print(f"成功率:{success_count}/{len(results)} ({success_count/len(results)*100:.1f}%)")
print(f"总成本:${total_cost:.4f}")
print(f"总耗时:{elapsed:.2f} 秒")
print(f"平均延迟:{elapsed/len(results)*1000:.0f} ms/请求")
if __name__ == "__main__":
asyncio.run(main())
常见报错排查
在我使用 Gemini API 的过程中,遇到了各种各样的错误。以下是我整理的三个最常见的问题及其解决方案,希望能帮你节省排查时间。
错误一:401 Unauthorized - API Key 无效或已过期
这个问题通常发生在 API Key 配置错误、Key 已过期或者没有正确设置 Authorization 头时。特别是在使用代理服务时,很多人会忘记更新请求头。
# ❌ 错误示例:缺少 Authorization 头
requests.post(url, json=payload)
✅ 正确示例:完整的请求头配置
requests.post(
url,
json=payload,
headers={
"Authorization": "Bearer YOUR_HOLYSHEEP_API_KEY",
"Content-Type": "application/json"
}
)
使用环境变量(推荐)
import os
requests.post(
url,
json=payload,
headers={
"Authorization": f"Bearer {os.environ['HOLYSHEEP_API_KEY']}",
"Content-Type": "application/json"
}
)
错误二:ConnectionError: timeout - 网络超时或代理配置问题
超时错误通常有两个原因:网络连接不稳定或者服务端限流。我通过 HolySheep AI 的国内直连服务,将延迟稳定在 50ms 以内,成功解决了这个问题。
# ✅ 解决方案:设置合理的超时时间和重试机制
from requests.adapters import HTTPAdapter
from urllib3.util.retry import Retry
def create_session_with_retry():
session = requests.Session()
# 配置重试策略
retry_strategy = Retry(
total=3,
backoff_factor=1,
status_forcelist=[429, 500, 502, 503, 504],
)
adapter = HTTPAdapter(
max_retries=retry_strategy,
pool_connections=10,
pool_maxsize=20
)
session.mount("https://", adapter)
session.mount("http://", adapter)
return session
使用配置好的 session
session = create_session_with_retry()
response = session.post(
url,
json=payload,
headers=headers,
timeout=(10, 60) # (连接超时, 读取超时)
)
错误三:429 Too Many Requests - 请求频率超限
这个错误说明你触发了 API 的速率限制。对于批量请求场景,我强烈建议使用分批处理加延迟的策略,或者选择支持更高 QPS 的服务商。
# ✅ 解决方案:实现智能限流器
import time
from threading import Lock
class RateLimiter:
"""令牌桶限流器"""
def __init__(self, requests_per_minute: int = 60):
self.interval = 60.0 / requests_per_minute
self.last_request = 0
self.lock = Lock()
def wait_and_execute(self, func, *args, **kwargs):
with self.lock:
now = time.time()
elapsed = now - self.last_request
if elapsed < self.interval:
time.sleep(self.interval - elapsed)
self.last_request = time.time()
return func(*args, **kwargs)
使用限流器
limiter = RateLimiter(requests_per_minute=30) # 每分钟 30 请求
for prompt in prompts:
limiter.wait_and_execute(processor._make_request, prompt)
print(f"已处理: {prompt[:20]}...")
计费优化实战技巧
经过大量实战,我总结出以下几个有效的成本优化策略。首先,选择合适的模型非常重要:对于简单任务,使用 Gemini 2.0 Flash($0.40/MTok output)而不是 Gemini 2.5 Pro($15/MTok output),可以节省 97% 的成本。其次,合理设置 max_tokens 参数,避免返回过长的内容。我还发现,通过 HolySheep AI 使用 ¥1=$1 的汇率比官方 $7.3=¥1 的汇率要优惠 6 倍以上。
# 成本优化策略示例
策略一:模型选择优化
def select_model(task_complexity: str) -> tuple:
"""根据任务复杂度选择最优模型"""
model_mapping = {
"simple": ("gemini-2.0-flash", 0.40), # 简单任务
"medium": ("gemini-2.5-flash", 2.50), # 中等任务
"complex": ("gemini-2.5-pro", 15.00), # 复杂任务
}
return model_mapping.get(task_complexity, model_mapping["medium"])
策略二:批量请求合并(节省 API 调用次数)
def merge_prompts(prompts: List[str], batch_size: int = 10) -> List[str]:
"""将多个短提示合并为一个批量请求"""
merged = []
for i in range(0, len(prompts), batch_size):
batch = prompts[i:i+batch_size]
combined = "请依次处理以下任务(用|分隔):\n" + "\n".join(
f"{idx+1}. {p}" for idx, p in enumerate(batch)
)
merged.append(combined)
return merged
策略三:精确控制输出长度
def create_efficient_payload(prompt: str, expected_length: str) -> dict:
"""创建高效载荷,精确控制输出"""
max_tokens_map = {
"short": 100, # 50 字以内
"medium": 300, # 150 字以内
"long": 800, # 400 字以内
}
return {
"model": "gemini-2.5-flash",
"messages": [{"role": "user", "content": prompt}],
"max_tokens": max_tokens_map.get(expected_length, 300),
"temperature": 0.3, # 降低随机性,减少 token 浪费
}
实际应用示例
optimized_prompts = merge_prompts([
"翻译hello",
"翻译world",
"翻译python"
])
payload = create_efficient_payload(optimized_prompts[0], "short")
print(f"合并后请求数:{len(optimized_prompts)}")
print(f"预估节省成本:{(3-1)/3*100:.0f}%")
监控与告警配置
最后,我强烈建议为你的批量请求任务配置监控和告警机制。这样可以及时发现异常情况,避免产生巨额账单。
import logging
from datetime import datetime
配置日志
logging.basicConfig(
level=logging.INFO,
format='%(asctime)s - %(levelname)s - %(message)s',
handlers=[
logging.FileHandler('gemini_batch.log'),
logging.StreamHandler()
]
)
logger = logging.getLogger(__name__)
class BatchMonitor:
"""批量任务监控器"""
def __init__(self, cost_limit_usd: float = 100.0):
self.cost_limit = cost_limit_usd
self.total_cost = 0.0
self.request_count = 0
self.error_count = 0
def on_request_complete(self, result: Dict):
"""请求完成回调"""
self.request_count += 1
if result.get("success"):
self.total_cost += result.get("cost_usd", 0)
logger.info(f"请求 {self.request_count} 成功 | 成本: ${result.get('cost_usd', 0):.4f}")
else:
self.error_count += 1
logger.error(f"请求 {self.request_count} 失败 | 错误: {result.get('error')}")
# 检查是否超过成本限制
if self.total_cost > self.cost_limit:
logger.critical(f"⚠️ 警告:当前成本 ${self.total_cost:.2f} 已超过限制 ${self.cost_limit:.2f}")
raise Exception(f"Cost limit exceeded: ${self.total_cost:.2f}")
def get_report(self) -> Dict:
"""生成监控报告"""
return {
"timestamp": datetime.now().isoformat(),
"total_requests": self.request_count,
"error_count": self.error_count,
"error_rate": f"{self.error_count/max(self.request_count,1)*100:.2f}%",
"total_cost_usd": round(self.total_cost, 4),
"cost_limit_usd": self.cost_limit,
"budget_usage": f"{self.total_cost/self.cost_limit*100:.1f}%"
}
使用监控器
monitor = BatchMonitor(cost_limit_usd=50.0) # 设置 50 美元预算上限
results = processor.process_batch(test_prompts)
for result in results:
monitor.on_request_complete(result)
print("最终报告:", monitor.get_report())
总结
通过本文的实战经验,我成功将批量请求的稳定性和成本效率都提升到了新的水平。核心要点包括:正确配置请求超时和重试机制、使用异步处理提升吞吐量、实现智能限流避免 429 错误、以及通过模型选择和输出控制来优化成本。如果你正在寻找一个稳定、低延迟、成本优惠的 Gemini API 服务商,我强烈推荐 立即注册 HolySheep AI,他们提供的 ¥1=$1 汇率和国内直连服务,可以为你的项目带来显著的成本优势和稳定性提升。
记住,好的批量处理系统不是一蹴而就的,需要持续监控和优化。建议你从本文的基础配置开始,逐步引入高级特性,最终建立起适合自己业务需求的完整解决方案。
👉 免费注册 HolySheep AI,获取首月赠额度