第 20 章

高级 Skills 技巧:OS 过滤、依赖门控、command-dispatch 与 Token 控制

第20章:高级 Skills 技巧——OS 过滤、依赖门控、command-dispatch 与 Token 控制

本章概览

本章是《OpenClaw 完全指南》Skills 部分的最终章。前几章建立了 Skills 的基础知识框架,本章深入那些让 Skills 真正专业化的高级特性:精准的 OS 过滤、多维度的依赖门控、command-dispatch 的内部机制、隐藏 Skill 的适用场景,以及如何将多项技术组合使用,在保持功能完整的同时将 Token 成本压到最低。


20.1 OS 过滤:让 Skill 只在正确的平台出现

问题背景

许多 Skill 依赖平台特定的工具或行为:

如果一个依赖 brew 的 Skill 在 Linux 上显示为"可用",用户触发后会立即报错,体验极差。OS 过滤解决了这个问题。

配置方式

metadata:
  openclaw:
    os: darwin    # 仅 macOS
metadata:
  openclaw:
    os: linux     # 仅 Linux(含 WSL)
metadata:
  openclaw:
    os: win32     # 仅 Windows(含 Windows 11)

不设置 os 字段 = 全平台可用

OS 过滤的内部机制

OpenClaw 在启动时检测当前运行平台(通过 process.platform),并在加载 Skill 时:

加载 Skill 元数据 → 读取 os 字段
  ├─ os 字段不存在 → 加载(全平台)
  ├─ os 与当前平台匹配 → 加载
  └─ os 与当前平台不匹配 → 跳过(不注入任何内容)

关键点: 不匹配的 Skill 完全不出现在模型 context 中,节省 token 的同时也避免了误触发。

实战示例:macOS 剪贴板 Skill

---
name: clipboard-mac
description: |
  在 macOS 上管理剪贴板内容:复制文本到剪贴板、
  从剪贴板读取内容、追加内容到剪贴板。
metadata:
  openclaw:
    emoji: "📋"
    os: darwin
    requires:
      bins:
        - pbcopy
        - pbpaste
---

# macOS 剪贴板操作

## 写入剪贴板

```bash
# 将文本复制到剪贴板
echo "Hello, World" | pbcopy

# 将文件内容复制到剪贴板
cat file.txt | pbcopy

# 将命令输出复制到剪贴板
ls -la | pbcopy

读取剪贴板

# 查看剪贴板内容
pbpaste

# 将剪贴板内容写入文件
pbpaste > output.txt

---

## 20.2 requires 四维度的差异与选择

### 维度一:requires.bins(硬性二进制依赖)

**语义:** PATH 中必须**全部**存在这些可执行文件。

```yaml
requires:
  bins:
    - git
    - gh
    - jq

使用场景: Skill 的功能无法降级,没有替代方案。

实际检测:

OpenClaw 执行等价于 `which git && which gh && which jq`
如果任何一个失败 → Skill 不加载

维度二:requires.anyBins(软性多选一依赖)

语义: 至少有一个存在即可。

requires:
  anyBins:
    - yarn
    - npm
    - pnpm
    - bun

使用场景: 多种工具都能完成任务,Skill 内部会检测用哪个。

Skill 内部的工具检测模式:

## 确定包管理器

按优先级检测:
1. `which bun` → 使用 bun
2. `which yarn` → 使用 yarn  
3. `which pnpm` → 使用 pnpm
4. `which npm` → 使用 npm(总是存在于 Node.js 环境)

找到第一个可用的即停止检测。

维度三:requires.env(环境变量门控)

语义: 所有列出的环境变量必须存在且非空

requires:
  env:
    - GITHUB_TOKEN
    - SLACK_WEBHOOK_URL

典型配置场景:

环境变量 用途
GITHUB_TOKEN GitHub API 访问
OPENAI_API_KEY OpenAI API 访问
ANTHROPIC_API_KEY Anthropic API 访问
SLACK_WEBHOOK_URL Slack 消息推送
DATABASE_URL 数据库连接

