最近一段时间,AI Agent 的热度又起来了,但真正能把 Agent 用进生产环境的人其实不多。我见过太多团队把 Agent 当成一个“聊天机器人”来调,结果 Chat 的时候什么都好,一放到工作流里就怎么都不对。今天想聊的这套东西,我把它叫做Skills:给 AI Agent 配一套工程工作流。说白了,就是给 Agent 配一套可复用、可调试、可评估的能力体系,让模型不再只是“会说话”,而是真的“能干活”。
这篇文章的目标读者,不是刚接触大模型 API 的入门玩家,而是那些已经跑通了一个 Demo,正在被 Agent 的稳定性、可维护性、评估问题折磨的开发者。我会从设计思路讲到代码实现,再讲到我踩过的坑和总结出来的调试方法,争取让你看完之后能直接照搬一套工作流到自己的项目里。
1. 为什么 Agent 需要一套 Skills 工程框架
1.1 从玩具到工具:Agent 落地的真实困境
先说一个很普遍的现象:很多团队最早做的 Agent Demo,本质上就是把用户问题拼进 Prompt,然后丢给大模型,让它自己决定调什么函数、用什么工具。Demo 阶段一切都很美好,因为测试问题都是人为挑过的,上下文也短,模型不会迷路。但一旦放到真实业务里,问题就暴露了:
- 模型经常选错工具,或者用了错误参数。
- 工具调用链一旦超过三四步,就开始出现上下文污染。
- 中间任何一步报错,整个流程就崩了,没有任何恢复机制。
- 出问题之后完全不知道是 Prompt 的问题、工具的问题,还是模型本身抽风。
这些问题不是靠“多写几个 Prompt”能解决的。本质上是因为你给 Agent 的能力是“散装”的,没有形成一套可以约束、可观测、可迭代的工程结构。Skills 框架要解决的,就是把“模型自由发挥”转变成“模型在边界内执行”,把不确定性关进笼子里。
我用一个比喻来解释:没有 Skills 的 Agent 就像一个新来的实习生,你告诉他“你去处理一下客户投诉”,他可能会干得很好,也可能闯大祸;但你如果给他一份标准作业流程、一套填好的表单、一个异常上报按钮,他至少能稳定发挥 80 分。Skills 就是那份标准作业流程。
1.2 什么是 Skills:把能力抽象成可复用单元
我给Skill下的定义很简单:它是 Agent 可以调用的一组最小能力单元,包含调用方式、输入输出定义、运行逻辑、资源依赖和失败处理策略。
一个 Skill 不等于一个“工具函数”。工具函数只是代码,而 Skill 是围绕这个代码形成的完整契约。比如“查天气”这个能力,最低级的实现是写一个get_weather(city)函数,然后在 Prompt 里告诉模型“你可以调用它”。但工程化的 Skill 还需要包含:
- 这个工具什么时候该用、什么时候不该用,比如查天气不能用来查空气质量。
- 输入参数怎么写,比如城市名要转成地区编码,还是直接传拼音。
- 返回结果如何被 Agent 理解,比如原始 JSON 要清洗成自然语言摘要。
- 超时、限流、API 报错后该怎么办,比如失败后要不要换备用数据源。
这些信息都应该打包在一个 Skill 元数据文件里,而不是散落在 Prompt 或代码注释中。这样 Agent 的能力边界才清晰,人才能对它的行为有预期。
1.3 Skills 和 Plugins、Tools、Workflows 有什么区别
很多读者会问:这不就是 Plugin 吗?确实有重叠,但侧重点不同。Plugin 是从宿主应用视角讲的,重点在“扩展应用能力”;Tool 是从模型视角讲的,重点在“函数调用”;而 Skills 是从“作业流程”视角讲的,重点在于“一个完整的工作单元”。
举例来说,单纯的 Tool 是一次“问答”:用户问 -> 模型调函数 -> 返回结果。而 Skill 可以是多步骤的:用户想要一份竞品分析报告 -> Agent 先爬取网页 -> 再调用摘要模型 -> 然后生成结构化文档 -> 最后发送到指定邮箱。这整个流程是一个 Skill,内部又可以拆成多个 Tool 调用。
Workflow 则是更高一层的概念,通常指多个 Skill 的编排。比如 “周报生成工作流” 可以拆成 “数据收集 Skill”、“文档生成 Skill”、“消息推送 Skill” 三个子技能的串联。实际项目中这两者经常混用,但只要把握住“Skill 是做一件事的最小完整闭环”,就不太会设计错。
2. Skills 工作流的整体设计与模块拆解
2.1 设计原则:最小可用、关注边界、渐进增强
我在设计这套 Skills 工作流时,有几个原则是反复踩坑踩出来的,直接分享给大家。
第一是最小可用。一个 Skill 不要一开始就追求覆盖所有边界情况。宁可先支持 80% 的主流场景,把流程跑通,再通过实测数据去补边角。否则很容易陷入“边开发边重构”的死循环。
第二是关注边界。每个 Skill 一定要明确它的“适用范围”。我见过太多 Agent 工具因为描述太宽泛,导致模型在无关问题上也强行调用。比如你给 Agent 一个“文档解析”能力,它就敢把垃圾分类的图片也拿去解析成文字。所以 Skill 描述里要写清楚“输入必须包含文本型图片,否则拒绝执行”,甚至可以直接在代码里做前置校验。
第三是渐进增强。所有 Skill 都要支持“先手动、后自动”的切换。刚开始跑流程的时候,我建议把 Agent 的所有决策点都打印出来,让人确认每一步。等积累了一批稳定案例之后,再逐步放开成自动执行。没有这个过渡期,你根本分不清是模型错了还是工具错了。
2.2 四大模块:定义、编排、执行、反馈
一个完整的 Agent Skills 工程工作流,我通常拆成四个模块:
- 定义层:负责 Skill 的注册、参数 Schema 管理、描述生成。相当于所有能力的名录。
- 编排层:负责决定当前任务要调用哪些 Skill,以及这些 Skill 的调用顺序。这一层可以由大模型动态决策,也可以由预先设定的 DAG 静态编排。
- 执行层:负责真正跑 Skill 的代码、资源分配、超时控制、重试机制。这是最容易出问题的地方,也是需要埋点观测的地方。
- 反馈层:负责把执行结果回传给模型、记录日志、生成评测指标,甚至是把失败的案例汇总成新的评测样例。
四个模块的依赖关系要控制成单向的:定义层不依赖执行层,执行层不关心编排层怎么选它。这样模块之间可以独立测试和替换。比如你想把某个 Skill 的底层实现从用第三方 API 换成本地模型推理,只需要改执行层里的一个类,定义层和编排层完全不用动。
2.3 目录结构与配置文件:一个 Skill 应该长什么样
我在项目里用一个可序列化的目录结构来管理 Skill,每个 Skill 都是一个文件夹。结构大致如下:
skills/ ├── weather_check/ │ ├── SKILL.md │ ├── schema.py │ ├── executor.py │ ├── requirements.txt │ └── tests/ │ └── test_weather.py ├── report_generator/ │ ├── SKILL.md │ ├── schema.py │ ├── executor.py │ └── tests/ └── shared/ ├── llm_client.py └── http_client.py其中SKILL.md是给大模型看的 Skill 描述,schema.py是给代码用的入参校验,executor.py是核心执行逻辑。这样分隔的好处是:模型的 Prompt 上下文里只需要注入SKILL.md的摘要,而不需要把整个 Python 代码都塞进去,能省下不少 token,也让模型更聚焦于“什么时候调用”而不是“内部怎么实现”。
SKILL.md的格式我自己固定成这样:
--- name: weather_check description: 查询指定城市当前天气,仅使用于天气相关的用户问题。输入 city 必须是中文城市名,例如“杭州”。 version: 1.0.0 --- 输入: - city: string, 必填,中文城市名 输出: - 包含天气状况、温度、湿度、风力的自然语言描述 失败处理: - 若城市不存在,返回错误码 CITY_NOT_FOUND,不猜测其他城市。这里最关键的是description和失败处理两段。前者决定了模型会不会误用这个 Skill,后者决定了 Agent 能不能体面地从错误中恢复。很多人在定义工具时只写“能做什么”,从来不写“不能做什么”和“失败后怎么办”,这是后续 Agent 行为失控的主要原因。
3. 核心实现:从零搭一套可运行的 Agent Skills 流水线
3.1 技术选型取舍:为什么我选了轻量方案
在真正动手写代码之前,需要先做技术选型。当前市面上的 Agent 框架不少,有的偏重多 Agent 对话,有的偏重代码执行沙箱,有的偏重流程可视化。但我的建议是,如果你刚准备给项目配一套 Skills 工作流,不要一上来就引重框架,先用最轻量的 Python 结构把流程跑通。
我当前使用的组合非常简单:
- Python 3.11:类型标注和异步支持都比较舒服。
- Pydantic:定义 Skill 的输入输出 Schema,顺手做校验。
- 标准库
asyncio:做多个 Skill 的并发调用控制。 - 一个简单的 LLM 客户端封装:不限定具体的模型厂商,底层通过统一接口调用。
这么选的原因很直白:重框架会把“模型调用-工具注册-流程控制”揉在一起,出了问题你很难定位是自己的逻辑错还是框架的隐藏行为。自己写一个不到 200 行的 runner,反而能完全掌控整个流程。等需求复杂到代码量扛不住的时候,再迁移到成熟框架也不迟。
3.2 定义 Skill Registry:把能力变成“可注册”的对象
所有 Skill 都需要一个注册中心,这样编排层才能知道当前系统有哪些能力可用。我用一个简单的 Python 类来实现:
from dataclasses import dataclass, field from typing import Dict, Callable, Any @dataclass class Skill: name: str description: str executor: Callable[..., Any] input_schema: Dict[str, Any] timeout: float = 10.0 retry_times: int = 2 class SkillRegistry: def __init__(self): self._skills: Dict[str, Skill] = {} def register(self, skill: Skill): if skill.name in self._skills: raise ValueError(f"Skill {skill.name} 重复注册") self._skills[skill.name] = skill def get(self, name: str) -> Skill: if name not in self._skills: raise KeyError(f"Skill {name} 不存在") return self._skills[name] def list_skills(self) -> list[dict]: return [ {"name": s.name, "description": s.description} for s in self._skills.values() ]这个 Registry 的要点有两个:一是 name 唯一,避免两个技能名字撞车;二是list_skills()只返回描述信息,不返回内部实现。这样当你把技能列表注入到 Prompt 里时,模型不会看到一堆与决策无关的类名和路径。
3.3 定义输入 Schema 与前置校验
给 Skill 配输入 Schema 不只是为了给模型看,更是为了在代码层拦截无效调用。我经常看到一些 Agent 在调用工具时传了奇怪参数,比如城市名带空格、日期格式不对、文件路径不存在。如果不在入口卡住,这些错误会一路传播到下游,最后变成一条莫名其妙的报错日志。
我使用 Pydantic 来定义每个 Skill 的入参模型:
from pydantic import BaseModel, Field class WeatherInput(BaseModel): city: str = Field(description="中文城市名,例如“杭州”", min_length=2, max_length=30) unit: str = Field(default="celsius", description="温度单位:celsius 或 fahrenheit")然后在 executor 执行前加一道统一校验:
def run_skill(skill: Skill, raw_input: dict): try: # 这里根据 skill.input_schema 动态创建 Pydantic 模型 validated = skill.input_schema(**raw_input) except Exception as e: return {"error": "INVALID_INPUT", "detail": str(e)} try: result = skill.executor(**validated.model_dump()) return {"result": result} except Exception as e: return {"error": "EXEC_FAILED", "detail": str(e)}这一层看起来朴素,但价值很大:它把“模型传参错误”和“技能执行失败”两类问题区分开。模型传参错误说明决策层有问题,需要优化 Prompt 或 Schema 描述;技能执行失败说明代码或上游依赖有问题,需要看异常栈。前者是 AI 问题,后者是工程问题,混在一起会非常难排查。
3.4 执行器实现:超时、重试与并发控制
执行层是 Agent 最容易出现“悬挂”和“雪崩”的地方。一个 Skill 如果超时没有返回,Agent 的整个上下文就可能卡住。我通常给每个 Skill 配置独立的超时时间和重试策略。
核心的执行代码可以这样写:
import asyncio async def execute_with_retry(skill: Skill, kwargs: dict) -> dict: last_exception = None for attempt in range(skill.retry_times + 1): try: # 用 asyncio.wait_for 实现硬超时 result = await asyncio.wait_for( skill.executor(**kwargs), timeout=skill.timeout ) return {"success": True, "data": result} except asyncio.TimeoutError as e: last_exception = e except Exception as e: last_exception = e if attempt < skill.retry_times: await asyncio.sleep(0.5 * (attempt + 1)) # 简单退避 return {"success": False, "error": str(last_exception)}这里的重试逻辑要注意一个问题:不是所有 Skill 都适合重试。比如“发送邮件”这种不可幂等的操作,重试可能导致同一个用户收到两封邮件。所以我会在 Skill 元数据里加一个idempotent标志,只有标志为真的 Skill 才允许重试。这点非常重要,我吃过大亏。
对于并发控制,我的经验是给整个 Agent 的 Skill 调用设置一个信号量限制。比如同时最多允许 3 个 Skill 在执行。因为如果不对规模做限制,一个任务可能瞬间触发十几个外部 API 请求,既容易被限流,也会让本地资源耗尽。
3.5 编排层:从“动态决策”到“稳定执行”
编排层的职责是决定下一步调用哪个 Skill。我见过两种主流风格:一种是完全让模型自由决策;另一种是用代码写死流程。前者灵活但不可控,后者可控但僵硬。我的做法是采用“意图路由 + 子流程限位”的混合编排。
首先,在系统提示词里,我会这样约束 Agent:
你有以下 Skills 可用: {skill_list} 你的任务是解决用户问题。规则如下: 1. 只能使用上面列出的 Skill,禁止自由编造工具。 2. 优先拆解问题,一次只执行一个 Skill,等待结果后再执行下一个。 3. 当某个 Skill 返回错误时,忽略重试,直接向用户告知无法完成。然后,我会在代码里对 Skill 调用次数做限制。比如一个任务最多连续调用 5 次 Skill,超过后自动终止。这个限制能有效防止模型陷入“循环调用”的陷阱。实测下来,像“反复调用同一个工具但参数略微变化”这类问题非常常见,限制次数是一剂猛药。
对于需要固定先后顺序的场景,比如“先收集数据,再生成报告”,我会在编排层用一个简单的状态机:
STEPS = ["collect_data", "generate_report", "send_email"] def next_step(current_step: str) -> str: try: return STEPS[STEPS.index(current_step) + 1] except IndexError: return None这种静态编排的好处是可以通过单元测试验证顺序,不会因为模型“自由发挥”而颠倒步骤。对于确定性强的流程,我的建议是能静态就静态,动态留给那些真正需要创意的环节。
3.6 工作流中的上下文管理:避免记忆污染
在 Agent 工作流中,上下文管理是最容易被忽视、却又最重要的一环。默认情况下,如果把每一次工具调用的原始返回都塞进对话上下文,几千 token 很快就没了,而且那些 JSON 噪声会严重干扰模型后续决策。
我的做法是维护一个独立的上下文缓冲器,它只保留三样东西:
- 用户原始请求。
- 每一步执行的“人类可读摘要”。
- 最终输出结果。
所谓“人类可读摘要”,就是让 Agent 在调用 Skill 后把结果压缩成一句话。比如调用天气 Skill 后,不保留完整 JSON,而是保留“杭州当前 26 度,多云,东南风 3 级”。这个摘要既满足后续决策需要,又不会让上下文膨胀。压缩动作可以交给同一个大模型来做,但要注意设置单次摘要的 token 上限,防止摘要本身太长。
3.7 可观测性:日志、追踪与指标
没有可观测性的 Agent 系统等于裸奔。我给 Skills 工作流里每个关键点都埋了可观测数据,具体分三类:
- 调用日志:每次 Skill 调用,记录时间、Skill 名称、入参、出参、耗时、是否重试、错误信息。
- 追踪 ID:一个用户请求从开始到结束,所有 Skill 调用共享同一个
trace_id,方便按请求维度查日志。 - 核心指标:Skill 调用成功率、平均耗时、P95 耗时、重试率、上下文 token 消耗量。这些指标我会定期做成报表,用来判断模型和工具的表现趋势。
日志格式我用 JSON 结构化输出,而不是一堆纯文本。这样后续接到日志平台或做统计分析都非常顺畅。一个典型的路由日志长这样:
{ "trace_id": "7f23a9c", "skill": "weather_check", "action": "execute", "status": "success", "duration_ms": 340, "retry_count": 0, "timestamp": "2024-06-01T10:12:33Z" }有了这些数据,你才能回答一个核心问题:“这周 Agent 的表现到底比上周好还是坏”。没有指标,你就只能凭感觉,而凭感觉优化 Agent,只会越优化越糟。
4. 调试与评测:工程工作流的落地关键
4.1 失败模式:Agent 最常见的几类坑
我在实测过程中,发现 Agent + Skills 结构的失败模式高度集中,下面列四个最常见的。
- 误选 Skill:模型在用户问题与 Skill 描述有语义重叠时,很容易选错。比如用户问“杭州今天适合穿什么”,模型可能调了“天气查询”而不是“穿衣建议”。这类问题的根因往往是 Skill 描述写得过于宽泛,缺少边界条件。
- 参数幻觉:模型会凭空编造一个城市名、日期或文件路径,即使它在上下文里根本找不到这个信息。这类问题要靠 Schema 描述里的“必填”和“值域”约束,以及前置校验来缓解。
- 上下文漂移:随着多轮调用,模型会慢慢忘记最初的用户目标,开始根据中间步骤产生的新内容发散。我的解决方式是每轮都回显“当前任务原始目标”,并提醒模型只能围绕该目标继续。
- 反馈失联:Skill 返回的错误信息如果不够明确,模型就无法理解失败原因,只能反复重试。所以 Skill 的异常返回必须带一个标准错误码和一句话描述,比如
CITY_NOT_FOUND: 你提供的城市名不存在。
4.2 评测集怎么建:把回归测试引入 Agent
Agent 的评测不能只靠人工“点几个例子看看”。工程化工作流一定要有可自动运行的回归测试集。我的构建方法是三步走。
第一步,收集真实历史请求。从最早期的线上日志和人工测试记录里,抽样 50~100 条有代表性的请求,覆盖正常路径、边界路径、异常路径。
第二步,为每类请求打标签。比如weather_query_normal、out_of_scope、multi_step_task、missing_parameter。标签的作用是后续可以分别计算每个场景的成功率,看清楚到底哪一类问题最多。
第三步,写一个自动评测脚本。流程是:请求 -> 跑 Agent -> 比对最终结果。结果比对不要求完全一致,而是判断是否满足预期行为。比如对于天气查询,如果模型返回了“当前温度”、“天气状况”、“风力”三个关键字段,就算成功;如果返回了“穿衣建议”但没查天气,就算失败。
我之前实现过一个简易的评测函数,用规则加 LLM 双重判断:
def evaluate_response(request, response, expected_hint): # 规则校验:关键字段是否存在 for keyword in expected_hint["required_keywords"]: if keyword not in response: return "FAIL" # LLM 校验:语义是否完成用户请求 judge_prompt = f"判断下面的回答是否解决了用户问题:{request}。回答:{response}。只回答 PASS 或 FAIL。" judge_result = llm_call(judge_prompt) return judge_result.strip()这种“规则 + LLM 双重判断”的方式可以大幅减少误报。单独用规则太死板,单独用 LLM 又可能不稳定,结合起来会发现效果是最稳的。
4.3 回归测试的自动化落地
评测集不能只建不用。我会把评测集接入到一个简单的 CI 流程里,每次修改任何一个 Skill 的定义或代码之后,先跑全套回归测试,再发布。手动跑也可以,但人总会偷懒,所以能自动还是要自动。
自动化回归的核心是一个 Runner 脚本,它的伪代码大致是:
for case in test_suite: agent = create_agent(with_skills=skills) response = agent.run(case.request) result = evaluate_response(case.request, response, case.expected_hint) print(f"{case.id} -> {result}") if result == "FAIL": collect_failure(case, response)跑完之后,我会重点关注两个指标:整体通过率和失败案例分布。整体通过率如果低于 80%,我不会考虑上线新改动;如果失败案例集中在某一个 Skill 上,说明这个 Skill 的描述或者执行逻辑有明显问题,需要单独拎出来调。
这里有一个经验:评测集要持续扩充。每一次线上失败案例,都是最好的测试样例。我每周都会把新增的线上失败请求加入评测集,确保同一个坑不会在下次改版后再次踩到。
4.4 线上监控与告警:让 Agent 在“出事前”被拦住
评测集只能覆盖离线场景,线上监控才能真正反映运行状态。我给 Agent 服务配的监控指标,除了常规的 CPU、内存之外,还有几个 Agent 特有的:
- Skill 调用分布:看看每个 Skill 被调用的频率是否合理。如果“查天气”在业务场景里一天被调用几百次,而实际业务根本不关心天气,那一定是误选。
- 平均每任务 Skill 调用次数:这个值如果突然飙升,说明 Agent 可能陷入了无效循环。
- 上下文 token 消耗速率:防止上下文无限增长导致成本失控。
- 错误码分布:比如
INVALID_INPUT增多,说明模型参数幻觉加重;EXEC_FAILED增多,说明上游 API 不稳定。
告警的阈值我建议先设置得宽松一点。刚开始不要追求“精准告警”,而是多记录数据,跑两周之后根据数据分布再来设定合理的阈值。上来就设一个 P95 告警,结果一天到晚被误报骚扰,最后只会变成“狼来了”,真的故障发生时反而没人响应。
5. 实战踩坑记录与经验总结
5.1 实测下来最容易翻车的三个点
这部分的坑我基本都实际踩过。第一个坑是Skill 描述过于抽象。最开始我给“文档生成”这个 Skill 写的描述是“能够根据输入内容生成一份结构完整、格式美观的文档”。结果模型在用户问“今天天气怎么样”时也强行调用它,生成了一篇作文。后来我把描述改成“仅当用户明确要求输出文档文件(如 Word/Markdown/PDF)时调用”,误选率立刻下降了一半以上。
第二个坑是无限制重试导致上游被拉爆。有一次某个外部的数据源接口偶发超时,我的重试逻辑没有做幂等控制,结果同一个失败请求连续重试了五次,直接把那个数据源打成了限流。后来我不仅加上了幂等标志,还把重试次数统一限制为最多两次,并且增加随机退避,再也没发生过这类事故。
第三个坑是上下文摘要吞掉关键信息。我以为把所有工具原始返回都转成一句话摘要会更干净,但有些场景里原始 JSON 里的具体数值比语义摘要更关键,比如用户问“杭州明天的气温曲线”,我摘要成一句“杭州明天天气不错”,模型就再也没法回答精确数据了。现在的做法是:摘要里必须保留可计算的数值关键项,其他辅助信息可以省略。
5.2 一些实用技巧:从运行效率到成本优化
再分享几个可以直接抄的小技巧。
关于 token 成本控制,我会使用分级摘要策略。对于单次 Skill 调用,如果返回结果小于 300 token,则保留原文;如果大于 300 token,则让模型压缩成不超过 100 token 的摘要。这样既不丢信息,也不会被长文本淹没。
关于 Skill 的并发,我建议把“可以并行的 Skill”和“必须串行的 Skill”分开定义。比如“同时查询多个城市天气”是可以并行的,而“先下载文件再解析文件”必须串行。我在编排层加了一个依赖声明,Skill 可以标记depends_on字段,这样 Runner 就能自动判断哪些可以并发执行,实测把多城市查询类任务的总耗时缩短了 40%。
关于模型选择,不同 Skill 可以用不同模型。比如简单格式化任务用便宜的小模型,而涉及复杂推理的写代码任务用能力更强的模型。我的做法是在 Skill 元数据里加一个model_hint字段,执行层根据字段路由到对应的模型服务。这样不仅提升了质量,还能明显降本。
5.3 Skills 工作流的扩展方向
最后聊聊这个工作流后续还能怎么扩展。我在当前的实现里,主要跑的是“单 Agent + 多 Skill”结构,但实际业务里已经有团队在往“多 Agent 协作”方向演进。到那个阶段,Skills 的定义和编排粒度就需要重新划分:每个 Agent 持有自己的 Skill 子集,Agent 之间通过消息队列传递中间结果。
另外一个趋势是 Skill 的自动化生成。既然 Skill 本身就是一份带有配置和代码的目录,那理论上我们可以写一个 Skill 生成器,输入一份业务文档,输出一个带 Schema 和 executor 骨架的新 Skill。我目前已经做了一个粗糙版本,效果还不完美,但明显感觉到这条路值得继续深入。
还有一点关于评测的扩展:现在的评测集主要是面向“任务是否完成”的二元判断,但实际业务指标远不止这些。比如“用户满意度”、“处理耗时”、“成本消耗”都应该折算进评测体系。未来可以把评测结果和业务指标做关联分析,这样才能回答“这套 Agent Skills 带来了多少商业价值”这个终极问题。
这段内容是我个人项目里最受益的一段,也分享给所有正在做 Agent 工程化的团队。反正 Agent 落地这件事,从来不是“模型够聪明”就行,而是“能不能用工程手段让它稳定地执行”。Skill 描述里加一点边界、执行层加一点超时控制、评测集里加一点历史失败案例,长期积累下来,你会发现 Agent 的表现会越来越像“一条靠谱的生产流水线”,而不是一个随时脱缰的聊天机器人。