skill-creator
创建新技能、修改并改进现有技能,并衡量技能表现。当用户想从零创建技能、编辑/优化已有技能、运行评测(evals)测试技能、用方差分析做基准测试(benchmark)、或优化技能描述以提升触发准确率时使用。
التثبيت باستخدام Codex أو Claude انسخ هذا Prompt والصقه في Codex أو Claude أو مساعد آخر ليراجع صفحة Skill ويثبّتها لك.
القائمة
创建新技能、修改并改进现有技能,并衡量技能表现。当用户想从零创建技能、编辑/优化已有技能、运行评测(evals)测试技能、用方差分析做基准测试(benchmark)、或优化技能描述以提升触发准确率时使用。
التثبيت باستخدام Codex أو Claude انسخ هذا Prompt والصقه في Codex أو Claude أو مساعد آخر ليراجع صفحة Skill ويثبّتها لك.
استنادا إلى تصنيف SOC المهني
| name | skill-creator |
| description | 创建新技能、修改并改进现有技能,并衡量技能表现。当用户想从零创建技能、编辑/优化已有技能、运行评测(evals)测试技能、用方差分析做基准测试(benchmark)、或优化技能描述以提升触发准确率时使用。 |
用于创建新技能并进行迭代改进的技能。
从宏观上看,创建技能的流程大致如下:
eval-viewer/generate_review.py 把结果展示给用户,同时让用户查看定量指标使用本技能时,你的工作是判断用户处于上述流程的哪一步,然后介入并推动他们向下一阶段推进。例如用户说“我想做一个用于 X 的技能”,你可以帮助澄清需求、写初稿、写测试用例、确定评估方式、跑完全部测试提示词,并据此反复迭代。
反过来,如果用户已经有技能初稿,你可以直接进入“评测/迭代”环节。
当然你需要保持灵活:如果用户说“我不需要跑一堆评测,咱们先凭感觉一起改”,也可以按用户偏好走。
技能完成后(顺序也可灵活调整),你还可以运行“技能描述优化器”(我们有单独的脚本)来优化技能的触发效果。
可以吧?那就开始。
Skill Creator 可能会被“对编程术语熟悉程度差异很大”的人使用。现在有一种趋势:模型能力让很多非技术用户也开始打开终端、搜索“如何安装 npm”。当然,也有相当一部分用户是比较懂电脑/软件的。
因此请根据上下文线索调整你的表达方式。默认情况下,大致可参考:
如果你不确定用户是否理解某个术语,简要解释是可以的;也可以用一句短定义来澄清含义。
从理解用户意图开始。当前对话里可能已经包含用户想“固化为技能”的流程(例如用户说“把这个做成技能”)。如果是这种情况,先从对话历史里提取关键信息:用到哪些工具、步骤顺序、用户做过哪些纠正、观察到的输入/输出格式等。用户可能需要补齐缺口;在进入下一步前应先确认这些信息。
主动询问边界情况、输入/输出格式、示例文件、成功标准以及依赖项等。在这些关键点明确之前,不要急着写测试提示词。
检查可用的 MCP:如果对研究有帮助(查文档、找类似技能、查最佳实践),在有子代理的情况下尽量并行研究;否则就直接在当前对话内完成。准备好上下文,尽量减少用户负担。
基于用户访谈,补全以下部分:
skill-name/
├── SKILL.md (required)
│ ├── YAML frontmatter (name, description required)
│ └── Markdown instructions
└── Bundled Resources (optional)
├── scripts/ - Executable code for deterministic/repetitive tasks
├── references/ - Docs loaded into context as needed
└── assets/ - Files used in output (templates, icons, fonts)
技能采用三层加载机制:
上述字数/行数只是粗略指导,必要时可以更长。
关键模式:
领域组织(Domain organization):当一个技能支持多个领域/框架时,可按变体组织:
cloud-deploy/
├── SKILL.md (workflow + selection)
└── references/
├── aws.md
├── gcp.md
└── azure.md
Claude 只会读取相关的参考文件。
不言自明:技能不得包含恶意软件、漏洞利用代码或任何可能危害系统安全的内容。技能的内容不应在“其描述的意图”层面上让用户感到意外。不要配合创建误导性技能,或用于未授权访问、数据外传等恶意活动的技能。但像“扮演某个角色进行对话”的需求通常是可以的。
指令中优先使用祈使句(imperative form)。
定义输出格式可以这样写:
## Report structure
ALWAYS use this exact template:
# [Title]
## Executive summary
## Key findings
## Recommendations
示例模式:包含例子通常很有用,可以这样组织(如果例子里包含 “Input/Output” 可能需要稍作变化):
## Commit message format
**Example 1:**
Input: Added user authentication with JWT tokens
Output: feat(auth): implement JWT-based authentication
尽量用“解释为什么重要”的方式替代生硬的 MUST/强制口吻。运用“换位思考”,让技能更通用,而不是过度依赖某个特定例子。先写初稿,再用“新鲜视角”回看并改进。
写完技能初稿后,提出 2-3 个真实的测试提示词——要像真实用户会说的话。把它们展示给用户(不必逐字照抄):“我想试几条测试用例,你看是否合适?要不要再加一些?”然后执行这些测试。
把测试用例保存到 evals/evals.json。先不要写断言(assertions)——只写 prompts。下一步在运行进行时再起草断言。
{
"skill_name": "example-skill",
"evals": [
{
"id": 1,
"prompt": "User's task prompt",
"expected_output": "Description of expected result",
"files": []
}
]
}
完整 schema(包括稍后才会添加的 assertions 字段)见 references/schemas.md。
这一节是一段连续流程——不要中途停下来。不要使用 /skill-test 或任何其他测试类技能。
把结果放在 <skill-name>-workspace/(与技能目录同级)。在 workspace 中按迭代组织(iteration-1/、iteration-2/…),每个测试用例再单独建目录(eval-0/、eval-1/…)。不要一次性把所有目录都预创建——边跑边建即可。
对每个测试用例,在同一轮里启动两个子代理——一个“带技能”,一个“基线(不带)”。这一点很重要:不要先跑带技能的,再回头跑基线;要一次性全启动,让它们尽量在相近时间完成。
带技能(With-skill)运行:
Execute this task:
- Skill path: <path-to-skill>
- Task: <eval prompt>
- Input files: <eval files if any, or "none">
- Save outputs to: <workspace>/iteration-<N>/eval-<ID>/with_skill/outputs/
- Outputs to save: <what the user cares about — e.g., "the .docx file", "the final CSV">
基线(Baseline)运行(同样 prompt,但基线取决于场景):
without_skill/outputs/。cp -r <skill-path> <workspace>/skill-snapshot/),再让基线子代理指向该快照。输出保存到 old_skill/outputs/。为每个测试用例写一个 eval_metadata.json(暂时可以让 assertions 为空)。根据“它在测什么”给每个 eval 取一个描述性名称,而不是只叫 “eval-0”;目录名也用这个名称。如果本次迭代使用了新的或修改过的 eval prompts,就为每个新的 eval 目录创建这些文件——不要假设它们会从上一轮自动沿用。
{
"eval_id": 0,
"eval_name": "descriptive-name-here",
"prompt": "The user's task prompt",
"assertions": []
}
不要只是等运行结束——可以利用这段时间做更有价值的事:为每个测试用例起草定量断言,并向用户解释这些断言。如果 evals/evals.json 里已经有断言,就复查并说明它们在检查什么。
好的断言应当可客观验证,并且名称具有描述性——在 benchmark viewer 中一眼就能看出它在检查什么。对偏主观的技能(写作风格、设计质量)更适合定性评估,不要把需要人工判断的东西硬塞进断言里。
断言起草完成后,更新各个 eval_metadata.json 以及 evals/evals.json。同时向用户说明在 viewer 里会看到什么——包括定性输出与定量 benchmark。
每个子代理任务完成时,你会收到包含 total_tokens 和 duration_ms 的通知。立即把数据保存到运行目录下的 timing.json:
{
"total_tokens": 84852,
"duration_ms": 23332,
"total_duration_seconds": 23.3
}
这是捕获该数据的唯一机会——它只会出现在任务通知中,不会在别处持久化。建议按通知到达顺序逐条处理,不要想着最后再批量补。
当所有运行都完成后:
给每次运行打分:启动 grader 子代理(或直接在当前对话内评分),读取 agents/grader.md,对照输出评估每条断言。将结果保存到每个运行目录的 grading.json。grading.json 的 expectations 数组字段必须使用 text、passed、evidence(不要用 name/met/details 等其他变体)——viewer 依赖这些字段名。对可编程验证的断言,优先写脚本运行校验,而不是目测;脚本更快、更可靠,还能复用。
聚合为 benchmark:在 skill-creator 目录下运行聚合脚本:
python -m scripts.aggregate_benchmark <workspace>/iteration-N --skill-name <name>
这会生成 benchmark.json 和 benchmark.md,包含每种配置的 pass_rate、耗时与 tokens(均值 ± 标准差,以及差值 delta)。如果要手工生成 benchmark.json,请参考 references/schemas.md 中 viewer 期望的精确 schema。
请把每个 with_skill 版本放在它的 baseline 版本之前。
做一次分析师(analyst)复盘:阅读 benchmark 数据,挖掘聚合统计可能掩盖的模式。看 agents/analyzer.md(“Analyzing Benchmark Results” 部分)了解要关注的点,例如:不区分好坏的断言(总是通过)、高方差 eval(可能不稳定/易抖动)、耗时/耗 token 的权衡等。
启动 viewer(同时提供定性输出与定量数据):
nohup python <skill-creator-path>/eval-viewer/generate_review.py \
<workspace>/iteration-N \
--skill-name "my-skill" \
--benchmark <workspace>/iteration-N/benchmark.json \
> /dev/null 2>&1 &
VIEWER_PID=$!
从 iteration 2 开始,还要传 --previous-workspace <workspace>/iteration-<N-1>。
Cowork / 无界面环境:如果无法使用 webbrowser.open() 或环境没有显示器,用 --static <output_path> 生成一个独立 HTML 文件,而不是启动服务器。用户点击 “Submit All Reviews” 后会下载 feedback.json;下载后把它复制到 workspace 目录,供下一轮迭代读取。
注意:请使用 generate_review.py 来创建 viewer;无需自写 HTML。
“Outputs” 标签页会一次展示一个测试用例:
“Benchmark” 标签页展示统计摘要:每种配置的通过率、耗时与 token 使用,并提供按 eval 的拆解和分析观察。
可通过上一页/下一页按钮或方向键导航。完成后用户点击 “Submit All Reviews”,会把所有反馈保存为 feedback.json。
用户告知完成评审后,读取 feedback.json:
{
"reviews": [
{"run_id": "eval-0-with_skill", "feedback": "the chart is missing axis labels", "timestamp": "..."},
{"run_id": "eval-1-with_skill", "feedback": "", "timestamp": "..."},
{"run_id": "eval-2-with_skill", "feedback": "perfect, love this", "timestamp": "..."}
],
"status": "complete"
}
反馈为空通常表示用户觉得没问题。把改进重点放在用户明确提出问题的测试用例上。
用完后关闭 viewer 服务器:
kill $VIEWER_PID 2>/dev/null
这是迭代循环的核心:你已经跑了测试用例,用户也评审了结果,现在需要根据反馈让技能变得更好。
从反馈中抽象出可泛化的规律。 核心目标是做出“可被反复使用很多次”的技能,能覆盖不同提示词。你和用户之所以反复在少数例子上迭代,是因为速度快、用户也更熟悉这些例子,便于快速评估。但如果最终技能只能在这些例子上工作,那就没有价值。相比加入琐碎的过拟合修补或极其压迫的 MUST,遇到顽固问题时不妨尝试更换隐喻/表述方式,或推荐不同的工作模式;试错成本相对低,可能会找到更好的方案。
保持提示词精炼。 删除不“值回票价”的内容。一定要看运行转录(transcripts),而不仅是最终输出——如果技能让模型把大量时间浪费在无产出的步骤上,尝试删掉促使它这么做的部分,看会发生什么。
解释“为什么”。 尽量解释你要求模型做每件事背后的原因。如今的 LLM 很聪明,有很强的“换位理解”能力,给到合适的约束与动机,它往往能超越死板指令真正把事情办成。即使用户反馈很短或带情绪,也要努力理解任务与用户话语背后的动机,并把这种理解转译到指令里。如果你发现自己在大写写 ALWAYS/NEVER 或用非常僵硬的结构,那是个黄灯信号——尽量改为解释理由,让模型知道为什么这件事重要;这通常更人性、更强大,也更有效。
寻找跨测试用例的重复劳动。 阅读测试运行的 transcripts,观察子代理是否都在独立地写类似的辅助脚本,或对同一类问题都采取了相同的多步方案。如果 3 个测试用例里都出现子代理写 create_docx.py 或 build_chart.py,这是强信号:技能应当把该脚本打包。把脚本写一次放进 scripts/,并在技能中指引去使用它,能避免后续调用重复造轮子。
这件事很重要(我们是在尝试创造巨大的经济价值),你的思考时间不是瓶颈;请认真琢磨。可以先写一版改动,再过一遍用“新鲜视角”去改进。
改进技能后:
iteration-<N+1>/ 目录里(包括 baseline)。如果是在创建新技能,baseline 永远是 without_skill(不带技能)——各轮都一致。如果是在改进已有技能,baseline 取决于你的判断:可能是用户带来的原始版本,也可能是上一轮版本。--previous-workspace 指向上一轮目录,启动 reviewer持续迭代直到:
当你需要对两个版本的技能做更严格的比较(例如用户问“新版本真的更好吗?”)时,可以使用盲测比较系统。细节见 agents/comparator.md 和 agents/analyzer.md。基本思路是:把两份输出交给一个独立代理,不告诉它哪份来自哪个版本,让它判断质量;再分析胜者为何胜出。
这一步是可选的,需要子代理,多数用户并不需要。通常人工评审循环已足够。
SKILL.md frontmatter 中的 description 字段是决定模型是否调用技能的关键机制。创建或改进技能后,可以主动提出:优化 description 以提升触发准确率。
创建 20 条评测 queries——应当混合 should-trigger 与 should-not-trigger。保存为 JSON:
[
{"query": "the user prompt", "should_trigger": true},
{"query": "another prompt", "should_trigger": false}
]
这些 queries 必须真实,像 Claude Code 或 Claude.ai 用户真的会输入的内容;不要抽象请求,而要具体、细节充分。例如包含文件路径、用户工作/处境的个人背景、列名和值、公司名、URL 等;可以带一点背景故事。有些可以全小写、包含缩写、拼写错误或口语表达。长度要有混合,并重点覆盖边界情况,而不是把正负样本写得过于“显而易见”(用户后续会审核并签字确认)。
Bad: "Format this data", "Extract text from PDF", "Create a chart"
Good: "ok so my boss just sent me this xlsx file (its in my downloads, called something like 'Q4 sales final FINAL v2.xlsx') and she wants me to add a column that shows the profit margin as a percentage. The revenue is in column C and costs are in column D i think"
对 should-trigger(8-10 条),关注覆盖面:同一意图用不同说法表达(正式/随意皆有)。要包含“用户没明确提技能或文件类型,但明显需要它”的情况;也可加入一些不常见用例,以及“该技能与其他技能存在竞争但应当胜出”的用例。
对 should-not-trigger(8-10 条),最有价值的是“近似误触发”样本:它们与技能共享关键词/概念,但实际需要的是别的东西。考虑相邻领域、容易被简单关键词匹配误触发的歧义表述,以及“涉及技能能力但在该上下文里更适合用别的工具/技能”的情况。
最需要避免的是:不要把 should-not-trigger 写得明显无关。比如用“写一个斐波那契函数”来作为 PDF 技能的负样本太简单,测不出什么。负样本应当足够“刁钻”,才能真正检验描述的鲁棒性。
使用 HTML 模板把 eval 集呈现给用户复查:
assets/eval_review.html 读取模板__EVAL_DATA_PLACEHOLDER__ → eval items 的 JSON 数组(不要加引号——它是 JS 变量赋值)__SKILL_NAME_PLACEHOLDER__ → 技能名称__SKILL_DESCRIPTION_PLACEHOLDER__ → 当前技能描述/tmp/eval_review_<skill-name>.html)并打开:open /tmp/eval_review_<skill-name>.html~/Downloads/eval_set.json ——如果有多个版本(如 eval_set (1).json),注意取最新这一步很关键——差的 eval queries 会导向差的描述。
告知用户:“这会花一点时间——我会在后台跑优化循环,并定期查看进度。”
把 eval 集保存到 workspace,然后在后台运行:
python -m scripts.run_loop \
--eval-set <path-to-trigger-eval.json> \
--skill-path <path-to-skill> \
--model <model-id-powering-this-session> \
--max-iterations 5 \
--verbose
--model 使用系统提示词里显示的模型 ID(当前会话所用模型),确保触发测试与用户真实体验一致。
运行期间,定期查看输出,向用户同步当前迭代轮次与分数情况。
该脚本会自动跑完整的优化循环:将 eval 集按 60% 训练 / 40% 留出测试划分,评估当前 description(每条 query 运行 3 次以获得更稳定的触发率),再让模型基于失败项提出改进建议;对每个新描述同时在训练集与测试集上复评,最多迭代 5 次。结束后会在浏览器打开 HTML 报告展示每轮结果,并输出包含 best_description 的 JSON(按测试集分数选择,而非训练集分数,以避免过拟合)。
理解触发机制有助于设计更好的 eval queries。技能会以 name + description 出现在 available_skills 列表中,模型会基于 description 决定是否读取该技能。关键点是:模型通常只会在“它靠自己不太容易直接完成”的任务上去查询技能——像“读一下这个 PDF”这类一步请求,即使描述完全匹配也可能不触发,因为模型觉得用基础工具就能做。复杂、多步或更专业的请求在描述匹配时更容易稳定触发技能。
因此你的 eval queries 应该足够“有内容”,让模型确实能从查阅技能中获益。像“读取文件 X”这种简单请求是糟糕的测试用例——无论描述写得多好,它们往往都不会触发技能。
从 JSON 输出中取 best_description,更新技能的 SKILL.md frontmatter。向用户展示 before/after,并汇报分数。
present_files 工具时)检查你是否能使用 present_files 工具;如果没有,跳过。如果可以,将技能打包并交付给用户:
python -m scripts.package_skill <path/to/skill-folder>
打包后,把生成的 .skill 文件路径告诉用户以便安装。
在 Claude.ai 中,核心流程相同(起草 → 测试 → 评审 → 改进 → 重复),但因为没有子代理,一些机制需要调整:
运行测试用例:没有子代理就无法并行执行。对每条测试用例,先读技能的 SKILL.md,然后你自己按指令完成该提示词;一次只做一个。它不如独立子代理严格(你既写技能又跑技能,拥有完整上下文),但作为 sanity check 很有用,而且人工评审能补足。可以跳过基线运行——直接用技能完成任务即可。
评审结果:如果无法打开浏览器(例如 VM 无显示器、或远程服务器),就跳过浏览器 reviewer,直接在对话里展示结果:对每个测试用例给出 prompt 与输出。如果输出是用户需要下载查看的文件(如 .docx、.xlsx),把文件保存到文件系统并告诉用户路径,便于下载检查。再在对话里询问反馈:“看起来怎么样?有什么要改的吗?”
基准测试:跳过定量 benchmark——它依赖基线对照,没有子代理时意义不大。聚焦用户的定性反馈即可。
迭代循环:与之前相同——改进技能、重跑测试、收集反馈——只是中间不再用浏览器 reviewer。如果你有文件系统,也可以继续按 iteration 目录组织结果。
描述优化:这一节需要 claude CLI(尤其是 claude -p),仅在 Claude Code 中可用;在 Claude.ai 上请跳过。
盲测比较:需要子代理,请跳过。
打包:package_skill.py 只需要 Python 和文件系统,任何环境都可运行。在 Claude.ai 上运行后,用户可以下载生成的 .skill 文件。
更新现有技能:用户可能是要你更新已有技能,而不是新建。此时:
name 字段保持不变。例如已安装技能是 research-helper,输出应是 research-helper.skill(不要改成 research-helper-v2)。/tmp/skill-name/,在那边编辑,再从副本打包。/tmp/ staging:再复制到输出目录——直接写可能因为权限失败。如果你在 Cowork 环境里,主要注意:
--static <output_path> 输出独立 HTML,而不是启动服务器;用户提交反馈会下载 feedback.json,你需要把它复制回 workspace。generate_review.py 生成 eval viewer 给人类看例子,然后再自己评估并改技能(不要自己写一套“定制 HTML”)。提前说声抱歉,这里要用大写强调:在你自己评估输入之前,先生成 eval viewer。要尽快把样例交给人类评审!feedback.json。你可能需要先请求访问,然后再读取它。package_skill.py 只需要 Python 和文件系统。run_loop.py / run_eval.py)在 Cowork 理论上可用,因为它通过 subprocess 调用 claude -p 而非浏览器;但请在你完全完成技能、且用户认可已成型后再做。agents/ 目录包含专用子代理的说明;当你需要启动对应子代理时读取相关文件。
agents/grader.md — 如何对照输出评估断言agents/comparator.md — 如何对两份输出做盲测 A/B 对比agents/analyzer.md — 如何分析为什么某版本胜出references/ 目录包含补充文档:
references/schemas.md — evals.json、grading.json 等 JSON 结构最后再重复一遍核心循环(强调):
eval-viewer/generate_review.py 让用户评审如果你有待办清单,请把关键步骤写进去以免遗漏。若在 Cowork 环境,请务必把“创建 evals JSON 并运行 eval-viewer/generate_review.py 让人类评审测试用例”明确写入待办,确保真的会做。
祝你好运!