跳到主要内容

最佳实践

编写高质量的 Skill 不仅是技术问题,更是设计问题。本章总结了一系列最佳实践,帮助你创建专业、可维护、高效的 Skills。

从真实专业经验出发

编写有效 Skill 的一个常见误区是让 LLM 在没有提供领域特定上下文的情况下生成 Skill——仅依赖 LLM 的一般训练知识。结果是模糊、通用的流程(如"适当处理错误"、"遵循认证最佳实践"),而不是具体的 API 模式、边界情况和项目约定。

有效的 Skill 必须基于真实的专业经验

从实际任务中提取

在与 Agent 协作完成真实任务的过程中,提供上下文、纠正和偏好,然后提取可复用的模式。关注以下方面:

  • 成功的步骤:导致成功的操作序列是什么?
  • 你做的纠正:你引导 Agent 方法的地方(如"用库 X 代替 Y"、"检查边界情况 Z")
  • 输入/输出格式:数据进出时的样子是什么?
  • 你提供的上下文:Agent 不知道的项目特定事实、约定或约束

从现有项目文档中综合

当你有现有的知识体系时,可以将其综合成一个 Skill。从团队实际事故报告和运维手册综合的数据管道 Skill,将优于从通用"数据工程最佳实践"文章综合的 Skill,因为它捕获了你的模式、故障模式和恢复程序。

好的源材料包括

  • 内部文档、运维手册和风格指南
  • API 规范、模式和配置文件
  • 代码审查评论和问题跟踪器(捕获重复关注点和审查者期望)
  • 版本控制历史,特别是补丁和修复(通过实际变更揭示模式)
  • 真实的故障案例及其解决方案

用真实执行来优化

Skill 的初稿通常需要优化。针对真实任务运行 Skill,然后将结果——所有的结果,不仅仅是失败的——反馈到创建过程中。问:

  • 什么触发了误报?
  • 什么被遗漏了?
  • 什么可以删减?

即使只有一次执行-然后-修订的流程也能显著提高质量,复杂领域通常需要几次迭代。

核心原则

简洁是关键

上下文窗口是公共资源。你的 Skill 与 Agent 需要知道的其他所有内容共享上下文窗口,包括:

  • 对话历史
  • 系统上下文
  • 其他活跃的 Skills

并非 Skill 中的每个 token 都有即时成本。启动时,只预加载所有 Skill 的元数据(name 和 description)。Agent 只在 Skill 变得相关时才读取 SKILL.md,并只在需要时读取额外文件。然而,保持 SKILL.md 简洁仍然很重要:一旦 Agent 加载了它,每个 token 都会与对话历史和其他上下文竞争。

默认假设:Agent 已经很聪明

只添加 Agent 还没有的上下文。质疑每条信息:

# 好的例子:简洁(约 50 tokens)

## 提取 PDF 文本

使用 pdfplumber 进行文本提取:

```python
import pdfplumber

with pdfplumber.open("file.pdf") as pdf:
text = pdf.pages[0].extract_text()

不好的例子:太啰嗦(约 150 tokens)

提取 PDF 文本

PDF(便携式文档格式)文件是一种常见的文件格式,包含文本、图像和其他内容。要从 PDF 中提取文本,你需要使用库。有很多库可用于 PDF 处理,但推荐使用 pdfplumber,因为它易于使用且能很好地处理大多数情况。首先,你需要使用 pip 安装它。然后你可以使用下面的代码...


简洁版本假设 Agent 知道 PDF 是什么以及库是如何工作的。

### 设置适当的自由度

根据任务的脆弱性和多变性,匹配指令的具体程度。

**高自由度**(基于文本的指令):当多种方法有效且任务可容忍变化时使用。

```markdown
## 代码审查流程

1. 分析代码结构和组织
2. 检查潜在的 bug 或边界情况
3. 建议可读性和可维护性改进
4. 验证是否遵循项目约定

中等自由度(伪代码或带参数的脚本):当有经过验证的方法但需要调整参数时使用。

## 生成报告

使用此模板并按需自定义:

