close

Volume 2 · Chapter 23

技能与命令:把知识变成工具、把动作变成命令

技能(skill)是「给模型的即用知识包」,命令(command)是「无需模型轮次的直接动作」。两者都是模型能力的补充面:skill 通过注入进入上下文,command 通过 ctx.commands 免轮次分派。

(卷一连接点) 08 页 inject(不唤醒)· 12 页 prompt 片段 本域:skill / skill-filesystem / tool-skill / commands / agent-instructions / command-feedback (回心脏) 技能内容经 inject 进 inbox → preStep 进模型上下文

示例本次示例:模型加载一个技能

示例轨迹 23-1 · 拉取式:模型主动调 skill 工具
# 技能发现:skill-filesystem 扫描 ~/.dsh/skills/ 与工作区的 SKILL.md
#   → 注册进 SkillRegistry(skill/src/index.ts:357)
# 模型不知道某技能的细节 → 调用 skill 工具(tool-skill 注册,161 行):
#   ① 列出技能 → "你有哪些技能" → [ {name:'pdf-to-text', description:'...'} ]
#   ② 读取技能 → 返回 SKILL.md 正文(作为 tool/result 进入 13/14 页流水线)
# 模型现在按技能指引行动——全程模型主动、时机确定
来源:23 页 §3 拉取式 + tool-skill/src/index.ts:25,161
示例轨迹 23-2 · 推送式:AGENTS.md 的注入
# agent-instructions 扫描工作区 → 发现子目录的 AGENTS.md
# → agent.inject(AGENTS.md 内容)(08 页 inject:next-step,不唤醒)
# → 下个 step 边界 preStep claim 到它(08 页 229 行)
# → 以 user/message 进入模型上下文(08 页示例轨迹 08-1 的改写场景)
# 与 23-1 的差异:inject 可能错过当前请求(preStep 已 claim 之后到达)
来源:23 页 §3 + 08 页 inject 语义

§1挂载条目

  • agent-instructions → @deepseek-ai/dsh-agent-instructions(1863 行)——AGENTS.md/CLAUDE.md 指令文件(08 页「subdir AGENTS.md」inject 的来源)
  • skill → @deepseek-ai/dsh-skill——技能注册表
  • skill-filesystem → dsh-skill-filesystem(1071 行)——从磁盘发现 SKILL.md
  • skill-badge(disabled)——badge 展示
  • tool-skill → dsh-tool-skill(461 行)——模型查询/加载技能的工具
  • commands → @deepseek-ai/dsh-commands——免轮次命令分派
  • command-feedback → dsh-command-feedback——/feedback 命令

§2包文件地图

规模角色
packages/skill/skill/2 文件 / 898 行Service DefinitionSkillRegistry extends Service(src/index.ts:357)——技能注册/发现/读取
packages/skill/skill-filesystem/2 文件 / 1071 行Providerinject = ['skills'](src/index.ts:46)——从目录树发现 SKILL.md
packages/skill/tool-skill/2 文件 / 461 行Consumerinject = ['agents', 'tools', 'skills'](src/index.ts:25),ctx.tools.register(skillTool)(161 行)
packages/context/agent-instructions/7 文件 / 1863 行AGENTS.md 扫描与注入——inject 的实际执行者

§3机制:注册 → 注入 → 消费

  1. 发现:skill-filesystem 扫描目录树里的 SKILL.md,注册进 SkillRegistry(名字、描述、正文)。
  2. 工具暴露:tool-skill 把「查技能列表、读技能正文」做成模型工具——模型需要某项技能时主动调它(拉取式)。
  3. 指令注入:agent-instructions 扫描工作区/子目录的 AGENTS.md(含父目录向上查找),把内容经 agent.inject() 放进 inbox——不唤醒(08 页 inject 语义),等下一次 step 边界被 claim 进上下文(拉取式之外还有推送式)。
  4. 命令分派ctx.commands 上的命令由 UI 直接触发,无需模型轮次——它是「旁路」(如 /compact 直接调压缩引擎,21 页)。

§4关键代码

packages/skill/skill/src/index.ts技能注册表357
357export class SkillRegistry extends Service {
packages/skill/tool-skill/src/index.ts技能工具的三依赖面25, 161
25export const inject = ['agents', 'tools', 'skills']
161  ctx.tools.register(skillTool)   // 拉取式的入口
357

技能域的 Definition。注意它是「注册表」而非「执行器」——技能本身没有运行时,正文就是它的全部。

25

tool-skill 的 inject 里有 agents——因为它需要 agent.inject() 把技能正文注入当前会话(与 agent-instructions 同一通道)。

161

「技能如何变成模型能力」的答案:注册进 tools(14 页 registry),schema 进提示词(12 页),模型调用它读取技能。

§5易错点

技能注入走 inbox 不唤醒(08 页 inject 语义)——一条技能注入若在 preStep 已 claim 之后到达,会错过当前请求,落到下一步。这是「拉取式(工具)优于推送式(注入)」的原因之一:模型主动调 skill 工具的时机是确定的。

命令是旁路不是轮次:commands 不需要模型参与——这就是为什么 command-compact(21 页)能直接调压缩引擎。它和「工具」的区别:工具需要模型决策后调用,命令由用户/UI 直接触发。