考察点
「如何保障工具调用的可靠性」和「Agent 的安全与可靠性如何保障」是同一族题,考察你把传统后端的容错思维(超时、重试、熔断、降级)移植到 Agent 场景的能力。面试官特别想听:模型这个不确定组件出错时,系统层面怎么兜。
参考答案
先把失败分类
不同失败要用不同姿势处理,我一般分三类:
1. 语义层失败:模型压根没调对工具——选错工具、参数瞎填、该调的时候不调。这类问题出在模型侧。治理手段:工具描述写清楚(每个参数给含义和例子)、工具数量控制在模型能选的范围内(超过 20 个就做动态筛选)、用 schema 强约束输出格式。FC 能力弱的模型可以在解析层加一道自愈:解析失败时把错误信息喂回去让模型重新生成。
2. 逻辑层失败:工具调对了,但执行逻辑出问题——SQL 查错表、参数合法但语义不对(比如把退款金额单位搞错了分/元)。这类最危险,因为系统不报错,错得悄无声息。治理靠执行前校验:写操作过一道规则引擎或二次确认(金额超阈值必须人审),以及执行后验证(影响行数是否符合预期)。
3. 异常层失败:传统的工程故障——超时、500、限流、网络断。这类用传统手段解决,但要注意 Agent 场景的特殊性。
异常层:传统容错,Agent 化的细节
- 超时:每个工具配独立超时,读操作 10-30 秒,写操作可以更短。超时的错误要翻译成模型能懂的话:「该工具暂时繁忙」,而不是扔一个 socket 异常堆栈进上下文。
- 重试:幂等的读操作可以自动重试 2-3 次(指数退避);写操作默认不自动重试,除非有幂等键。重试对模型透明,别让模型看到三次失败的过程,只给最终结果。
- 熔断:某个工具连续失败 N 次,标记为不可用,并在 prompt 里动态摘掉这个工具的描述——否则模型会锲而不舍地继续调一个挂掉的工具。
- 降级链:工具挂了之后的退路要提前设计好。比如主搜索接口挂了 → 切备用搜索引擎 → 再不行用 LLM 内部知识回答并明确标注「未联网核实」。
系统级降级:整个 Agent 都靠不住时
比单工具失败更严峻的是模型侧整体出问题(API 限流、模型抽风)。降级链从贵到贱:
- 换模型:主模型 429/超时 → 网关自动路由到备用模型(能力可以弱一点,先保证服务活着)。这就是模型网关存在的意义。
- 退化为 Workflow:Agent 模式连续失败,回退到预定义的固定流程。比如智能诊断 Agent 不可用,就退化成「固定采集 N 项指标 → 模板生成报告」。能力打折但确定性回来了。
- 退化为人机协同:把 Agent 已收集的中间结果整理好,转人工接管。注意保留完整 trace,让人能接着 Agent 的进度干,而不是从头再来。
- 体面失败:以上都不行,给用户一个明确的失败说明和预计恢复时间,绝不让请求挂死。
输出侧的守门
Agent 的最终产出也要过一道闸:
- Schema 校验:产出必须是结构化 JSON 的场景,校验不过就让模型修一次,修不好走降级。
- 事实核对:关键数字、代码、命令,能用工具验证的先验证再输出(代码过一遍执行,SQL 先 EXPLAIN)。
- 危险动作拦截:DELETE、DROP、退款、发消息这类不可逆操作,无论模型多有把握,都必须经过规则层或直接人审。这是红线,不依赖模型的自觉性。
一句话总结这套思路
模型是不确定的,所以确定性要从系统层补回来:输入侧管好工具描述和上下文,执行侧超时重试熔断降级,输出侧 schema 校验加危险动作拦截。把 Agent 当成一个能力很强但偶尔醉酒的员工——重要的门要上锁,而不是指望它永远清醒。
可能的追问
- 「重试会不会让 Agent 上下文里塞满失败记录?」 会,所以重试在工具执行层做、对模型透明;必须暴露给模型的失败只保留摘要:「调用失败,原因 X,建议 Y」。
- 「怎么发现逻辑层失败?系统不报错啊。」 两条路:写操作的前后状态校验(对账思维),以及离线评估——定期拿历史 case 回放,人工抽查 Agent 行为轨迹。
- 「降级到备用模型,能力跟不上怎么办?」 备用模型搭配更保守的策略:缩小可用工具范围、收紧 max_iterations、输出更短的答案。降级的目标是保住核心体验,不是全功能平替。