
这几年做 AI Agent 落地听得最多的一个词就是 agent-skills。很多人一开始以为它就是给大模型挂一堆工具等到真把 Agent 放到业务里跑才发现工具只是手脚真正让 Agent 像老员工一样干活的是它把这堆工具组合成一套成熟动作的能力——这就是技能。我自己是从写单个 function call 起步的那会儿觉得自己很懂 Agent后来在项目里反复被需求打脸才慢慢把 agent skills 当成一个独立的工程领域来对待。这篇文章不聊大而全的框架理论就说我做技能拆分、封装、复用和排错时的真实做法以及踩过之后才知道的那些规矩。1. agent-skills 到底解决什么问题不是多了一个函数是多了一层抽象1.1 工具、技能和工作流三者别混淆先讲一个我在项目评审时经常遇到的场景开发同学说我们已经接了二十个工具Agent 该有的能力都有了。真到了验收环节需求是帮我整理这十份行业报告的关键结论Agent 的表现非常拉胯——它确实会调用读取 PDF 的工具、搜索工具、摘要工具但每次执行路径都不一样有时候搜着搜着就偏了有时候明明读完三份报告就直接开始总结剩下七份完全被忽略。这里缺的恰恰不是工具而是技能。工具解决的是单个动作能做什么比如打开网页、执行 Python、查询数据库它是一个静态能力。技能解决的是一个任务应该怎么做它把一连串工具调用、中间判断、格式约束、异常处理打包成一套可复用的执行方案。工作流则是更大尺度的编排可能同时调动多个技能来跑完一条业务线。我习惯用一个表格来区分这三层维度工具 Tool技能 Skill工作流 Workflow粒度单个动作单个任务跨任务流程输入结构化参数任务描述 上下文流程触发信号或业务事件输出原始结果结构化产物多环节的组合结果复用方式任意场景直接调用按参数复用于同类任务整体复用改动风险更高典型示例web_search(query)竞品情报搜集从线索挖掘到商机报告的全链路很多团队一开始就把精力全砸在接工具上觉得 API 种类越多 Agent 越强。实际跑下来你会发现Agent 能力的下限取决于模型上限往往取决于技能封装得好不好。工具是一堆散装零件技能是把零件拧成部件工作流才是整条产线。1.2 为什么没有技能的 Agent 特别容易飘没有技能约束的 Agent本质上是在让大模型每次遇到任务都临场发挥。临场发挥有多个问题。第一行为不可复用。同一个任务今天执行和明天执行可能走两套完全不同的路径排查问题的时候你不知道该信哪一条日志。第二关键步骤会被跳步。大模型天然倾向于省事尤其是上下文快满的时候它可能扫了两眼资料就开始生成结论那些你希望它必须执行的交叉验证、源数据回溯步骤全被它悄悄省略了。第三输出格式漂移。没有固定模板Agent 给出来的结果今天是表格明天是长文下游解析器根本没法稳定对接。技能层面的封装核心就是为了对抗这三件事。它把该做什么、按什么顺序做、做到什么标准算完这三件事固化下来让模型在有限的弹性空间里跑。技能内部依然有大模型的推理能力但边界和骨架是确定的这样你得到的就不是一个随机行为而是一个稳定、可测试、可评估的执行单元。1.3 技能是对肌肉记忆的模拟我自己做 agent-skills 时最喜欢用的一个类比是技能就是给 Agent 建立肌肉记忆。老员工处理周报不会每次重新想周报要分几段、数据要不要图表他直接按照多年形成的习惯完成。技能做的就是这个事——把成熟做法沉淀下来让 Agent 不用每次从零推理。当技能沉淀得足够多Agent 才有资格去处理更复杂的任务。否则你把它放到一个新场景里它既要理解任务又要设计路径还要控制格式输出质量全看运气。2. 技能的边界感80% 的 Agent 翻车都栽在职责不清2.1 一件事一个技能别把宇宙塞进去技能设计之初最容易犯的错就是贪大。我见过有人封装了一个叫分析一切的技能输入是任何数据输出是任何分析结论。这种技能等于没有技能因为它的内部根本没有可复用的路径大模型照样需要临场发挥。合理的边界是一个技能只对一个任务类型负责。任务类型要从真实业务需求里抽象而不是从工具列表里倒推。比如竞品信息收集是一个任务类型竞品定价变更监控是另一个任务类型。前者面对的是泛化的调研请求后者面对的是结构化、周期性的数据抓取——它们的技能路径截然不同。判断边界是否合理有个很土但很有效的办法你能不能给这个技能写出一句话说明书写不出来就说明边界太模糊。比如该技能负责从零散资料中整理结构化竞品档案包含公司概览、产品线、定价策略、融资动态四个字段这就是一句话能说清的技能。2.2 输入输出约定宁可繁琐不要宽松技能的输入不能是给我一个主题这么粗。要在入口处做约束。我自己设计技能时入口参数一定是结构化字段加校验规则。以竞品调研技能为例{ skill: competitor_intel, version: 2.3.0, input: { competitor_name: { type: string, required: true, description: 目标竞品官方名称或常用品牌名 }, markets: { type: array, items: string, required: false, description: 限定关注市场区域不传则默认全球 }, focus_dimensions: { type: array, enum: [product, pricing, funding, team, channel], required: false, default: [product, pricing, funding] } }, output: { format: json_object, fields: [ company_overview, product_lines, pricing_strategy, funding_status, data_confidence ] } }入口参数写清楚一方面方便外面调用方传参另一方面这些字段会直接拼入技能提示词模型就能明确知道自己要关注什么。输出约定更关键它决定下游能不能稳定消费这份产物。我见过最痛苦的接缝问题就是上游输出变化导致下游解析报错有了强输出 schema这个问题基本能绝迹。2.3 失败兜底技能必须知道自己什么时候该认怂很多技能设计者只考虑正常路径不考虑失败路径。真实环境里搜索接口会断、目标网站会改版、数据源会返回空结果技能如果没有兜底逻辑就会硬着头皮编造结果。我现在的做法是每个技能必须内置三层兜底。第一层是模块级重试对临时性失败做二次尝试第二层是降级策略比如主数据源挂了就切备用数据源或者用模型生成合理估计但显著标注第三层是明确承认失败如果所有路径都走不通技能要输出本次任务未能完成并附上失败阶段和已获得的部分结果而不是给一个虚假的完整答案。尤其在做 agent-skills 时敢于失败这个属性比永远成功重要得多。一个会明确承认完不成的技能比一个会瞎编结果的技能安全十倍。这条规矩在自动化业务链路里直接决定事故等级。3. 一个技能从 0 到 1 的搭建过程用竞品信息收集技能当例子3.1 技能骨架提示词、工具集、验证器的三角结构一个成熟技能内部由三部分组成提示词模板、工具集、验证器。提示词模板负责告诉模型任务的执行顺序和判断标准。工具集是为这个任务预选好的能力列表技能不对所有工具开放只对自己需要的工具开放这一点在安全性和稳定性上都极关键。验证器则承担输出检查的职责它不是大模型而是代码逻辑负责校验格式、必填字段、来源引用是否存在。我写提示词模板时会刻意用必须和禁止来画红线防止模型自由发挥你是竞品情报分析助手。执行步骤固定如下 1. 使用 tool_crawl 抓取竞品官网、官方博客、新闻稿页面至少覆盖 5 个独立域名。 2. 使用 tool_search 补全融资、招聘、产品发布类信息。 3. 对收集到的原始材料按重点维度做标注不要提炼结论先做事实归档。 4. 在归档完成后交叉验证关键数据点至少两处来源一致才可写入报告。 5. 按 output schema 输出 JSON并给每个字段标注 data_confidence。 禁止事项 - 不要在未完成步骤 1 和 2 时开始生成结论。 - 不要把未经来源标注的信息写入报告。 - 如果核心字段无法获取不要猜测填充使用空字符串并注明原因。这套提示词让模型的自由度集中在怎么执行步骤上而不是该不该执行步骤上。实测下来技能输出的稳定性会有质的提升。3.2 工具集选择的三个原则给技能配工具时我遵循三个原则最小集、可替换、可观测。最小集就是只给执行本任务必需的工具能少给就少给。给多了模型就容易在途中被其他工具吸引走注意力。可替换是说每个工具最好抽象成统一接口内部实现可以随时替换。比如我用了一个web_capture接口底层今天可以接爬虫服务明天可以接浏览器渲染服务技能本身不感知。这样工具挂了不用改技能逻辑。可观测则是要求每个工具调用都记录耗时、返回体大小、成功标识这些数据后面排错全靠它们。没有观测的工具调用出问题时就是一个黑洞。3.3 验证器到底验什么验证器是我认为 agent-skills 里被低估最多的模块。很多人觉得提示词写得好就够了但模型输出本质是概率性的必须有一层确定性的校验在前面挡着。我的验证器至少校验四件事字段完整性输出 JSON 中必填字段是否存在类型是否正确。来源可溯性报告里每个核心论断是否关联了 source_url没有来源的一律视为无效。时间逻辑比如财务报表日期、融资时间不能出现晚于当前时间或者明显矛盾的时间线。重复与冲突两份来源数据冲突时验证器要能识别出来并触发交叉验证步骤而不是默默保留未处理的结果。验证器一旦发现异常我不会让它直接硬改结果而是把异常反馈给模型做一轮自我修正。也就是检测—反馈—重跑循环。一般给两轮机会两轮没搞定就转人工或直接判定失败。这套机制让技能的实际准确率从裸跑的六成左右拉到了接近九成。3.4 一个完整执行链路的落地示例我把上述设计合成一个完整的最小执行链路展示下不是代码层面的完整工程但结构很清晰输入竞品名称如 GrowthLab Inc. → 参数校验与标准化 → 加载 competitor_intel 技能 → 照提示词模板启动执行计划 → 工具集开始抓取官网、新闻、招聘、融资库 → 中间做数据归档逐条记录来源 URL、抓取时间 → 交叉验证关键指标 → 输出结构化 JSON过验证器 → 验证不通过则触发模型修正循环最多两次 → 输出最终产物 置信度字段 失败原因记录这条链路我跑了大概四个月覆盖三个行业的竞品调研场景整体表现非常稳定。核心经验是技能不追求让模型更聪明追求的是让模型的路走得更确定。4. 通用技能库和项目定制技能怎么分配才合理4.1 技能分层底座层、业务层、现场层技能积累到一定数量之后就会面临一个管理问题哪些技能应该沉淀成公共资产哪些技能应该躺在具体项目里。我的做法是把技能分成三层。底座层是跟领域无关的通用技能比如网页内容清理长文本按结构拆分多源数据去重合并。这一层几乎每个项目都用得上需要写得极其稳定测试最严格因为影响面最大。业务层是跟某个业务领域强相关的技能比如金融研报摘要电商商品信息抽取竞品情报收集。它们可以在同领域的不同项目中复用但换领域就不适用。现场层则是项目现场一次性写的临时技能代码仓库都不一定进只服务于本次需求。分层决定了你能复用多少也决定了谁有权限改。底座层和业务层的技能变更必须走评审和回归测试现场层可以写得糙但出了问题也就影响局部。4.2 什么时候该复用什么时候该新写我总结了几个判断标准凡是符合三条以上的就值得新写一个技能任务类型在现有技能库里找不到对应物现有技能如果硬套需要在提示词里加大量 if else 分支复杂度明显上升目标任务的产出格式与现有技能完全不兼容任务的失败模式和兜底策略完全不同任务牵涉的数据源类型与权限体系不一样。不少团队掉进过强行复用的坑。我看过一个项目硬用一个通用网页信息抽取技能去处理银行 PDF 对账单结果解析错误率一直在百分之四十以上后来专门写了银行流水表解析技能错误率一下子降到百分之三。复用是好品质但硬复用比新写更贵。4.3 技能版本化是早晚要做的事技能一旦进入共享库就必须版本化。我用的方案很朴素每个技能包里有 version 字段技能包整体打进代码仓库用 Git 管理变更记录。技能之间如果存在依赖关系在描述文件里声明依赖的技能名和版本区间防止上游技能改了结构下游直接崩。这里分享一个重要教训技能变更最大的风险不是提示词改了效果变差而是输出结构变了导致下游消费者没人通知。为了根治这个我要求任何技能变更 output schema 时必须同时更新下游解析器的兼容层并单开一个契约测试。这个机制执行之后由技能升级引起的事故基本清零。5. 让技能在生产环境里跑稳测试、日志与迭代闭环5.1 给技能做单元测试而不是只看 demo很多人验证技能好坏的方式是跑两个 demo觉得效果不错就上线。这实在不够。现在我把技能测试分四级单测、回归、对抗、压测。单测是给定固定的标准输入断言输出结构、关键字段、禁止行为是否达标。回归是对历史跑过的 50 到 100 条真实输入重新执行确保新改动没让旧样本变差。对抗测试是人为构造脏数据、断网、超时、空响应看技能会不会瞎编。压测则是模拟高频调用观察技能涉及的第三方 API 是否会被限流、缓存策略有没有生效。单测覆盖率达到多少我不追求百分之百但对于核心技能我会保证单测样本里包含至少 20 种典型输入变体覆盖正常、异常、边界三类情况。对抗测试出的问题往往比正常用例更有价值。5.2 日志里必须包含的七个字段技能运行日志的质量直接决定事故排查速度。现在的技能日志我都会输出下面这些字段skill_id 和 version定位具体技能版本trace_id贯穿整个任务链路的标识用于串联多技能协作requested_at / started_at / finished_at用于计算耗时和发现有死循环input_hash输入快照的哈希值方便复现问题但避免存全量敏感数据plan_summary模型自己生成的执行计划摘要tool_calls每一步工具调用的清单、状态、耗时output_validator_report验证器检查结果的详细记录。有了这些排查问题基本能定位到具体哪一步而不是靠猜。技能跑得多了以后你会发现日志设计其实是在给 Agent 的可解释性兜底。5.3 灰度上线和回归阈值技能模型是软件工程就不能跳过分级发布。我现在做技能发布的标准动作是先在仿真环境跑回归全量样本通过率低于 95% 不准上线。然后灰度放量到 10% 的真实流量观察三个指标任务完成率、格式通过率、用户重试占比。如果三个指标都不劣于旧版再逐步放量到 50%、100%。一旦灰度期间发现完成率掉 5 个点以上立即回滚。这套灰度机制看着笨重但真正能拦住大事故。我有一次改了一个看似人畜无害的提示词措辞把至少收集 5 个独立域名改成了尽可能覆盖多个来源灰度指标立刻掉了一大截因为模型开始偷偷减少抓取量。如果没有灰度这个改动就会直接污染全部线上任务。6. 做 agent-skills 这两年的复盘最好用的规矩和最常踩的坑6.1 五个值得沉淀的硬规矩第一技能必须是可评估的。任何技能上线前都要有可量化的通过标准投入再大的技能不能评估就不要上线。第二提示词里多写禁止项少写鼓励项。你可以这样做在模型眼里几乎没有约束力禁止那样做才有。第三技能内部不要让模型直接读整个网站原文强制先摘要再归纳不然上下文爆炸只是时间问题。第四第三方工具失效时技能必须显式降级绝不能默默跳过某一步继续后续逻辑。第五所有技能参数都要有默认值主调用方漏传时技能还能在合理假设下运行同时把假设写入日志方便后续纠正。6.2 新人最容易踩的坑我基本都踩过刚做 agent-skills 时我最大的毛病是总想通过在提示词里堆细节来提升效果。提示词越来越长模型表现得越来越差因为关键指令被淹没在大量软性描述里。后来改成把指令压缩筛选只保留影响行为的硬约束效果反而好了不少。这不只是我一个人的经验团队里后来的新人也反复踏上同一条弯路。另一个坑是轻视状态管理。有些技能执行过程中需要记住之前的中间结果比如已访问过哪些页面哪些字段已经有来源支撑。如果状态管理做不好技能会反复做重复工作甚至漏掉依赖关系。我现在特别强调把中间状态显式写入执行上下文每一步都从上下文读取最新状态而不是依赖模型自己记住。还有一个特别现实的坑模型版本升级后技能表现居然会变差。同一个提示词在旧版本模型上稳定输出在新版本模型上却频繁违反禁止项。这说明技能不是一次性的工程模型一变所有技能都得过一遍回归测试。我们后来把模型版本也纳入技能依赖声明里写明该技能在哪个模型版本区间做过验证。6.3 持续沉淀而不是一次性交付最后想强调一点agent-skills 的价值随数量和质量指数级上升但前提是持续维护。我会为每个技能建立一个极简的档案一句话定位、边界说明、最近三次变更说明、当前已知风险。这个档案不需要很长但必须维护。技能一旦进入运行状态就以两周为一个周期看一次通过率指标和失败样例不是为了完成 KPI而是为了发现提示词里那些已经开始失效的假设。技能建设没有终点只有不断迭代。真正好用的 agent-skills 不是你某一次灵光一现写出来的而是跑了几百次真实任务、踩过十几个隐蔽的坑之后一点点打磨成型的。如果你现在准备开始建自己的技能库我的建议是从一个任务类型最简单、又反复出现的场景入手把它做成一个极致的技能跑上一个月再慢慢铺开。一上来就想覆盖所有场景通常会得到一个哪里都能凑合、哪里都不够可靠的半成品。