生产级 AI 网关落地:鉴权、限流与故障转移的 7 个坑
关键词网关 / 生产实战 / 避坑 适用读者已经决定在业务和模型之间加一层网关正在写第一版实现的工程师很多团队在本地把网关跑通、调通了 GPT-5 和 Claude 4 Sonnet 就以为万事大吉结果一上生产就被各种诡异问题暴击Key 泄露、请求雪崩、流式中断、额度一夜烧光……下面这 7 个坑是我从多次生产事故里攒出来的。每一条都配一段能直接抄的代码片段照着改能省掉至少一晚的 oncall。注下文示例默认你的网关对外暴露OpenAI 兼容协议这样业务侧几乎不用改代码就能在 GPT-5、Claude 4 Sonnet、Gemini 3 Flash、DeepSeek V4 之间自由切换。坑 1密钥硬编码在代码里最典型的低级事故。Key 写进源码推到仓库转头就被扫库机器人拖走额度半小时清空。正确做法Key 走环境变量或密钥管理服务网关内部再做一层对外统一 Key、对内多厂商 Key 池的映射。python# ❌ 错误密钥写死 # OPENAI_KEY sk-xxxxx # ✅ 正确网关侧统一入口 Key背后映射多家厂商 Key 池 # 国内聚合网关示例统一 OpenAI 兼容协议新用户有免费额度额度包 # 注册https://www.moyu.info/register?affCRB8 GATEWAY_BASE https://gateway.example.com/v1 GATEWAY_TOKEN os.environ[GATEWAY_TOKEN] # 业务侧只持有一个网关 Key坑 2没有全局超时某家模型一旦卡住限流排队、内部故障你的请求会一直挂着连接池被占满连锁拖垮整服务。pythonimport httpx # 连/读都要有上限且读超时别太长 client httpx.AsyncClient( timeouthttpx.Timeout(connect3.0, read30.0, write10.0, pool5.0) )坑 3限流只在客户端做客户端说自己限流了不代表真限住了——多个实例、多个业务线各自限流汇总到网关侧早就超了。python# 限流必须落在网关层且按 (业务线, 模型) 维度 from slowapi import Limiter limiter Limiter(key_funclambda r: f{r.headers.get(X-Tenant)}:{r.json().get(model)}) limiter.limit(20/minute) async def proxy(request): ...坑 4单点故障没有 fallback主模型比如 GPT-5限流或抖动时如果没有兜底用户直接看到报错。pythonFALLBACK_CHAIN { gpt-5: [claude-4-sonnet, deepseek-v4], claude-4-sonnet: [gpt-5-mini, gemini-3-flash], } async def call_with_fallback(model, payload): chain [model, *FALLBACK_CHAIN.get(model, [])] for m in chain: try: return await do_request(m, payload, timeout8.0) except (RateLimit, TimeoutError): continue # 下一个兜底模型 raise AllModelUnavailable()坑 5没有请求追踪出问题查不到这个请求走了哪家模型、花了多少 token、卡在哪一步。python# 每个请求带 trace_id贯穿网关与厂商调用 import uuid, logging trace_id request.headers.get(X-Trace-Id, str(uuid.uuid4())) logging.info({trace_id: trace_id, model: model, action: upstream_call})坑 6流式响应没处理中断前端断了、用户关了页面网关还在傻傻往厂商拉流连接和额度双浪费。pythonasync def stream(model, payload): async with client.stream(POST, f{GATEWAY_BASE}/chat/completions, jsonpayload, headersauth) as resp: async for chunk in resp.aiter_lines(): if await request.is_disconnected(): # 客户端已断开 break # 立即中止向上游拉流 yield chunk坑 7额度没做隔离一个测试脚本把你整月的额度刷爆生产业务直接无模型可用。python# 按 tenant 做额度配额超额直接拒绝而非扣爆共享池 QUOTA {prod: 1_000_000, test: 50_000, eval: 200_000} # 单位token/天 def check_quota(tenant: str, estimate: int): used redis.incrby(fquota:{tenant}:today, estimate) if used QUOTA.get(tenant, 0): raise QuotaExceeded(tenant)落地清单照着勾密钥不进代码库网关统一入口 Key 厂商 Key 池全局 connect/read 超时都设了限流在网关层且按 (tenant, model) 维度主模型失败有兜底链 超时每个请求有 trace_id 贯穿全链路流式响应监听客户端断开按业务线做额度隔离把这 7 条在第一次提交时就写进去后面至少能少背三次锅。本文聚焦生产环境 AI 网关的工程实现与避坑代码片段为示意请结合自身技术栈调整。文中出现的聚合网关链接仅作示例不构成推荐。