1. OpenClaw 技能开发到底在做什么,为什么值得从零搭一个
OpenClaw 技能开发,说白了就是给一个已经能对话的 AI 装上「专业手脚」:它本来只会聊天,你给它一个 SKILL.md,它就知道遇到「查天气」「生成日报」「同步表格」这类请求时该调用什么命令、走什么接口、按什么格式返回。技能(Skill)是 OpenClaw 的核心扩展机制,一个技能就是一个能力模块,本质是一份带 YAML 头的 Markdown 指令文件,复杂一点再配 scripts/ 脚本和 references/ 文档。它适合谁?适合想把自己的重复劳动打包成可复用能力的人,也适合想做一个能跑起来、能交付、甚至能上架 ClawHub 的 AI 产品的人。
我先把整条路径摊开:本地建目录 → 写 SKILL.md → 配好模型调用通道 → 本地调试 → 打包发布到 ClawHub。这里面最容易被忽略、也最容易卡住的一步,是模型调用通道的配置。技能写得再好,如果 AI 侧根本调不通模型,你的技能就是一份没人执行的说明书。所以这篇会把 TaoToken 统一 Key 接入作为前置环节讲清楚,再回到技能本身,最后用一次端到端调用验证它真的能用。
先明确几个概念,避免后面混淆。技能不等于插件,插件是扩展功能的代码模块,技能是给 AI 的「能力包」,包含指令和资源;技能也不等于工具,工具是具体的可执行程序,比如 curl、ffmpeg,而技能是告诉 AI 什么时候、怎么去用这些工具。技能的核心优势是:不需要写代码就能让 AI 具备新能力,当然复杂技能可以包含脚本。它能做的事覆盖 API 调用、文件处理、自动化任务、数据处理、企业系统集成。对个人开发者来说,门槛低、可复制、能持续迭代,这三点决定了它是一个值得投入的方向。
2. TaoToken 统一 Key 前置准备:把模型调用通道先打通
在写技能之前,先把模型调用这条链路打通,否则你调试技能时会分不清是 SKILL.md 写错了,还是模型根本没连上。TaoToken 在这里扮演的是统一 Key / API 通道的角色:你拿到一个 Key,配好 Base URL,就能在 OpenClaw 里完成模型调用配置,不用为每个模型单独折腾一套凭证。官网入口是 https://taotoken.net/?utm_source=taotoken_aicg_blog_end&utm_medium=csdn&utm_campaign=rewrite&utm_content= ,API 地址是 https://taotoken.net/api 。
你需要准备三样东西,我把它叫「三件套」:Base URL、API Key、Model ID。这三件套在后面的配置文件里会反复出现,缺一个都跑不起来。Base URL 填 https://taotoken.net/api ,API Key 在控制台的 API Keys 页面创建,Model ID 按你实际要用的模型填。创建 Key 的入口在 https://taotoken.net/console/api-keys?utm_source=taotoken_aicg_blog_end&utm_medium=csdn&utm_campaign=rewrite&utm_content= ,接入文档在 https://taotoken.net/doc?utm_source=taotoken_aicg_blog_end&utm_medium=csdn&utm_campaign=rewrite&utm_content= 。
这里有个我踩过的坑:很多人把 Key 直接写进 SKILL.md 里,这是错的。SKILL.md 是会被分享、会被发布到 ClawHub 的文件,Key 写进去等于公开泄露。正确做法是把 Key 放在 OpenClaw 的全局配置或环境变量里,SKILL.md 只负责描述「怎么用能力」,不负责「拿什么凭证」。下面给出一个可复制的配置片段,路径按 OpenClaw 的配置约定来,你按自己实际安装位置调整。
{ "models": { "provider": "taotoken", "baseUrl": "https://taotoken.net/api", "apiKey": "sk-你的TaoToken密钥", "model": "你的ModelID" } }如果你用的是 TOML 风格的配置,等价写法如下:
[models] provider = "taotoken" base_url = "https://taotoken.net/api" api_key = "sk-你的TaoToken密钥" model = "你的ModelID"配好之后先别急着写技能,用一条最小请求验证通道是否通。你可以直接在模型对话页面发一条测试消息,入口在 https://taotoken.net/models?utm_source=taotoken_aicg_blog_end&utm_medium=csdn&utm_campaign=rewrite&utm_content= ,能正常返回就说明三件套没问题。这一步花两分钟,能帮你省掉后面半小时的排查。
3. 可复制配置:SKILL.md 模板、目录结构与 ClawHub 上传命令
现在进入技能本体。先建目录,一个完整的技能目录结构长这样:
mkdir -p ~/.openclaw/workspace/skills/weather-skill cd ~/.openclaw/workspace/skills/weather-skill mkdir -p scripts references assets目录说明:SKILL.md 是必需文件,scripts/ 放可执行脚本,references/ 放参考文档,assets/ 放模板和静态资源。新手先只写 SKILL.md 就能跑,后面按需加目录。
SKILL.md 分两部分。第一部分是 YAML Frontmatter,也就是触发条件,AI 靠 description 判断什么时候用这个技能,所以 description 要写清楚「做什么、什么时候触发、典型问题」。第二部分是 Markdown Body,写具体指令、命令示例、注意事项。下面是一份可直接复制的模板:
--- name: weather-skill description: "查询天气和天气预报。当用户问天气、温度、预报、下雨、气温时使用。支持全球城市查询。" --- # 天气查询技能 通过 wttr.in 服务查询天气,无需额外 API Key。 ## 使用场景 - "今天天气怎么样?" - "北京明天会下雨吗?" - "上海这周的天气预报" ## 基本命令 ### 当前天气(简洁版) ```bash curl "wttr.in/北京?format=3"3 天天气预报
curl "wttr.in/北京"JSON 格式(适合程序处理)
curl "wttr.in/北京?format=j1"常用格式参数
| 参数 | 说明 | 示例 |
|---|---|---|
| ?format=3 | 简洁一行 | 北京: +12°C |
| ?format=j1 | JSON 格式 | {"current_condition": ...} |
| ?0 | 仅当前天气详细 | 当前天气详情 |
| ?1 | 明天预报 | 明天的天气预报 |
| ?2 | 后天预报 | 后天的天气预报 |
注意事项
- 无需 API Key,直接使用
- 有请求频率限制,不要频繁调用
- 中文城市名需要 URL 编码或使用拼音
注意上面模板里嵌套了代码块,实际写入文件时按 Markdown 规范处理即可。写完保存,重启 OpenClaw 让技能生效: ```bash openclaw gateway restart然后在聊天里测试「北京今天天气怎么样」,AI 应该会调用 wttr.in 并返回结果。测试通过后打包发布到 ClawHub:
npm i -g clawhub clawhub login clawhub publish ./weather-skill \ --slug weather-skill \ --name "天气查询" \ --version 1.0.0 \ --changelog "首个版本发布"参数说明:--slug 是唯一标识,用英文;--name 是显示名称,可以中文;--version 遵循语义化版本;--changelog 写更新日志。发布前确认 SKILL.md 里没有硬编码任何 Key,这是底线。
4. 验证请求与成功结果:一次端到端调用确认技能可用
配置和技能都就位后,做一次端到端验证。验证的目标不是「AI 回了一句话」,而是「AI 确实按 SKILL.md 的指令调用了命令并返回了结构化结果」。我建议分三步走。
第一步,验证模型通道。在模型对话页面发一条普通消息,确认能返回。如果这一步就失败,先回到第 2 节检查三件套,别往下走。
第二步,验证技能被触发。在 OpenClaw 聊天里输入「北京今天天气怎么样」,观察日志里是否出现技能名 weather-skill 的加载记录。如果 AI 直接凭记忆瞎答而没有调用命令,说明 description 写得不够明确,回去把触发词补全。
第三步,验证命令输出。手动执行一次技能里的命令,确认返回格式和 SKILL.md 描述一致:
curl "wttr.in/北京?format=3"预期输出类似北京: +12°C。如果命令本身返回异常,那是外部服务的问题,不是技能的问题,换一个城市或稍后重试即可。
三步都通过,说明你的技能从「模型调用」到「指令执行」整条链路是通的。这时候你可以把技能打包成 .skill 文件分享给别人,也可以继续迭代。对于需要长期跑编码类、Agent 类任务的场景,可以考虑用 Coding Plan 来承载更稳定的调用额度,入口在 https://taotoken.net/coding-plan?utm_source=taotoken_aicg_blog_end&utm_medium=csdn&utm_campaign=rewrite&utm_content= 。
5. 本篇常见错排查:401、local proxy failed、reading choices、OAuth
技能开发过程中,报错基本集中在模型调用这一层,而不是 SKILL.md 本身。下面按真实报错逐个对照。
401 未授权。最常见的原因是 Key 填错、Key 过期,或者 Base URL 写成了带路径的地址。检查三件套:Base URL 必须是 https://taotoken.net/api ,Key 从控制台重新复制一次,注意前后不要有空格。如果 Key 是刚创建的,确认没有复制到多余字符。
local proxy failed。这个报错通常出现在本地网络环境或代理配置异常时。先确认你的配置里没有多余的代理设置,再确认 Base URL 可达。可以在终端直接请求一次接口地址,看是否能建立连接。如果本地环境有额外的网络层,先把它排除掉再测。
reading choices 相关报错。这类报错一般出现在响应解析阶段,说明请求发出去了但返回结构不符合预期。常见原因是 Model ID 填错,或者请求体格式和接口不匹配。回到配置里核对 Model ID,确保它和你在控制台看到的一致。如果用的是自定义请求体,确认字段名没有拼错。
OAuth 相关报错。如果你在配置里混用了 OAuth 流程和 API Key 流程,会出现凭证冲突。TaoToken 的接入用 API Key 即可,不需要额外走 OAuth。把配置里多余的 OAuth 字段删掉,只保留 Base URL、API Key、Model ID 三件套。
还有一个高频问题:技能不触发。这不是报错,但比报错更让人困惑。原因几乎总是 description 写得太泛,比如只写「查询天气」,AI 无法判断何时该用。解决办法是把典型用户问题写进 description,像模板里那样列出「天气、温度、预报、下雨、气温」这些触发词。
排查顺序建议固定下来:先看模型通道是否通,再看技能是否被加载,最后看命令是否执行成功。这个顺序能帮你快速定位问题在哪一层,而不是在三个层面之间来回猜。
6. 从技能到 AI 产品:把统一 Key 接入变成你的交付底座
把技能做出来只是第一步,让它变成一个能交付、能复用、能持续迭代的 AI 产品,才是这条路径的价值所在。而支撑这一切的底座,是稳定的模型调用通道。你不可能每做一个技能就换一套凭证体系,统一 Key 接入的意义就在这里:一次配好,所有技能共用。
回到 OpenClaw 技能开发本身,它的产品化路径其实很清晰。第一阶段,写免费技能练手,把 SKILL.md 的触发逻辑、命令组织、错误处理摸熟。第二阶段,把有实用价值的技能发布到 ClawHub,设置合理价格,积累评价。第三阶段,接定制需求,把技能开发和部署打包成服务。第四阶段,把常用技能组合成套餐,提高客单价。每一步都建立在「技能真的能跑通」这个前提上,而跑通的前提是模型调用通道稳定。
如果你要长期做编码类或 Agent 类技能,建议把 Coding Plan 作为主力通道,入口在 https://taotoken.net/coding-plan?utm_source=taotoken_aicg_blog_end&utm_medium=csdn&utm_campaign=rewrite&utm_content= 。日常调试和验证模型是否正常,用模型对话页面就够,入口在 https://taotoken.net/models?utm_source=taotoken_aicg_blog_end&utm_medium=csdn&utm_campaign=rewrite&utm_content= 。Key 的管理统一在控制台,入口在 https://taotoken.net/console/api-keys?utm_source=taotoken_aicg_blog_end&utm_medium=csdn&utm_campaign=rewrite&utm_content= 。接入细节以文档为准,入口在 https://taotoken.net/doc?utm_source=taotoken_aicg_blog_end&utm_medium=csdn&utm_campaign=rewrite&utm_content= 。
最后给你一个实操建议:每开发一个新技能,先复制一份能跑通的最小 SKILL.md,改 name 和 description,跑通端到端调用,再往里加命令和脚本。不要一上来就写复杂技能,那样一旦不触发,你很难判断是 description 的问题还是命令的问题。先用最小可用版本验证链路,再逐步加能力,这是最省时间的做法。