```python
def generate_report(data, format="markdown", include_charts=True):
# 处理数据
# 以指定格式生成输出
# 可选地包含可视化

**低自由度**(特定脚本,很少或没有参数):当操作脆弱、一致性重要或必须遵循特定顺序时使用。

```markdown
## 数据库迁移

严格运行此脚本:

```bash
python scripts/migrate.py --verify --backup

不要修改命令或添加额外参数。


**类比**:把 Agent 想象成探索路径的机器人:

- 高自由度:给它一个目的地,让它自己找路
- 中等自由度:给出路线建议,但允许根据路况调整
- 低自由度:给出详细地图和必须遵循的具体路线

## 设计原则

### 单一职责原则

每个 Skill 应该专注于一个明确的任务。不要试图创建"全能型" Skill。

❌ 违反单一职责 name: "code-helper" description: "帮助编写、审查、测试和优化代码"

✅ 遵循单一职责 name: "code-reviewer" description: "审查代码质量,发现潜在问题"

name: "test-generator" description: "为代码生成单元测试"

name: "code-formatter" description: "按照规范格式化代码"


单一职责的好处:
- 更容易触发:description 更精准
- 更易维护:修改不会影响其他功能
- 更易复用:可以灵活组合多个 Skills

### 明确边界原则

Skill 应该明确说明它的适用范围和边界。

```markdown
## 适用范围
- Python 3.8+ 代码
- 单文件或代码片段
- 项目代码(非库代码)

## 不适用场景
- 其他编程语言
- 整个项目审查
- 库 API 设计审查

## 边界情况处理
- 空文件:提示用户
- 超大文件(>500 行):建议分批审查
- 非代码文件:跳过并提示

渐进式信息原则

指令应该从简单到复杂,从概览到细节。

## 审查流程

### 第一阶段:快速扫描(30 秒)
快速识别明显问题:
- 语法错误
- 导入问题
- 命名规范

### 第二阶段:详细审查(5 分钟)
逐项检查:
- 类型注解
- 文档字符串
- 错误处理

### 第三阶段:深度分析(可选)
针对关键代码:
- 性能分析
- 安全审计
- 可维护性评估

Description 编写技巧

功能 + 触发条件公式

description 应该遵循"功能描述 + 触发条件"的格式:

[功能描述]。当用户 [触发条件] 时触发。

示例:

description: "审查 Python 代码质量,检查 PEP 8 规范和潜在问题。当用户请求代码审查、代码检查、code review 或提交 Python 代码时触发。"

关键词覆盖

列出用户可能使用的各种说法:

description: "为代码生成单元测试。当用户请求生成测试、写测试、添加单元测试、创建测试用例或 test coverage 时触发。"

排除条件

如果需要避免误触发,可以添加排除条件:

description: "审查 Python 代码质量。当用户请求代码审查时触发。注意:不适用于代码编写、代码调试或代码解释场景。"

指令编写技巧

使用检查清单

检查清单让 AI 系统地执行任务:

## 检查清单

在审查代码时,请逐项检查以下内容:

### 命名规范
- [ ] 变量名使用 snake_case
- [ ] 类名使用 PascalCase
- [ ] 常量使用全大写 SNAKE_CASE
- [ ] 私有属性以单下划线开头
- [ ] 名称具有描述性,避免单字母(循环变量除外)

### 类型注解
- [ ] 函数参数有类型注解
- [ ] 返回值有类型注解
- [ ] 复杂类型使用 typing 模块
- [ ] Optional 类型正确使用

### 文档
- [ ] 模块有 docstring
- [ ] 公共函数有 docstring
- [ ] docstring 格式一致

提供示例

示例比抽象描述更有效:

## 输出示例

### 📊 审查摘要
- 文件:user_service.py
- 问题总数:5

### 🔴 严重问题
| 行号 | 问题描述 | 修改建议 |
|------|----------|----------|
| 15 | 未处理可能的 None 值 | 添加 None 检查 |
| 42 | 资源未关闭 | 使用 with 语句 |

### 🟡 警告
| 行号 | 问题描述 | 修改建议 |
|------|----------|----------|
| 8 | 缺少类型注解 | 添加参数和返回值类型 |
| 23 | 行长度超过 88 字符 | 拆分长行 |