注意: requires.env 只检查变量是否存在,不验证值是否有效(错误的 API Key 要到调用时才暴露)。

维度四:requires.config(功能开关门控)

语义: openclaw.json 中的指定路径必须存在且为真值

requires:
  config:
    - features.experimental.acp
    - tools.browser.enabled

openclaw.json 对应配置:

{
  "features": {
    "experimental": {
      "acp": true
    }
  },
  "tools": {
    "browser": {
      "enabled": true
    }
  }
}

适用场景: 实验性功能开关、企业版特性、用户选择加入(opt-in)的高风险功能。

四维度组合使用

requires:
  bins:
    - docker
    - kubectl
  anyBins:
    - helm
    - kustomize
  env:
    - KUBECONFIG
    - DOCKER_REGISTRY_TOKEN
  config:
    - features.k8s.enabled

当所有条件同时满足时,Skill 才会加载。任何一个维度不满足,Skill 整体跳过。


20.3 install 自动安装脚本的四种类型

requires.bins 中的工具缺失时,OpenClaw 可以根据 install 配置尝试自动安装。

类型一:brew(macOS Homebrew)

install:
  - type: brew
    pkg: ffmpeg
  - type: brew
    pkg: imagemagick
    tap: homebrew/cask    # 可选:指定 tap

适用: macOS 用户,需要 Homebrew 已安装。

执行等价命令:

brew install ffmpeg
brew install imagemagick

类型二:node(npm/npx 包)

install:
  - type: node
    pkg: "@anthropic-ai/claude-cli"
    global: true          # 安装为全局包
  - type: node
    pkg: "tsx"
    global: true

执行等价命令:

npm install -g @anthropic-ai/claude-cli
npm install -g tsx

类型三:go(Go 二进制工具)

install:
  - type: go
    pkg: github.com/cli/cli/v2@latest

执行等价命令:

go install github.com/cli/cli/v2@latest

前提: 需要 Go 已安装(不会自动安装 Go 本身)。

类型四:uv(Python 工具)

install:
  - type: uv
    pkg: ruff
  - type: uv
    pkg: mypy

执行等价命令:

uv tool install ruff
uv tool install mypy

注意: uv 是现代 Python 工具管理器,比 pip install 更快、更安全。

类型五:download(直接下载二进制)

install:
  - type: download
    url: https://releases.example.com/tool-v2.0-darwin-arm64.tar.gz
    dest: ~/.local/bin/
    extract: true          # 是否解压
    chmod: "0755"          # 设置执行权限
    binary: tool           # 解压后的二进制文件名

适用: 没有包管理器支持的闭源工具,或需要特定版本。

自动安装的完整流程

用户触发包含 requires.bins: [ffmpeg] 的 Skill
  ↓
OpenClaw 检测:which ffmpeg → 不存在
  ↓
读取 install 配置,找到 type: brew, pkg: ffmpeg
  ↓
提示用户:
  "ffmpeg 未安装。是否自动安装?(y/n)"
  ↓
用户确认 → 执行 brew install ffmpeg
  ↓
安装完成 → 继续加载并执行 Skill

20.4 command-dispatch 的内部机制

零推理调用路径

普通 Skill 调用流程:

用户输入 → [模型 token 消耗] → 模型决策 → 工具调用 → 结果

command-dispatch 调用流程:

用户输入 → OpenClaw 路由层 → 工具调用 → 结果
(完全绕过模型,0 token 消耗)

路由层的工作原理

当 OpenClaw 接收到 /browser https://example.com 时:

1. 解析斜杠命令名称:browser
2. 查找名为 browser 的 Skill
3. 检查 Skill 是否设置了 command-dispatch: tool
4. 是 → 读取 command-tool: "browser_action"
5. 读取 command-arg-mode: raw
6. 将 "https://example.com" 作为原始字符串传递给 browser_action 工具
7. 直接返回工具结果
(整个过程不调用语言模型)

