魔搭 Skill 格式适配工具
把别人/别的平台给的 Skill 压缩包,自动改成魔搭 ModelScope 社区能直接上传的规范格式。核心解决两类报错:一是 name 含中文/大写/空格导致校验不通过,二是 description 为空或规范外字段被拒。
什么时候用
- 用户丢来一个 .zip 形式的 skill 包,说「改成魔搭能传的」「适配魔搭社区」「魔搭上传报格式不正确」。
- 用户要求把中文 skill 名换成英文 slug。
- 来源可能是 SkillHub、自建、Anthropic 系工具产出的 SKILL.md。
执行步骤
第一步,确认输入。 拿到 .zip 路径。压缩包里应当有且仅有 1 个 SKILL.md(可能在根层,也可能包在一层目录里)。
第二步,运行转换脚本。 在命令行执行:
python scripts/normalize_skill.py <输入.zip> [--outdir 目录] [--name 英文名] [--description 覆盖描述]
- 默认输出到输入文件同目录,文件名加
-魔搭版.zip后缀。 --name可强制指定新 name(必须小写字母+数字+连字符,≤64 字符)。--description仅当原文件 description 实在为空时用来兜底。
第三步,核对报告。 脚本会打印:原 name、新 name(=目录名)、description 字数、被收进 metadata 的字段、输出 zip 路径,并声明原文件未改动。
第四步,交付。 把输出的 *-魔搭版.zip 给用户,提醒其在魔搭平台「展示名」一栏另填中文名(SKILL.md 里只放英文 slug)。
它具体改了什么
- name 规范化。 优先用原
slug;没有就从name/displayName推导(转小写、非法字符换连字符、合并连续连字符、去首尾连字符、截断到 64)。结果必须与最终目录名完全一致。 - 目录名对齐。 原包若包在一层中文目录里,整层改名为新 name;若根层直接是文件,则包裹一层
name/。 - description 保非空。 用 PyYAML 正确解析(含
>折叠块),压成单行,清掉中文标点后的残留空格;为空时回退到summary,再不行报错退出。长度超过 1024 会截断并告警。 - 规范外字段进 metadata。
version、slug、displayName、summary、pricing、trigger等魔搭不认识的顶层字段,全部原样收进metadata,信息不丢。 - 正文分隔线。 正文里独立的
---换成***,避免被误判为 frontmatter 收尾。 - 编码与换行。 统一 UTF-8 无 BOM、LF 换行。
- 不改原文件。 全程只写新 zip。
关键校验清单(为什么这样改)
魔搭 Skills 中心遵循 Agent Skills 协议,上传审查的关键项:
name:必填,仅小写字母+数字+连字符,≤64 字符,且必须等于父目录名。中文名必报错。description:必填,非空,≤1024 字符。- 允许的顶层字段:
name、description、license、compatibility、metadata、allowed-tools等;其余一律塞metadata。 - 压缩包根目录必须有且仅有 1 个
SKILL.md。 - 全文
---从文件第 0 字节开始,UTF-8 无 BOM。
真实踩坑:手写正则提取折叠 description 时漏了多行标志,导致 description 写成空值——魔搭判「文件格式不正确」。所以本工具一律用 yaml.safe_load 解析,再回验,杜绝空值。
注意事项
- 转换只是改头部与目录名,正文、references、scripts、assets 原样保留。若脚本里把中文名当界面展示文字(标题/横幅)使用,那是安全的,改名不影响功能;若脚本真的用中文名拼路径,请人工复查。
- 支付宝 A2M 之类支付脚本通常不读 SKILL.md 头部,改 name 不影响支付流程;但稳妥起见,转换后跑一次
grep -rin "slug\|SKILL.md\|frontmatter\|displayName" scripts/确认。 - 脚本依赖
pyyaml:pip install pyyaml。
示例
输入:/path/to/your-skill.zip(任意来源的 skill 压缩包,例如某位作者发布的示例技能包 example-skill-pack.zip)
执行:python scripts/normalize_skill.py "/path/to/your-skill.zip"
输出:/path/to/your-skill-魔搭版.zip(目录名按推导出的英文 slug,例如 example-skill-pack/;展示名在平台另填中文,例如「示例技能包」)
排错
- 报「找不到 SKILL.md」:压缩包结构不对,确认里面确实有一个 SKILL.md。
- 报「多个 SKILL.md」:包里嵌套了目录,先手动整理成单层入口再转。
- 报「无法推导合法 name」:原文件 slug/name/displayName 都没有英文可识别部分,用
--name显式指定。 - 报「description 为空」:原文件 description 和 summary 都空,用
--description给一句功能+触发描述。
Scan to join WeChat group