### 📝 总体评价
代码整体结构清晰,但存在一些需要改进的地方。建议优先修复严重问题。(评分:7/10)

定义优先级

明确问题的优先级,帮助用户聚焦:

## 问题优先级

### 🔴 严重(必须修复)
- 可能导致运行时错误
- 安全漏洞
- 数据丢失风险

### 🟡 警告(建议修复)
- 代码风格问题
- 性能问题
- 可维护性问题

### 🔵 建议(可选优化)
- 代码简化建议
- 文档改进建议
- 测试覆盖建议

组织多个 Skills

技能组合

多个 Skills 可以组合成工作流:

项目开发工作流:
1. code-formatter → 格式化代码
2. code-reviewer → 审查代码质量
3. test-generator → 生成测试
4. doc-generator → 生成文档

避免功能重叠

确保不同 Skills 之间没有功能重叠:

❌ 功能重叠
skill-a: "审查 Python 代码风格"
skill-b: "检查 Python 代码规范"

✅ 功能互补
skill-a: "审查 Python 代码风格(PEP 8)"
skill-b: "检查 Python 类型注解正确性"

建立技能库

为团队建立统一的技能库:

team-skills/
├── python/
│ ├── code-reviewer/
│ ├── test-generator/
│ └── doc-generator/
├── frontend/
│ ├── react-reviewer/
│ └── css-linter/
└── devops/
├── docker-reviewer/
└── ci-cd-generator/

版本管理

版本号规范

使用语义化版本号:

---
name: "code-reviewer"
version: "1.2.0"
---

版本号格式:主版本号.次版本号.修订号

  • 主版本号:不兼容的重大变更
  • 次版本号:向后兼容的功能新增
  • 修订号:向后兼容的问题修复

变更日志

在 Skill 文件中记录变更:

## 变更日志

### v1.2.0 (2026-01-15)
- 新增:支持异步代码审查
- 改进:优化输出格式

### v1.1.0 (2026-01-01)
- 新增:支持类型注解检查
- 修复:空文件处理问题

### v1.0.0 (2025-12-20)
- 初始版本

性能优化

控制指令长度

过长的指令会增加 Token 消耗和响应时间:

❌ 过长的指令(5000+ 字符)
包含大量重复内容、冗长解释

✅ 适中的指令(1000-3000 字符)
精炼、结构化、无冗余

按需加载

利用 description 实现按需加载:

description: "审查 Python 代码。仅在用户明确请求代码审查时触发。"

分层指令

对于复杂任务,可以使用分层指令:

## 基础审查(默认执行)
- 语法检查
- 风格检查

## 深度审查(用户请求时执行)
- 性能分析
- 安全审计

测试与验证

测试用例

为 Skill 准备测试用例:

## 测试用例

### 用例 1:正常代码
输入:符合规范的 Python 代码
预期:通过审查,无严重问题

### 用例 2:问题代码
输入:包含明显问题的代码
预期:正确识别并报告问题

### 用例 3:边界情况
输入:空文件
预期:友好提示,不报错

### 用例 4:误触发测试
输入:"帮我写一个 Python 函数"
预期:不触发此 Skill

持续改进

根据使用反馈持续改进:

  1. 收集用户反馈
  2. 分析触发准确性
  3. 优化输出质量
  4. 更新文档和示例

常见陷阱

陷阱一:过度抽象

❌ 过度抽象
description: "处理文本"

✅ 具体明确
description: "审查 Python 代码质量,检查 PEP 8 规范"

陷阱二:指令冲突

❌ 指令冲突
"检查所有代码风格问题,但忽略命名规范"

✅ 指令一致
"检查所有代码风格问题,包括命名规范"

陷阱三:忽略边界情况

❌ 忽略边界
(没有处理空输入、超大输入等情况)

✅ 处理边界
"对于空文件,提示用户提供代码"
"对于超大文件,建议分批审查"

用真实执行来优化

Skill 的初稿通常需要优化。针对真实任务运行 Skill,然后将结果——所有的结果,不仅仅是失败的——反馈到创建过程中。问:什么触发了误报?什么被遗漏了?什么可以删减?即使只有一次执行-然后-修订的流程也能显著提高质量,复杂领域通常需要几次。