command-dispatch 的实际 Token 节省

场景: 用户每天平均使用 /browser 命令 20 次

调用方式 每次 Token 消耗 每日 Token 消耗 月度成本估算
普通 Skill ~1,200 tokens 24,000 tokens ~$0.72
command-dispatch 0 tokens 0 tokens $0.00

以 GPT-4 级别 $0.03/1K tokens 计算

command-arg-mode 的两种模式

raw 模式:

用户输入:/search --limit 10 python async best practices
工具接收:python async best practices --limit 10
(参数原样传递,不做解析)

parsed 模式(默认):

用户输入:/search --limit 10 python async best practices
工具接收:{query: "python async best practices", limit: 10}
(参数被解析为结构化格式)

20.5 disable-model-invocation 的适用场景

什么时候该隐藏 Skill?

disable-model-invocation: true 将 Skill 完全从模型 context 中移除。以下场景适合使用:

场景一:内部工具,不应暴露给用户

---
name: internal-diagnostics
description: 内部诊断工具(不对外)
disable-model-invocation: true
user-invocable: true   # 只有特定用户知道命令名才能调用
---

场景二:减少 context 消耗的高频命令工具

---
name: clipboard
description: 剪贴板快速操作
disable-model-invocation: true
user-invocable: true
command-dispatch: tool
command-tool: "clipboard_action"
---

这个 Skill 永远不会被模型自动触发,也不占用 context,但用户可以通过 /clipboard 命令直接使用。

场景三:防止意外触发的高风险操作

---
name: production-deploy
description: 部署到生产环境(危险操作)
disable-model-invocation: true
user-invocable: true
---

只有用户显式输入 /production-deploy 才能触发,模型永远不会在对话中自动决定"该部署了"。

disable-model-invocation vs requires.config 的选择

需求 推荐方案
永久隐藏 Skill disable-model-invocation: true
条件性隐藏(可开关) requires.config: [feature.x.enabled]
仅对特定环境隐藏 os: darwin(OS 过滤)

20.6 always: true 的风险与适用场景

always: true 是一个特殊字段,设置后 Skill 会跳过所有 gate(包括 requires 检查),始终可用。

配置方式

---
name: core-guidelines
description: 核心行为准则,始终激活
metadata:
  openclaw:
    always: true
---

# 核心准则

每次对话都遵循以下原则:
- 回答前先确认理解用户意图
- 给出代码时同时提供测试方案
- 不确定时主动说明不确定

真正的适用场景(极少数)

always: true 的风险

风险 说明
始终消耗 context 即使当前任务与此 Skill 完全无关
无法被 requires 门控 即使依赖工具不存在也会加载
可能与其他 Skill 冲突 始终激活的指导可能与专业 Skill 的指导矛盾
难以调试 忘记有 always Skill 存在时,行为异常难以排查

建议: 绝大多数情况下不要使用 always: true。如果确实需要,控制 Skill 体积在 200 tokens 以内。


20.7 Token 成本控制:懒加载 + command-dispatch 组合策略

策略架构图

高频命令性操作
    ↓
command-dispatch + disable-model-invocation
    → 0 token 消耗

低频、需要推理的操作
    ↓
懒加载(仅注入元数据)
    → ~50 token 元数据,激活时才加载完整内容

深度参考资料
    ↓
references/ 目录 + {baseDir} 引用
    → 仅在明确需要时加载

实战:为一个团队工具包优化 Token 消耗

场景: 团队使用 15 个 Skills,每天对话 50 轮,每轮平均触发 2 个 Skills。

优化前(全量加载):

每轮对话:15 Skills × 1500 tokens = 22,500 tokens(Skills 部分)
每日:50 × 22,500 = 1,125,000 tokens
月度成本:~$33.75

优化后(懒加载 + command-dispatch):

每轮对话:
  - 元数据:15 × 50 tokens = 750 tokens
  - 激活的 Skills:2 × 1500 tokens = 3,000 tokens
  - command-dispatch Skills(5个):0 tokens
  总计:3,750 tokens(Skills 部分)

