共计 2292 个字符,预计需要花费 6 分钟才能阅读完成。
为什么需要代理服务层
直接调用 OpenAI 官方 API 时,开发者常遇到三类典型问题:

- 网络稳定性:跨国 API 调用受网络波动影响大,偶发连接超时需要手动重试
- 速率限制:免费账号每分钟仅 3 次请求,付费账号也有 TPM(每分钟 tokens)限制
- 错误处理:API 返回 429/503 等状态码时缺乏标准化处理流程
HTTP 客户端选型对比
根据实际测试数据(相同并发量下):
| 客户端 | 同步 / 异步 | 长连接支持 | 性能(QPS) |
|---|---|---|---|
| requests | 同步 | ❌ | 120 |
| aiohttp | 异步 | ✅ | 850 |
| httpx | 双模 | ✅ | 780 |
推荐选择:生产环境优先使用 aiohttp,需要同步 / 异步切换时选择 httpx
核心实现代码
指数退避重试装饰器
from functools import wraps
import random
import time
def retry_with_backoff(
max_retries: int = 3,
initial_delay: float = 1.0,
max_delay: float = 10.0,
jitter: bool = True
):
def decorator(func):
@wraps(func)
async def wrapper(*args, **kwargs):
delay = initial_delay
for attempt in range(max_retries):
try:
return await func(*args, **kwargs)
except Exception as e:
if attempt == max_retries - 1:
raise
# 计算下一次延迟时间
sleep_time = min(delay * 2 ** attempt, max_delay)
if jitter:
sleep_time *= random.uniform(0.5, 1.5)
await asyncio.sleep(sleep_time)
return wrapper
return decorator
异步请求封装示例
import aiohttp
from typing import Optional, Dict, Any
class ChatGPTProxy:
def __init__(self, api_keys: list[str]):
self.api_keys = api_keys
self.current_key_idx = 0
self.session = aiohttp.ClientSession(timeout=aiohttp.ClientTimeout(total=30)
)
@retry_with_backoff()
async def send_request(
self,
prompt: str,
model: str = "gpt-3.5-turbo"
) -> Optional[Dict[str, Any]]:
headers = {"Authorization": f"Bearer {self._get_current_key()}",
"Content-Type": "application/json"
}
payload = {
"model": model,
"messages": [{"role": "user", "content": prompt}]
}
try:
async with self.session.post(
"https://api.openai.com/v1/chat/completions",
headers=headers,
json=payload
) as resp:
if resp.status == 429:
self._rotate_key()
return await resp.json()
except aiohttp.ClientError as e:
log_error(f"Request failed: {str(e)}")
raise
def _get_current_key(self) -> str:
return self.api_keys[self.current_key_idx]
def _rotate_key(self) -> None:
self.current_key_idx = (self.current_key_idx + 1) % len(self.api_keys)
生产环境关键配置
熔断机制实现
建议使用 circuitbreaker 包:
from circuitbreaker import circuit
@circuit(
failure_threshold=5,
recovery_timeout=60,
expected_exception=aiohttp.ClientError
)
async def safe_request():
# 业务代码
敏感信息存储方案
- 开发环境:使用
python-dotenv管理.env 文件 - 生产环境:
- Kubernetes:Secret 资源
- AWS:Parameter Store
- 自建方案:Vault + 定期轮换
进阶思考
分布式代理架构设计
- 负载均衡层:Nginx 根据 API Key 哈希值分配请求
- 节点注册:每个代理实例启动时向 Consul 注册健康状态
- 流量控制:Redis 令牌桶算法实现全局速率限制
流量控制算法选择
- 固定窗口:实现简单但存在临界问题
- 滑动日志:精确但消耗内存
- 令牌桶(推荐):平衡精度与性能,适合大多数 AI 场景
性能优化数据
通过代理层优化后(测试环境):
| 指标 | 直接调用 | 代理方案 | 提升幅度 |
|---|---|---|---|
| 成功率 | 82% | 99.7% | +21.5% |
| 平均延迟 | 1.2s | 0.8s | -33% |
| 最大 QPS | 45 | 210 | 4.6x |
最终建议
对于中小规模应用,建议先从单节点代理开始实现核心重试和密钥轮换功能。当日均请求量超过 5 万次时,再考虑引入分布式架构。所有 HTTP 调用务必设置合理超时(建议总超时≤30s),避免级联故障。
正文完
