这一章把前面所有内容转成可操作的判断。不是「学哪个」,而是「在你的约束下,哪个设计是对的」。
这是分水岭。先回答它,后面一半的决策会自动确定。
| 单一工作负载 | 多样工作负载 |
|---|---|
| 例子:只做代码助手 / 只做客服 / 只做数据分析 | 例子:一个平台,上面跑各种各样的智能体 |
| 该做:把上下文策略、工具集、提示词全部针对这一种负载做死。深度优化 | 该做:抽象基类 + 可插拔。允许每种负载配自己的策略 |
| 不该做:过早抽象。你会为了一个永远不会有第二种实现的接口,付出永久的复杂度 | 不该做:把某一种负载的假设写进核心。它会在第二种负载出现时炸掉 |
最常见的错误是「预防性抽象」:还没有第二种实现,就先定义一个抽象基类。
代价:你的接口是凭想象设计的,而不是从两个真实实现里提炼的。等真的出现第二种实现时,你会发现接口不合适,然后要么改接口(破坏第一个实现),要么让第二个实现别扭地适配。
更好的做法:先写死。当出现第二个真实需求时,再从两个具体实现里提炼接口。那时你提炼出来的接口才是对的。
| 扩展者 | 该提供的机制 | 不该提供的 |
|---|---|---|
| 只有你自己 | 直接改代码。也许加几个配置项 | 插件系统。你在给自己制造麻烦 |
| 你的团队 | 技能(Markdown) + 配置。零代码,人人可写 | 复杂的插件 API |
| 其他工程团队 | 工具注册 + 钩子 + MCP | 让他们能替换核心策略 |
| 不可信的第三方 | MCP(跨进程隔离) | 同进程插件。一个崩溃会拖垮你 |
记住 Hermes 第 9 章那个权限梯度:扩展的门槛应该和它能造成的破坏成正比。
技能(纯文本、人人可写、最多让智能体走错路)
→ MCP(跨进程、崩溃隔离、只能提供工具)
→ 插件(同进程、能挂钩子、但钩子只能追加不能替换)
→ 核心策略(能替换整个上下文,但单选,必须用户显式配置)
不要提供一个万能的插件接口让所有人都能做所有事。
这是第 2 章八条共识的行动版本:
| # | 要做的事 | 具体动作 |
|---|---|---|
| 1 | 给上下文记账 | 算清楚:系统提示词多少 token、工具定义多少、每轮增长多少。任何常驻内容都要能说出它为什么值这个价 |
| 2 | 渐进式披露 | 工具、技能、文档、记忆 —— 全部改成「目录常驻 + 内容按需」。并且在描述质量上投入时间 |
| 3 | 至少两层安全 | 「能力收窄」(不给危险工具)+ 「执行隔离」(容器/沙箱)。规则匹配不算一层可靠的防御 |
| 4 | 默认失败即关闭 | 检查每一处 try/except:出异常时是放行还是拒绝?把所有「出错就跳过」改成「出错就拒绝」 |
| 5 | 加硬限制 | 委派深度、并发数、单次输出长度、遍历跳数、缓存条目数。每一个「理论上不会太大」的量都要有上限 |
| 6 | 能力查询而非身份判断 | 搜索代码里所有的 if xxx == "某个具体名字",改成 if xxx.supports_yyy() |
| 7 | 错误分类 | 至少分出三类:可重试的临时故障(短退避)/ 配置或凭据问题(长退避或告警)/ 逻辑错误(不重试,直接报告) |
| 8 | 两段式操作带租约 | 任何「先声明后完成」的操作(工具调用、任务认领、锁),都要处理「声明了但没完成」:补偿或超时 |
不要从「有一个循环,模型调工具,工具返回结果」开始讲。这是所有人都会说的,说明不了什么。
从约束开始讲:
「首先要确定两件事:用户在不在场,以及工作负载是单一还是多样。
用户在场,安全的终点可以是问人;不在场,就必须有自动决策规则、告警系统和执行隔离,因为出了问题没人会发现。
工作负载单一,就把策略写死做深度优化;多样,就需要抽象基类 —— 但要区分哪些是可叠加的能力,哪些是必须单选的策略。
然后是三个跑不掉的约束:上下文是最稀缺的资源,所以一切设计围绕渐进式披露;安全必须分层,因为每一层都不可靠;默认值必须是 fail-closed。」
| 被问到 | 可以举的例子 |
|---|---|
| 上下文管理 | 五级阶梯(每级的信息损失递增,从最轻的开始);select_context 与 compress 的正交(读 vs 写,那个误用故事) |
| 提示词缓存 | 前缀匹配,一个字节不同就全部失效;分叉子智能体为了共享缓存做到字节级一致 |
| 安全 | _CMDPOS 命令位置锚定和那次 gh pr create --title 误拦事故;绕过免疫检查放在模式判断之前 |
| 多智能体 | MAX_DEPTH = 1(用硬限制消灭指数爆炸);set_spawn_paused(区分「停止接受新工作」和「终止现有工作」) |
| 可靠性 | 孤儿 tool_use 必须在每条中止路径合成结果;try_register_running_job 防定时任务堆叠 |
| 重试 | 凭据池按 HTTP 状态码决定冷却时长(429 短、401 长、5xx 极短) |
这七个问题不需要你记住任何一个具体实现。
它们是从 Claude Code 的 176,391 字分析和 Hermes 的 141,079 字分析里提炼出来的、真正可迁移的部分。
具体的实现会过时 —— 模型会变、API 会变、框架会变。但这些约束来自「智能体」这个形态本身,它们不会变。