每日:50 × 3,750 = 187,500 tokens
月度成本:~$5.63

节省:83%

按操作类型分配技术

操作类型 推荐技术 Token 消耗
立即响应命令(< 0.5s) command-dispatch 0
模型需要判断的任务 懒加载 50(元数据)+ 按需
深度文档查阅 references/ 目录 仅按需
全局行为准则(谨慎) always: true 全量(每轮)

20.8 多 Skills 协作模式:skill-creator 元 Skill

元 Skill 的概念

元 Skill(meta-skill)是一种特殊的 Skill:它的目的是创建其他 Skills。这是 OpenClaw Skills 系统中最高级的使用模式。

完整 skill-creator SKILL.md 示例

---
name: skill-creator
description: |
  当用户想要创建新的 OpenClaw Skill、将重复性工作流打包为 Skill、
  或者询问如何编写 SKILL.md 时使用。
  引导用户通过问答过程生成完整的 Skill 文件。
user-invocable: true
metadata:
  openclaw:
    emoji: "🏗️"
    primaryEnv: shell
---

# Skill Creator — Skill 创作向导

## 第一步:收集信息

向用户提问以下问题(每次一个,等待回答):

1. **这个 Skill 要做什么?** (一句话描述核心功能)
2. **用户在什么情况下需要它?** (触发场景,用于 description)
3. **它依赖哪些外部工具?** (用于 requires.bins)
4. **它需要哪些环境变量?** (用于 requires.env)
5. **它应该在哪些操作系统上运行?** (darwin/linux/win32/全部)
6. **用户可以通过斜杠命令调用吗?** (user-invocable)
7. **有简单的命令行形式吗?** (是否需要 command-dispatch)

## 第二步:选择合适的模式

根据收集的信息,按以下逻辑选择模式:

有明确的单一工具调用? ├─ 是 → command-dispatch 型 └─ 否 → 有复杂工作流? ├─ 是 → 信息型或 TDD 专业型 └─ 否 → 依赖外部工具? ├─ 是 → 工具集成型 └─ 否 → 工具型(最简洁)


## 第三步:生成 SKILL.md

根据收集的信息,生成完整的 SKILL.md 文件。

**生成规则:**
- description 控制在 50-150 字符
- requires 只声明确认存在的依赖
- 正文按"操作步骤"组织,不要写成散文
- 如果正文超过 1000 tokens,将详细内容移到 references/

## 第四步:验证与安装

生成后,提供以下验证步骤:

```bash
# 1. 查看生成的文件
cat ~/.openclaw/skills/<skill-name>/SKILL.md

# 2. 验证 SKILL.md 格式
openclaw skill validate ~/.openclaw/skills/<skill-name>/

# 3. 测试触发
# 在新对话中输入 Skill 的触发场景,检查是否被正确激活

常见 Skill 模板

如需具体模板,参见:


---

## 20.9 高级组合案例:生产级 Skill 设计

### 案例:企业级 Kubernetes 部署 Skill

这个案例展示了如何将本章所有高级技术组合使用:

```yaml
---
name: k8s-deploy
description: |
  当团队需要将服务部署到 Kubernetes 集群时使用:
  创建/更新 Deployment、Service、ConfigMap,
  执行滚动更新,回滚失败部署,查看 Pod 状态和日志。
  仅适用于已配置 kubectl 访问权限的环境。
user-invocable: true
disable-model-invocation: false
metadata:
  openclaw:
    emoji: "☸️"
    os: linux
    requires:
      bins:
        - kubectl
        - helm
      anyBins:
        - kustomize
        - helmfile
      env:
        - KUBECONFIG
        - K8S_NAMESPACE
      config:
        - features.k8s.enabled
        - features.k8s.production_access
    primaryEnv: shell
    homepage: https://kubernetes.io/docs/
    install:
      - type: brew
        pkg: kubernetes-cli
      - type: go
        pkg: helm.sh/helm/v3@latest