执行跟踪分析

在迭代 Skill 时,比较 Agent 在各测试用例上的执行跟踪。如果你注意到 Agent 每次运行都独立重新发明相同的逻辑——构建图表、解析特定格式、验证输出——那就是写一个经过测试的脚本并捆绑到 scripts/ 的信号。

上下文消耗策略

一旦 Skill 激活,其完整的 SKILL.md 正文就会加载到 Agent 的上下文窗口中,与对话历史、系统上下文和其他活跃 Skills 并存。Skill 中的每个 token 都与窗口中的其他所有内容竞争 Agent 的注意力。

渐进式披露:三层加载

Skills 采用三层加载机制高效管理上下文:

层级内容类型加载时机Token 预算
1. 元数据frontmatter (name + description)会话启动时,加载所有 Skills~100 tokens
2. 指令SKILL.md 正文Skill 被激活时< 5000 tokens(建议)
3. 资源scripts、references、assets指令明确引用时按需加载

添加 Agent 缺乏的,省略它已知道的

专注于 Agent 在没有你的 Skill 情况下不会知道的内容:项目特定约定、领域特定流程、非显而易见的边界情况,以及要使用的特定工具或 API。你不需要解释什么是 PDF、HTTP 如何工作或数据库迁移做什么。

设计一致的单元

决定 Skill 应该覆盖什么就像决定函数应该做什么:你希望它封装一个一致的工作单元,并能与其他 Skills 很好地组合。

  • 范围太窄的 Skill 会强制为单个任务加载多个 Skill,有开销和指令冲突的风险
  • 范围太广的 Skill 变得难以精确激活

查询数据库并格式化结果的 Skill 可能是一个一致的单元,而也覆盖数据库管理的 Skill 可能试图做太多事情。

追求适度细节

过于全面的 Skill 可能弊大于利——Agent 难以提取相关内容,可能追求由不适用的指令触发的非生产性路径。简洁、逐步的指导和有效的示例通常优于详尽的文档。

当你发现自己覆盖每个边界情况时,考虑大多数是否最好由 Agent 自己的判断来处理。

用渐进式披露构建大型 Skills

规范建议保持 SKILL.md 在 500 行和 5000 tokens 以下——只包含 Agent 每次运行需要的核心指令。当 Skill 合法地需要更多内容时,将详细参考材料移到 references/ 或类似目录中的单独文件。

关键是告诉 Agent 何时 加载每个文件。"如果 API 返回非 200 状态码,读取 references/api-errors.md"比通用的"详见 references/ 更有用。"这让 Agent 按需加载上下文而不是预先加载,这正是渐进式披露的设计工作方式。

偏好流程而非声明

Skill 应该教 Agent 如何处理 一类问题,而不是 为特定实例生成什么。比较:

# 声明式(特定实例)

生成包含以下部分的用户报告:
- 用户名
- 注册日期
- 最后登录
- 总订单数

# 流程式(通用方法)

分析用户数据并生成报告:
1. 确定数据源中的可用字段
2. 选择与报告目的相关的字段
3. 格式化为清晰、可读的结构
4. 添加总结或关键洞察(如适用)

即使个别细节是特定的,流程式方法也应该泛化。

小结

遵循这些最佳实践,可以创建高质量的 Skills:

  1. 简洁是关键:上下文窗口是公共资源,添加 Agent 缺乏的,省略它已知道的
  2. 单一职责:每个 Skill 只做一件事,封装一致的工作单元
  3. 明确边界:定义适用范围和边界情况
  4. 精准触发:description 包含功能和触发条件,使用祈使语气编写
  5. 结构化指令:使用检查清单和示例
  6. 适当自由度:根据任务脆弱性调整指令具体程度
  7. 渐进式披露:大型 Skills 使用分层结构,SKILL.md < 500 行
  8. 偏好流程:教 Agent 如何处理问题,而不是为特定实例生成什么
  9. 易错点清单:列出环境特定的陷阱
  10. 持续优化:根据真实执行反馈改进
  11. 多模型测试:在所有计划使用的模型上测试 Skill

下一章我们将通过 实战案例 加深理解。