每一个具有韧性的 LLM 设计在配置中都有一行代码指定了一个备选模型。它之所以存在,是因为有人在设计评审中提出了正确的问题——“如果主模型宕机了怎么办?”——而另一个人用一个 fallback: 键回答了这个问题。大家都点头表示赞同。架构图上多了一个带有虚线箭头的第二个框。合规文档中也增加了一句关于优雅降级的描述。
然后,再也没有人碰过它。
备选模型是大多数生产环境 AI 系统中被断言得最自信、但演练最少的组件。它被命名、被记录、被画在图中——而在它真正承载流量的那一天,也是它第一次遇到真实请求的一天。你并没有建立安全网。你只是构建了第二个断裂强度未知的模型,而你将在最糟糕的时刻发现那个极限。
发生这种情况的原因是结构性的,而非疏忽。主模型接收你编写的每一个提示词、运行的每一次评估、来自每个用户的每一份错误报告。它在数月的生产流量磨练中成型。而备选模型只得到了一个配置条目。一条路是锻造出来的,另一条路是宣称出来的。当主模型性能下降且流量转移时,你并不是切换到一个经过测试的系统——你是在事故期间、在高负载下、毫无缓冲地冷启动一个新系统。
配置了备选并不等于测试了备选
“备选”(fallback)这个词里隐含着一种微妙的歧义。在设计评审中,它意味着 一个在主模型无法工作时能处理流量的模型 。在配置文件中,它意味着 一段路由代码在看到 503 错误时会选择的字符串 。这两者并不是一回事,而它们之间的差距正是第二次事故潜伏的地方。
路由到备选模型是简单部分。网关和代理已经很好地解决了这个问题:优先级组、熔断器、健康检查、备份提供商的自动重试。如果你的主模型返回 503,同一个请求会在几毫秒内重新发送给备选模型。这套机制很有效,也很可靠。它也不是会出问题的地方。
会出问题的是路由决策 下游 的所有环节。备选模型产生输出。这些输出流入一个根据主模型的格式习惯调优的 JSON 解析器、一个根据主模型的表述习惯校准的提示词注入过滤器、一个假设主模型工具调用约定的函数调用层,以及一个渲染主模型 Markdown 特性的 UI。所有这些都没有针对备选模型进行过测试。路由层完美地完成了它的工作,将一个正确的请求交给了一个其输出从未被你的系统成功处理过的模型。
一个配置好的备选方案证明了你的 路由器 工作正常。但它无法证明你的 应用程序 能在备选模型的输出上正常运行。这些需要单独的证据,而其中只有一种证据是容易获得的。
提示词无法通用,这才是核心问题
大多数备选配置中包含的最昂贵的假设是:提示词是与模型无关的——即你为主模型精心调优的指令在备选模型上会有相同的效果。事实并非如此。
真正更换过模型的从业者会直截了当地告诉你:提示词的可移植性根本不存在。措辞和顺序的细微变化都会引起输出的巨大变化。提示词不是交给可替换执行器的规范;它是为特定锁切割的钥匙。能可靠地让主模型输出严格 JSON 的指令,可能会让备选模型输出“包裹在正文中的 JSON”。锚定主模型语气的少样本(few-shot)示例可能会被具有不同指令遵循偏好的模型所忽略。在主模型上表现稳固的系统提示词,在备选模型上可能在几轮对话后就悄悄偏离。
这就是为什么切换到备选模型并不等同于优雅降级。优雅降级意味着同一个请求产生了一个略差但仍然 有效 的结果。实际发生的情况更接近于范畴变化:响应在结构上是不同的,而结构差异破坏的是解析器,而不是心情。没有模式强制(schema enforcement)的旧模型符合预期输出格式的比例不到 40%——而这还是你所关注的模型的 实测 失败率。你从未调优过的备选模型,其失败率根本无人衡量。
如果你的备选模型与主模型共享同一个配置键,但没有经过独立评估的对应提示词,那么你并没有备选方案。你只是拥有一个将被交给为别人编写的指令的模型。
备选路径也是生产代码——请同样对待它 解决方法并不高明。它只是一种枯燥的纪律,即把备选路径视为必须演练的生产代码,因为它本身就是。
将备选模型作为一等公民进行评估。 你针对主模型运行的每个评估套件都应该针对备选模型运行,并在需要时配备其专属的提示词变体。运行的产出不应该是“备选模型是否工作”,而是“备选模型的实际模式符合率、拒绝率和延迟的具体数字”。一个无法用数字说明质量的备选方案,只是一个披着配置键外衣的猜测。
刻意地迁移和重新调优提示词。 接受备选模型需要自己的提示词,并与主模型的提示词一起进行版本控制。当你修改主模型的提示词时,备选模型的提示词就过时了——你需要像跟踪其他偏差一样跟踪这种滞后,因为一个落后主模型半年调优进度的备选提示词,已经不再匹配你的产品了。
故意将真实流量路由到备选模型。 一个只在停机期间接收流量的备选模型永远是冷的。持续将一小部分实时请求镜像到它上面,或者刻意将 1% 或 2% 的生产流量路由经过它。这能保持它的热度,保持其指标是最新的,保持其提示词的有效性,并且——至关重要地——将备选模型的失败变成普通的“周二 Bug”,而不是复合型事故。你希望在备选模型只占 1% 流量时发现它的 JSON 格式损坏,而不是在占 100% 流量时才发现。
压测故障转移过程,而不仅仅是压测备选模型。 有两个独立的事实需要验证。第一:备选模型能承载你的流量 规模 ——一个额定承载能力仅为负载 10% 的备选方案,无法应对主模型全面停机的情况。第二:切换过程 本身是可承受的。故障转移是一个“惊群效应”事件:原本请求主模型的每一个请求都会在一个健康检查周期内到达备选模型。逐渐增加合成负载,找到备选模型队列激增、首个 Token 响应时间(TTFT)急剧下降的拐点——因为这个点一定存在,唯一的问题是你是在测试中发现它,还是你的用户在事故中发现它。
无人定价的成本 在未经验证的备选方案(fallback)中隐藏着另外两种故障模式,它们表面上是技术细节,实则是预算项目。
第一点是成本。团队通常选择成本最低且能胜任的模型作为主模型。这意味着备选模型从定义上来说几乎肯定更贵。在流量高峰期,长达数小时的主模型宕机不仅会转移负载,还会悄无声息地改变你的单位经济效益(unit economics),且没有警报,也无需审批。长达十小时的故障转移(failover)可能会产生足以引起重视的成本飙升,而人们往往直到看到账单时才会察觉。备选方案的每 token 价格应与它的质量数据一起记入操作手册(runbook)。
第二点是缓慢失效(slow failure)。一个返回 HTTP 200 但包含细微错误输出的备选方案,比直接返回 503 错误更加危险,因为你的路由层会认为请求成功,监控面板也会显示绿色。硬性故障(hard failures)往往动静很大。而软性故障(soft failures)——例如格式错误但可解析的 JSON、看似合理实则错误的内容、或者主模型本可以回答但备选模型拒绝回答——会直接传导给用户。这就是为什么备选方案的验证不能止步于 HTTP 状态码。输出需要经过 Schema 验证,“性能下降但未被检测到”必须是一个可告警的状态,而不是静默状态。
在供应商替你测试之前,先自己测试 行业的 API 正常运行时间(uptime)正在下滑,而非提升 —— 随着需求超过基础设施的承载能力,LLM API 的总体可用性逐年显著下降。仅在最近的一个月内,各大供应商就记录了数十起事故,累计影响时长达数百小时。你的主模型肯定会 宕机。故障转移肯定会 触发。这本身不是风险。风险在于,故障转移触发后接入的是一个你的系统从未成功处理过其输出的模型,它运行着陈旧的提示词(prompt),承受着从未经过规模测算的流量,并产生了无人审批的高额费用。
备选方案是一个“灯火常亮”的承诺。目前对大多数团队来说,这个承诺仅仅由一个配置项(config key)和一份希望支撑。请改用证据来支撑它:使用真实数据进行评估(eval)运行,为次级模型优化并锁定提示词版本,通过持续的小流量保持其“预热”状态,并对切换过程本身进行压力测试。
供应商最终会替你测试你的故障转移机制。你唯一能做的决定是:你是否在那之前已经自己测试过了。
会员专享
余下内容仅对会员开放。 会员可读完整内容 —— 每一个公开发布的观点背后,那些框架、决策与推理的全貌。
— 完整文章,包含未公开存档的部分 — 可落地的工作框架,附带权衡与决策依据 — 新文章抢先看,先于公开发布 登录以继续阅读→ 随时取消 · 一次订阅,畅读全部