---

# Kubernetes 部署 Skill

## 安全前提(每次操作前必读)

**生产环境操作三原则:**
1. 先在 staging 验证,再推到 production
2. 滚动更新,绝不直接 delete+recreate
3. 保留回滚点(--record 已废弃,改用 revision history)

## 部署新版本

```bash
# 更新镜像版本(推荐方式,保留历史)
kubectl set image deployment/<name> \
  <container>=<image>:<tag> \
  -n ${K8S_NAMESPACE}

# 查看滚动更新进度
kubectl rollout status deployment/<name> -n ${K8S_NAMESPACE}

查看状态

# 查看所有 Pod
kubectl get pods -n ${K8S_NAMESPACE} -o wide

# 查看特定 Pod 日志(最近 100 行)
kubectl logs <pod-name> -n ${K8S_NAMESPACE} --tail=100 -f

# 查看 Pod 事件(排查 CrashLoopBackOff)
kubectl describe pod <pod-name> -n ${K8S_NAMESPACE}

回滚

# 查看 Deployment 历史
kubectl rollout history deployment/<name> -n ${K8S_NAMESPACE}

# 回滚到上一版本
kubectl rollout undo deployment/<name> -n ${K8S_NAMESPACE}

# 回滚到指定版本
kubectl rollout undo deployment/<name> \
  --to-revision=3 \
  -n ${K8S_NAMESPACE}

Helm 部署

详细的 Helm values 配置说明见:{baseDir}/references/helm-values-guide.md Chart 模板最佳实践见:{baseDir}/references/helm-chart-patterns.md


**这个 Skill 使用了哪些高级技术:**
- ✅ `os: linux`:OS 过滤(K8s 通常在 Linux 环境)
- ✅ `requires.bins`:硬性依赖 kubectl + helm
- ✅ `requires.anyBins`:软性依赖 kustomize 或 helmfile
- ✅ `requires.env`:门控 KUBECONFIG(无此变量不应加载)
- ✅ `requires.config`:双重门控(features.k8s.enabled + production_access)
- ✅ `{baseDir}/references/`:深度文档懒加载
- ✅ `install`:提供自动安装路径

---

## 20.10 本章小结与最佳实践速查

### 技术选择快速决策表

| 需求 | 技术 | 字段 |
|------|------|------|
| 仅在 macOS 可用 | OS 过滤 | `os: darwin` |
| 需要全部工具存在 | 硬性依赖 | `requires.bins` |
| 需要任一工具存在 | 软性依赖 | `requires.anyBins` |
| 需要 API Key | 环境变量门控 | `requires.env` |
| 需要功能开关 | 配置门控 | `requires.config` |
| 命令直达工具 | 零推理调用 | `command-dispatch: tool` |
| 完全隐藏 Skill | 从模型隐藏 | `disable-model-invocation: true` |
| 全局始终激活(慎用)| 跳过所有门控 | `always: true` |
| 减少 context | 深度文档延迟加载 | `references/ + {baseDir}` |

### 高级 Skill 设计的核心原则

1. **精确门控胜过宽松允许**:`requires` 配置得越精确,Skill 越可靠
2. **command-dispatch 优先**:凡是可以确定行为的命令,都应该 command-dispatch
3. **references/ 是 context 的缓冲区**:详细内容永远放 references/,正文只留操作核心
4. **always: true 是核武器**:只在真正需要全局影响时使用
5. **OS 过滤保护用户体验**:平台特定工具必须配置 OS 过滤

**恭喜!** 你已经完成了《OpenClaw 完全指南》Skills 部分的全部学习。从第16章的 ACP 协议到第20章的高级技巧,你现在具备了设计和实现企业级 Skills 生态系统的完整知识体系。

下一部分将介绍 OpenClaw 的安全模型与部署策略——如何在团队和企业环境中安全地运行 OpenClaw。
本章评分
4.8  / 5  (10 评分)

💬 留言讨论