1. 项目概述一个让AI“各司其职”的智能路由插件最近在折腾一个叫OpenClaw的AI网关项目它本身是个挺有意思的东西能把各种大模型比如Claude、GPT、本地跑的Llama统一管理起来通过一个入口比如Telegram机器人或者网页来调用。但用久了发现一个问题我手头既有需要快速响应的简单问答任务也有需要深度思考的复杂推理任务。如果只用同一个模型比如Claude Opus来处理所有事情要么是“杀鸡用牛刀”浪费昂贵的推理成本要么是“小马拉大车”让轻量模型处理复杂任务效果不佳。频繁手动切换模型又太麻烦。于是我动手写了一个插件叫model-router。它的核心思想很简单让主AI学会“看人下菜碟”。你可以用自然语言定义一些规则比如“简单的问答用本地跑的Llama 3.3”、“代码审查用Claude Opus”、“翻译任务用Gemini Flash”。当用户提出一个请求时主AI会先看看这个请求符合哪条规则。一旦匹配它自己不会直接回答而是会“呼叫”一个专门运行指定模型的“子AI”来处理这个任务然后把结果返回给用户。整个过程主AI的模型本身不会改变避免了因切换模型而导致的上下文重新注入和令牌浪费。这个插件特别适合那些手头有多个不同能力、不同成本的AI模型并且希望根据任务类型智能分配的用户。无论是个人开发者想优化本地模型的调用成本还是团队希望建立一个高效、经济的AI任务处理流水线这个插件都能提供一个轻量、灵活的解决方案。接下来我会详细拆解它的设计思路、实现细节、实操步骤以及我踩过的一些坑。2. 核心设计思路与架构解析2.1 为什么选择“委托子任务”而非“切换主模型”在最初构思时我考虑过两种方案一是让网关在运行时动态切换主会话所使用的模型二是保持主模型不变通过创建子会话来委托任务。我最终选择了后者原因基于对OpenClaw工作流的深入分析。方案一动态切换模型的潜在问题令牌浪费严重OpenClaw的会话Session通常包含完整的对话历史。如果切换模型系统需要将整个会话的上下文可能包含数千个令牌重新注入到新模型的提示词中。这不仅消耗额外的API调用令牌还可能因为不同模型的上下文窗口和格式要求不同而引入兼容性问题。状态管理复杂切换模型可能意味着会话状态如思维链、工具调用历史的中断或重置用户体验不连贯。违反安全沙箱OpenClaw对插件有严格的安全限制直接操作核心的模型会话对象可能触发安全机制导致插件失效。方案二委托子任务的优势零令牌浪费主会话的模型和上下文保持不变。只有当任务匹配规则时才通过sessions_spawn工具创建一个全新的、独立的子会话来处理。子会话从零开始只接收当前任务指令无需携带主会话的历史极大节省了令牌。职责清晰主AI扮演“调度员”或“项目经理”的角色负责理解用户意图并分配任务子AI是“专家执行者”专注于用最适合的模型完成特定工作。架构清晰符合单一职责原则。利用原生能力OpenClaw本身就提供了sessions_spawn工具允许一个AI代理创建另一个代理。这个插件只是通过规则自动化了主代理调用该工具的决定过程完全在OpenClaw的安全框架内运行。灵活性高规则是自然语言描述的主AI通常是一个能力较强的模型如Claude Opus可以理解复杂的意图匹配比简单的关键词匹配更智能。例如规则“处理需要多步推理的数学问题”可以被很好地理解。注意这里的关键是sessions_spawn工具。它本质上是主AI向OpenClaw网关发起的一个请求要求创建一个新的、独立的会话。这个新会话可以指定使用不同的模型并且与主会话完全隔离。任务完成后子会话的结果会作为工具调用的返回值传递回主AI再由主AI呈现给用户。2.2 插件核心架构三驾马车驱动整个插件虽然只有约140行TypeScript代码但结构清晰由三个核心模块协同工作2.2.1 规则存储与管理 (src/rules-store.ts)这是插件的数据层。所有用户通过/route add等命令创建的规则最终都会持久化到一个本地JSON文件中默认路径是~/.openclaw/plugins/model-router/rules.json。这个模块负责规则的增删改查CRUD和文件读写。设计考量采用简单的JSON文件存储而非数据库是为了保持插件的轻量化和零外部依赖。规则数据量通常很小文件操作完全足够。读写操作被封装成原子函数确保在并发操作虽然OpenClaw环境下罕见下的数据一致性。2.2.2 命令接口 (index.ts中的命令注册部分)这是与用户交互的入口。插件通过OpenClaw的api.registerCommand()方法注册了/route系列命令。关键设计点这些命令的执行完全绕过了LLM和提示词注入管道。这意味着当你输入/route add coding use claude-opus时OpenClaw会直接调用插件中对应的处理函数更新规则文件并立即返回结果。这个过程不消耗任何LLM令牌响应速度极快。这是实现高效规则管理的基础。2.2.3 提示词注入与路由决策 (src/prompt-inject.ts及index.ts中的钩子)这是插件的“大脑”和“触发器”。它通过OpenClaw的before_prompt_build钩子介入每次对话。注入在每次构建发送给主AI的提示词之前这个钩子函数会被触发。它从内存缓存中读取所有规则将它们格式化成一段清晰的自然语言指令例如“你有以下路由规则1. 如果是编码任务请使用sessions_spawn工具并指定模型anthropic/claude-opus-4-5。2. ...”然后通过appendSystemContext方法将这些指令追加到系统提示词System Prompt的末尾。决策主AI在收到包含路由指令的完整提示词后会结合用户的问题进行理解。如果它判断当前任务符合某条规则它就必须根据指令使用sessions_spawn工具并按照规则指定的模型参数去创建子任务。如果不符合任何规则它就正常处理。2.2.4 内存缓存机制为了追求极致的性能插件引入了内存缓存。规则在插件加载时从磁盘文件读取一次并存入一个内存变量中。后续所有读取操作尤其是每次消息触发before_prompt_build钩子时都直接访问内存。只有当通过/route add或/route remove等命令修改规则时才会同时更新内存缓存和磁盘文件。为什么这么做消息处理是高频操作而磁盘I/O相对较慢。如果每次处理消息都去读文件会引入不必要的延迟。内存缓存几乎零开销确保了路由决策的实时性。整个数据流和工作流程可以概括为下图所示的闭环用户输入 /route add 规则 -- 命令处理器 -- 更新[规则文件]与[内存缓存] 用户输入普通问题 -- before_prompt_build 钩子触发 -- 从[内存缓存]读取规则 -- 注入到[系统提示词] -- 主AI接收提示词并思考 -- 判断匹配规则 -- 是调用 sessions_spawn(指定模型) 创建子任务 -- 子AI返回结果 -- 用户获得答案 -- 否主AI直接回答 -- 用户获得答案3. 从零开始的完整部署与配置指南3.1 环境准备与前期检查在安装插件之前你需要一个正常运行的OpenClaw环境。我假设你已经在macOS、Linux或Windows上完成了OpenClaw的基础安装。验证OpenClaw安装 打开终端运行以下命令确保OpenClaw的版本至少是2026.3.0。这个版本包含了插件系统必要的API支持。openclaw --version如果提示命令未找到你需要重新安装OpenClaw。可以通过npm全局安装npm install -g openclaw或者从官网下载对应平台的安装包。检查模型提供商配置 路由规则的核心是指定模型如anthropic/claude-opus-4-5或ollama/llama3.3:8b。你必须确保OpenClaw已经正确配置了至少一个对应的模型提供商。检查配置文件OpenClaw的配置文件通常位于~/.openclaw/config.json。查看配置你可以运行openclaw config list来查看当前配置或者直接查看配置文件。你需要确认类似providers.anthropic.apiKey或providers.ollama.baseURL的配置项已正确设置。一个常见的坑Ollama用户有时会忘记在OpenClaw配置中Ollama的模型ID需要包含ollama/前缀。例如本地运行的llama3.3:8b模型在规则中必须写为ollama/llama3.3:8b。3.2 插件安装的两种方式插件本身是一个包含openclaw.plugin.json和index.ts等文件的目录。安装的本质是让OpenClaw知道这个目录的存在并将其加载。方式一从本地路径安装推荐用于开发和测试如果你已经克隆了插件仓库到本地比如路径是/home/yourname/projects/openclaw_modleRouterPlugin那么安装命令非常简单openclaw plugins install /home/yourname/projects/openclaw_modleRouterPlugin/model-router注意openclaw plugins install命令期望的参数是插件目录的路径。根据项目结构插件代码在model-router/子目录下所以我们需要指向这个子目录。方式二从Git仓库直接安装OpenClaw的插件安装命令也支持Git仓库URL。你可以一步到位openclaw plugins install https://github.com/sputnicyoji/openclaw_modleRouterPlugin.git#model-router这里的#model-router是一个Git引用它告诉安装器去克隆仓库并使用仓库内model-router子目录作为插件源。这是最便捷的线上安装方式。安装成功验证 安装成功后可以运行openclaw plugins list来查看已安装的插件列表。你应该能看到model-router在列表中并且状态可能是loaded或installed。3.3 关键配置开启提示词注入钩子这是整个插件能否工作的最关键一步也是最容易出错的地方。OpenClaw出于安全考虑默认禁止插件向系统提示词中注入内容。执行配置命令openclaw config set plugins.entries.model-router.hooks.allowPromptInjection true这条命令的作用是在OpenClaw的配置文件中为model-router这个插件条目单独设置hooks.allowPromptInjection属性为true。为什么必须这么做OpenClaw的插件钩子如before_prompt_build运行在一个安全沙箱中。如果allowPromptInjection为false默认值当插件尝试通过appendSystemContext添加内容时安全层会静默地丢弃这个操作而不会抛出任何错误。结果就是你的路由规则永远不会被添加到系统提示词里主AI根本“看”不到这些规则自然也就不会进行路由。这个问题非常隐蔽因为插件命令/route依然可以正常工作让你误以为插件已就绪。3.4 重启网关并验证修改了插件配置后必须重启OpenClaw网关服务才能使配置生效。停止并启动网关openclaw gateway stop openclaw gateway start你也可以使用openclaw gateway restart命令但分开执行stop和start有时能更清晰地观察启动日志。功能验证 连接到你的OpenClaw前端可以是Telegram机器人、Discord机器人或Web界面。 输入一个测试命令/route add 这是一个测试规则 use ollama/llama3.3:8b如果一切正常你应该会收到类似Added rule #1: 这是一个测试规则的回复。 接着输入/route list应该能看到刚添加的规则。 最后为了保持干净可以输入/route remove 1删除这条测试规则。如果/route命令没有任何反应或者提示“未知命令”请返回检查插件是否在openclaw plugins list中以及网关是否成功重启。可以查看OpenClaw的日志输出通常在你启动网关的终端窗口来排查错误。4. 高级使用技巧与规则定义策略4.1 规则定义的语法与最佳实践规则的基本格式是/route add 自然语言描述 use 模型标识符。自然语言描述这是给主AI看的“任务描述”。描述得越清晰、越具体主AI的匹配准确率就越高。模型标识符格式为提供商/模型名。常见的提供商有anthropic(Claude),openai(GPT),ollama(本地模型),google(Gemini) 等。高效规则定义示例与解析基于任务复杂度分层/route add 简单的、事实性的问答或者需要快速回复的闲聊 use ollama/llama3.2:3b /route add 需要分析、总结、润色文本或者进行中等复杂度的推理 use anthropic/claude-haiku /route add 复杂的逻辑推理、代码架构设计、学术问题探讨 use anthropic/claude-opus-4-5技巧用“简单/复杂”等程度副词并列举典型任务场景帮助AI理解边界。将最廉价、最快的模型分配给最高频的简单任务。基于专业领域划分/route add 翻译任何语言的内容特别是中英互译 use google/gemini-2.0-flash /route add 编写、审查、调试或解释代码 use anthropic/claude-sonnet /route add 进行创意写作如故事、诗歌、营销文案 use openai/gpt-4o技巧明确领域关键词“翻译”、“代码”、“创意写作”并指定在该领域公认表现较好的模型。Gemini在翻译上性价比较高Claude Sonnet在代码上很稳健。组合条件与排除法/route add 涉及数学计算、公式推导或数据统计分析的问题 use openai/gpt-4o-mini /route add 非技术性的、开放式的头脑风暴或点子生成 use anthropic/claude-haiku注意规则是顺序无关的但AI会同时评估所有规则。如果两个规则有重叠AI可能会选择它认为更匹配的一个。尽量避免定义相互矛盾的规则。实操心得规则定义后需要进行“训练”和“调优”。刚开始可以定义得宽泛一些然后观察AI的匹配情况。如果发现某个简单任务被错误地路由到了重型模型就把对应规则的描述修改得更严格或增加排除条件。这个过程类似于训练一个分类器。4.2 规则的管理与持久化查看所有规则/route list会列出所有已添加规则的编号和内容方便你管理。删除单条规则/route remove 编号编号由/route list显示。清空所有规则/route clear使用前请确认。数据持久化所有规则都保存在~/.openclaw/plugins/model-router/rules.json文件中。这意味着重启OpenClaw网关后规则依然存在。你可以手动备份或编辑这个JSON文件但编辑时请确保格式正确最好在网关停止时操作。可以在多台机器间同步这个文件来共享路由配置。4.3 理解路由决策的幕后过程当用户发送消息“帮我将这篇技术博客翻译成中文”时幕后发生的事如下触发钩子OpenClaw准备构建发送给主AI假设是Claude Opus的请求。注入规则model-router插件的before_prompt_build钩子被调用它将所有规则例如“翻译任务用google/gemini-2.0-flash”格式化成一段文本追加到系统提示词的末尾。AI接收与思考主AI Claude Opus收到了这样的系统提示“你是AI助手...原有职责...此外你必须遵守以下路由规则1. 如果是翻译任务请使用sessions_spawn工具并指定模型google/gemini-2.0-flash...”匹配与决策Claude Opus分析用户请求识别出“翻译”这个意图并匹配到规则1。执行委托根据规则中的强制指令Claude Opus不会自己翻译而是调用sessions_spawn工具参数为modelgoogle/gemini-2.0-flash,task请将用户提供的技术博客翻译成中文。子任务执行OpenClaw网关创建一个新的临时会话使用Gemini Flash模型来处理这个翻译任务。结果返回Gemini Flash完成翻译后结果作为sessions_spawn工具的返回值传回给Claude Opus。最终回复Claude Opus可能简单地转述这个结果或者加上一句“已通过Gemini完成翻译”然后将最终文本回复给用户。整个过程中主会话Claude Opus的对话历史里只会增加一条它调用sessions_spawn工具的记录而不会包含翻译任务消耗的大量令牌。翻译任务的全部上下文和消耗的令牌都隔离在Gemini Flash的子会话中。5. 故障排除与深度调试指南即使按照步骤安装配置在实际使用中仍可能遇到问题。下面是我在开发和测试中总结的常见问题及其解决方法。5.1 问题规则添加成功但AI从不进行路由委托这是最常见的问题症状是/route list能看到规则但无论问什么问题主AI都自己回答仿佛规则不存在。排查步骤首要检查项allowPromptInjection配置这是最可能的罪魁祸首。运行以下命令双重确认openclaw config get plugins.entries.model-router.hooks输出应该显示{ allowPromptInjection: true }。如果显示false或整个hooks对象不存在你需要重新执行设置命令并重启网关。检查网关日志在启动OpenClaw网关的终端里查看实时日志。当你发送一条应该触发路由的消息时留意是否有相关错误或警告信息。插件加载时的日志也应被检查确认model-router插件被成功加载。验证钩子是否被调用高级调试如果熟悉OpenClaw开发可以临时修改插件代码在before_prompt_build钩子函数里添加一行日志输出例如console.log(‘[ModelRouter] Hook triggered, rules count:’, rules.length)。然后重新安装插件并重启网关观察发送消息时终端是否出现这行日志。如果没有说明钩子注册可能有问题。5.2 问题AI尝试委托但sessions_spawn失败症状主AI回复显示它试图调用sessions_spawn但操作失败了返回错误信息。可能原因与解决方案错误信息特征可能原因解决方案Model ‘xxx/yyy’ not found或Provider not configured模型标识符写错或对应提供商未配置1. 用/route list检查规则中的模型ID。确保格式是provider/model-name。2. 运行openclaw config list检查对应提供商如anthropic,ollama的配置是否正确API密钥或基础URL是否有效。Tool call failed: sessions_spawn ...(无具体模型错误)OpenClaw的sessions_spawn工具本身调用出错可能是权限或内部错误1. 在不使用插件的情况下直接让主AI尝试调用sessions_spawn工具看是否成功。这可以排除插件本身的问题。2. 检查OpenClaw网关版本确保其支持sessions_spawn工具。子任务创建成功但子AI无响应或输出乱码指定的模型存在但可能不适合该任务或子会话初始化有问题1. 尝试在OpenClaw中直接使用该模型进行对话确认模型本身工作正常。2. 检查规则描述是否过于模糊导致传递给子AI的task参数不清晰。可以尝试让规则更具体。5.3 问题路由行为不符合预期症状AI进行了路由但任务被分配给了“错误”的模型或者简单任务触发了复杂模型。分析与调整审查规则描述主AI是基于自然语言理解来匹配规则的。如果你的规则是“写代码用Claude Opus”而用户说“帮我写个简单的Python Hello World”AI可能会认为这也是“写代码”从而触发路由。你需要将规则描述得更精确例如“复杂的代码架构设计、系统设计或算法优化使用Claude Opus”而将“简单的代码片段、语法问题”指向一个更轻量的模型。利用规则列表顺序虽然理论上AI会评估所有规则但你可以通过/route list观察规则的呈现顺序。在定义规则时尽量让更具体、范围更窄的规则先被AI“考虑”到。不过这更多依赖于AI自身的推理能力。进行测试与迭代定义几条核心规则后构造一系列典型的测试问题观察路由结果。根据结果反复调整规则的描述语言。这是一个持续优化的过程。5.4 插件开发与测试注意事项如果你打算基于此插件进行二次开发或者运行其测试套件需要注意单元测试在插件目录下直接运行npx vitest run。这些测试不依赖OpenClaw环境主要验证规则存储和提示词构建逻辑的正确性。集成测试集成测试需要完整的OpenClaw源代码环境。你需要将tests/目录下的测试文件复制到OpenClaw源码树的插件测试目录中然后使用OpenClaw项目的测试命令来运行。这个过程验证了插件在真实OpenClaw环境下的加载、钩子运行和命令注册。踩坑记录集成测试环境搭建时务必注意OpenClaw项目本身的依赖安装通常是pnpm install。直接复制测试文件过去可能会因为模块解析路径问题导致失败需要根据OpenClaw项目的具体结构稍作调整。6. 性能考量、扩展思路与局限性6.1 性能与开销分析这个插件的设计目标之一是轻量高效其对系统性能的影响微乎其微内存与CPU插件本身代码量小常驻内存的只有规则数组通常几KB。before_prompt_build钩子中的逻辑只是字符串拼接CPU开销可忽略不计。延迟主要的延迟来自于主AI对规则的理解和决策过程这本身是LLM推理的一部分。插件注入规则增加的提示词长度非常有限每条约几十个token对主AI的响应速度影响极小。令牌成本这是本插件带来的正收益。它通过避免主模型切换节省了大量上下文重新注入的令牌。虽然给主AI的提示词中增加了规则描述一次性固定成本但相比起将整个对话历史迁移到新模型所消耗的令牌这点增加几乎可以忽略不计。6.2 可能的扩展方向当前插件是一个功能完整的最小可行产品MVP但仍有不少可以增强的方向规则优先级与冲突解决目前规则是平铺的AI自行决定最佳匹配。未来可以引入优先级权重或定义更明确的冲突解决策略如“最先匹配”或“最具体匹配”。基于上下文的动态路由现在的规则是静态的。可以扩展为根据对话历史动态调整路由。例如如果连续三个问题都是编程相关即使第四个问题描述模糊也倾向于路由给代码模型。路由历史与反馈学习记录每次路由的决策用户问题、匹配的规则、使用的模型并允许用户提供“正确”或“错误”的反馈。这些数据可以用于后续优化规则描述甚至训练一个简单的路由分类器。可视化规则管理为Web UI提供一个管理界面可以更直观地添加、编辑、测试和监控路由规则。6.3 当前局限性依赖主AI的理解能力路由的准确性完全依赖于主AI通常是Claude Opus或GPT-4对自然语言规则和用户意图的理解能力。如果主AI“犯糊涂”就可能出现误路由。规则描述的主观性“简单”、“复杂”这类描述是主观的不同AI的理解可能有细微差异。无法处理极其模糊的请求对于“帮帮我”这种极度模糊的请求AI可能无法匹配任何规则从而由主模型处理这可能是合理的但也可能不是用户期望的。子任务结果处理较原始目前子任务的结果直接返回给主AI再由主AI呈现。对于复杂的输出如包含代码块、图片这种传递可能不是最优的有时格式会发生变化。总的来说model-router插件以一种巧妙且低成本的方式在OpenClaw生态中实现了智能的模型路由。它将昂贵的模型调度决策交给了能力最强的AI本身充分利用了现有架构避免了复杂的工程改造。对于需要精细化控制AI调用成本与效果平衡的用户来说这是一个非常实用的工具。我在使用它管理个人和多个项目的AI助手后感觉在响应速度和API费用之间找到了一个很好的平衡点。如果你也受困于“一个模型通吃”的低效不妨试试这个插件从定义两三条核心规则开始逐步构建起你自己的AI任务调度系统。