
这两年做 AI 编程工具链的底层支持最大的感受是每换一个工具就要重新调教一遍 Agent。Cursor 里手写的规则换到 Windsurf 就失效Claude Code 能正常跑的技能包复制给 Copilot 直接报错。后来我把“Skills Manager”这个跨平台桌面中枢搭了出来把 54 款 AI 编程工具的 Agent 技能统一收编到同一个本地仓库这个问题才算真正解决。今天就把这套方案的完整思路、架构设计和实操过程分享出来希望能给同样在折腾 AI 编程工具选型和技能管理的朋友一个参考。先说清楚这东西定位它不是又一个 AI 编程工具也不是提示词编辑器而是站在所有 AI 编程工具之上的一层“技能调度层”。不管底层接的是哪家大模型、哪款 IDE、哪个命令行工具所有 Agent 技能都从这里集中定义、统一投递、可查可管可迁移。适合谁用个人开发者频繁切换工具的场景、团队内部多人共用多款 AI 编程工具的协作场景以及那些手握 AI 工具选型话语权、想先建好团队能力基线的技术负责人。1. 为什么一个桌面端要管 54 AI 编程工具的 Agent 技能1.1 Agent 技能到底是什么Agent 技能听起来高大上本质上就是给 AI 编程工具里的 Agent 准备的一组“操作手册”。它告诉 Agent 遇到什么场景先做什么、后做什么、按什么标准输出。同一个代码规范在 Cursor 里可能就是一条 .mdc 规则在 Claude Code 里是 SKILL.md在 Copilot 里是自定义指令。各家叫法五花八门skill、rule、command、instruction本质都是同一类东西——都属于 Agent 技能。我个人的习惯是避免用“提示词”这个词来称呼这堆东西。“提示词”给人感觉是一次性输入的几句话用完就丢而技能是一个标准模块应该能独立维护、独立分发、独立升级。后面我会统一用“技能包”这个词指代所有工具里的这类内容也只有把概念统一了后面的标准格式设计才有基础。1.2 现实世界里的技能碎片化现状如果只用一款工具、固定一台电脑其实压根不需要 Skills Manager 这类东西。但现实中绝大多数开发者和团队都处在混合状态本人可能今天用 Cursor 写前端明天用 Claude Code 跑自动化脚本团队里有人是 Windsurf 党有人是 Copilot 党还有人命令行重度依赖 Gemini CLI。这种混合状态会带来一层一层的麻烦。第一层是格式不通用Claude Code 的 skill 目录结构投到 Windsurf 里不一定被识别Cursor 的规则用的是 .mdc 后缀直接把 markdown 文件改名放进去也不一定被加载各家工具的加载逻辑都有自己的脾气。第二层是路径不一致Windows、macOS、Linux 的目录结构差异很大技能里但凡出现绝对路径换台机器百分百出问题。第三层是命名混乱同一个“代码审查”技能仓库里可能同时存在 code-review、review-agent、codeReview.md 三种叫法时间一久连作者自己都记不清哪份是最新的。第四层是版本冲突同一个技能在 A 工具里被改了B 工具里还是老版本两个版本逻辑互相矛盾Agent 行为完全不可控。这四层问题叠加起来最直接的结果是团队引入 AI 编程工具后每个人都在“各写各的规则”项目经验很难沉淀。我见过不止一个团队大半年下来积累了成堆的技能文件却没有人能说清这些文件的用途和维护关系。1.3 统一管理之后实际省下了什么这套方案的核心目标是在本地建立一个“技能唯一事实源”所有技能包只有一份标准内容所有 AI 编程工具都从这里派发。实现之后的实际收益非常直观。换工具不再伤筋动骨。从 Cursor 迁到 Windsurf技能包不需要重写只需要重新投递一遍整个流程用不上十分钟。团队协作也有了共同基线代码审查规则、命名规范、架构约束、安全红线全团队用同一套技能文件审计和培训都变得简单。技能也可以真正版本化了文件放 Git 仓库里管理每次修改有记录、有 diff再也不会出现“这个规则谁改的、为什么改”的糊涂账。我在做技术选型时经常看到有人在纠结“推荐选哪个大模型”“哪个 AI 编程工具最好用”我的经验是工具层和模型层的差异远小于技能层的一致性带来的差异。同一个 Agent喂一套结构混乱、互相冲突的技能包和喂一套组织良好的技能包表现差距非常明显。所以如果你有采购选型的话语权先把技能仓库立起来永远是投入产出比最高的第一步。1.4 什么样的工具才配叫“跨平台桌面中枢”跨平台桌面只是表象核心是“中枢”两个字。我认为它至少要满足几个条件所有技能操作的入口统一所有工具的适配可扩展所有数据本地保存且可迁移。说白了就是让桌面应用承担“调度中心”的角色它本身不写代码、不替 Agent 做判断但它清楚每一份技能应该发往哪款工具、哪个目录、用什么格式。54 这个数字听起来很多但真正的门槛不是适配器数量而是标准是否稳定。只要标准稳定适配器就是“复制粘贴”级别的工作。2. 整体架构设计与核心技术思路这一章主要讲设计。如果你准备二次开发同类工具或者想评估现有工具是否靠谱理解这三层设计基本就够了。2.1 三层结构本地仓库、适配层、桌面壳我把系统拆成三层每层职责单一。第一层是技能仓库本质是本地磁盘上的一个标准目录存放所有技能包的源文件它是唯一事实源不依赖任何一款 AI 编程工具。第二层是适配层一组接口每个 AI 工具对应一个适配器负责把标准技能包翻译成目标工具认识的格式再写入目标工具读取的位置。第三层是桌面壳基于跨平台桌面框架做的图形界面提供技能浏览、编辑、导入导出、投递、状态启停这些高频操作。这个三层结构本质上是在模仿操作系统里的驱动设计应用不用关心外设具体是哪家厂商系统只要装好对应的驱动程序就能统一调度所有设备。适配器就是技能层的驱动。做这个设计时我特意避开了“中心化服务器”方案。原因很实际技能包本身是纯文本丢到 Git 仓库里天然就能协作而服务器方案要额外维护鉴权、同步、在线状态复杂度翻几倍收益却几乎没有。本地优先还能保证离线可用对开发场景更友好。2.2 技能包的标准格式SKILL.md skill.yaml统一格式是整个方案的基石。我定义了一个两文件结构简单到不能再简单SKILL.md 是给 Agent 看的完整提示词正文skill.yaml 是机器可读的元信息用于索引、筛选、版本管理、投递路由。举一个真实的代码审查技能包例子code-review/ SKILL.md skill.yamlSKILL.md 的内容类似这样# Code Review 你是一名高级代码审查工程师。收到代码变更后请按以下流程审查 ## 审查步骤 1. 确认变更范围和受影响模块。 2. 检查逻辑缺陷、边界条件、空值处理、资源释放。 3. 检查安全问题注入风险、敏感信息泄露、越权访问。 4. 检查性能问题循环复杂度、高频IO、内存占用。 5. 输出分级结论。 ## 输出格式 - P0必须修复的严重缺陷 - P1强烈建议修复 - P2可改进项 - P3可选优化skill.yaml 的内容name: code-review version: 1.2.0 description: 对代码变更执行结构化审查输出P0-P3分级结论 engines: - cursor - windsurf - claude-code - copilot - gemini-cli scripts: - scripts/prepare.py注意 scripts 字段这个设计来源于实际踩坑。很多技能不只是提示词还包括配套脚本、示例样本、正则模板。把这些资源统一归属到技能包目录下导出和投递时才能整体搬运。写 SKILL.md 的心得是把它当成岗位说明书而不是聊天开场白。清晰定义角色、流程、约束和输出格式。只有激情没有流程的提示词换到 Agent 身上就会变成只输出漂亮话、不出实际结果的“嘴强王者”。2.3 为什么用 SQLite 做台账和索引技能文件的正文是 Markdown但整个仓库的台账、标签、版本、启用状态、支持工具列表我用了一张 SQLite 表来管。这一步的体验提升非常明显。查询方便是一方面想找“所有启用了 claude-code 且版本大于 1.0、打了 security 标签的技能”一条 SQL 语句就出来了。轻量可靠是另一方面SQLite 就一个文件推到团队共享目录里就是一份随时可迁移的台账不需要额外部署数据库服务。这里顺带一提跨平台桌面应用普遍是这种存储思路开源的跨平台音乐管理系统、DB Browser for SQLite社区常叫 db4s都这么干。SQLite 被无数应用验证过可靠性完全不需要担心。索引文件损坏的情况一年半载不会出现一次万一出现删除重建即可因为源文件都在磁盘上。说到底SQLite 只是一种加速查询的方式源文件才是本质这种思路比把所有内容都塞进数据库要安全得多。2.4 54 工具的适配策略三类加载模型把工具数量堆到 54 以后逐个开发适配器会很累。我一开始就先对主流工具的加载机制做了分类最后发现三类就能覆盖绝大多数情况。目录型工具最简单直接把 Markdown 或者配套文件放到约定目录即生效。Claude Code 的 skills、Windsurf 的 commands 都属于这种。配置型工具需要在工具的配置文件里显式声明启用路径Cursor 的 rules、Copilot 的自定义指令更接近这种文件放对了但配置里没挂上也不会生效。插件型工具需要生成插件入口文件、注册指令代码或者遵循特定包结构一般出现在功能更重的 IDE 插件方案里。适配器接口收敛得很快from typing import Protocol, Path class SkillAdapter(Protocol): name: str supported_tools: list[str] def export(self, skill, target_path: Path) - None: 把标准技能包转成目标工具格式写入目标路径 ... def verify(self, target_path: Path) - list[str]: 校验投递结果返回未通过项 ...新增一个工具的流程就三步确定类型、写 export 方法、写 verify 方法。遇到目录型工具基本半天搞定遇到插件型工具需要多看文档两天也足够了。这个项目里“54”不是炫耀的资本恰恰说明适配层一旦抽象对了工作量可以线性压缩。2.5 框架选型Tauri 与 Electron 之间的取舍跨平台桌面壳的选择我在 Tauri 和 Electron 之间纠结了很久。Electron 生态成熟、遇到问题资料多缺点是打包体积大、内存占用高Tauri 用系统 WebView打包体积小、内存占用低但跨平台一致性需要多花精力验证。这个项目最终用了 Tauri。原因有三一是 Skills Manager 交互不重不需要 Electron 级别的完整浏览器内核二是技能管理工具本身应该轻量常驻托盘时不希望吃掉几百 MB 内存三是前端基于 Web 技术可以用 Vue 快速做界面Rust 后端负责文件扫描、SQLite 读写、适配器调度。这类选择没有绝对对错。如果团队熟悉 Node 技术栈、后续要做大量可视化Electron 会更省心。我自己是踩过跨平台兼容性的坑之后对资源占用又比较敏感才定的 Tauri。3. 实操搭建从零收编第一个 Agent 技能包理论讲再多不如把流程跑一遍。这一节按真实操作顺序走包括环境准备、仓库初始化、技能包创建、导入迁移和投递验证。3.1 环境准备与安装我分别在 Windows 10、macOS 13、Ubuntu 22.04 上验证过三个平台的安装包都是向导式一路 Next 就能装完。几个平台细节值得提前说。macOS 首次打开第三方应用需要到“系统设置-隐私与安全性”里允许一次如果下载的是未签名版本甚至需要在应用图标上右键打开。Linux 下如果启动报 WebKit 相关的缺库错误装一下 libwebkit2gtk-4.0-dev 之类的依赖就能解决不同发行版的包名略有差异按提示安装即可。Windows 上尽量用普通用户目录安装避免路径带中文或者空格导致适配器文件路径解析出问题。3.2 初始化技能仓库打开应用后第一步是设置技能仓库路径。我推荐的路径是 Windows 下用 %USERPROFILE%.skills-manager\skillsmacOS 和 Linux 下用 ~/.skills-manager/skills。设置完后应用会做三件事创建目录结构、扫描已有文件、写入索引台账。如果是从零开始你会看到一个空列表。这里我想强调一下目录命名一定要看得懂、可排序。我统一用 kebab-case 小写命名比如 code-review、unit-test-generator不用带空格的名字也不用中文理由后面排查章节会解释。3.3 手工创建第一个技能包直接在技能仓库目录下新建一个文件夹 code-review里面放 skill.yaml 和 SKILL.md 两个文件按 2.2 节的示例填写内容。应用界面上技能列表会立刻出现这个技能包。如果没出现多半是目录路径没对上或者文件后缀写错了。YAML 文件的严格格式容易踩坑字段之间有缩进错误时很多工具不会明确报错只会在解析时静默失败。注意YAML 里缩进必须一致不要混用 TAB 和空格。我见过好几个同事的技能包没生效最后排查半天就是 skill.yaml 第一行多了个看不见的全角空格。3.4 从现有工具导入技能迁移旧技能是高频场景。在应用里选择“导入”来源类型选 Claude Code Skills指定源目录应用会自动解析原技能包并转换。导入时有个易错点Claude Code 的 SKILL.md 里经常通过相对路径引用 scripts 目录下的脚本。导入过程如果只搬运了 md 文件没搬运 scripts后面投递到别的工具就会找不到脚本。所以导入完成后我都会在应用里跑一遍“依赖检查”逐项确认引用的文件都存在。有一次我导入了同事给的“测试用例生成”技能包正文写得好好的结果 Agent 在实际执行时一直报错。打开检查才发现SKILL.md 里写了 scripts/seed.py但 scripts 目录根本不存在。类似案例我遇到不止一次所以已经把依赖检查当成导入流程的必做项。3.5 投递到目标工具并验证技能包就位后在应用里点“投递”选择目标工具。适配器会自动做格式转换并写入对应位置。不同目标的常见落位可以参考这张表目标工具投递落位格式要点Cursor.cursor/rules/*.mdc建议文件名与技能名同名Claude Code~/.claude/skills/ /SKILL.md目录名必须与技能名一致Windsurf.windsurf/commands/*.md可保留 frontmatter 元信息GitHub Copilot.github/copilot-instructions.md多个技能会聚合进同一份文件Gemini CLI~/.gemini/skills/ /SKILL.md与 Claude Code 结构类似投递只是第一步验证才是关键。我的习惯是打开目标工具输入一句“按代码审查流程处理这段代码”然后观察输出是否严格包含 SKILL.md 里定义的输出格式。只要输出结构对得上说明技能生效了如果输出自由发挥说明技能没有被加载需要回到排查流程。3.6 用命令行实现批量管理和脚本化技术功底深的读者可能不满足于界面操作。我额外在项目里暴露了一个 CLI 入口核心用法如下# 列出所有已启用技能 skills-manager list --enabled # 投递指定技能到 cursor skills-manager push code-review --tool cursor # 校验某个技能包完整性 skills-manager check code-review # 从 claude-code 导入技能 skills-manager import claude-code ~/.claude/skills/code-reviewCLI 有什么用它可以放进 CI 或者团队初始化脚本里。比如新同事入职时一条命令就完成本地技能仓库克隆和投递省去手动操作的麻烦。我自己通常会把投递命令写进项目的 Makefile新增成员照着执行一遍就行。如果要做定时同步也可以把命令挂进 crontab 或者任务计划程序技能包在团队仓库里更新后本地自动重新投递。4. 常见问题与排查技巧实录再多设计思路落到真实环境里都会遇到各种意外。这里整理几个高频问题每个都是我实际踩过并且解决过的直接给出处理路径。4.1 技能“显示投递成功”但工具里不生效这个问题出现频率最高而且最容易被误判为“工具版本不支持”。按下顺序排查基本能定位。先看落位路径。适配器写入的目录未必是工具当前加载的目录比如 Cursor 可以通过设置修改 rules 目录如果用户改过路径写入默认目录就不会生效。再看文件格式Claude Code 要求 SKILL.md 这个精确文件名Cursor 的规则文件需要 .mdc 后缀Copilot 的自定义指令要在统一文件里聚合格式错一个字母工具就当没看见。然后看配置声明配置型工具需要在主配置里引用规则文件光把文件放进去不会自动加载。最后看文件大小技能正文太长会导致加载被截断表现为“有时生效有时不生效”。我的经验阈值是 SKILL.md 不超过 50 行。超过 50 行就考虑拆分技能正文只保留核心指令细节放到 references 目录下由 Agent 按需阅读。这既保证加载完整又不会因为上下文太长稀释注意力。4.2 同样一份技能在不同工具里表现不一致这是跨工具使用的核心痛点。原因也很简单不同大模型对提示词格式的敏感度不同Claude Code 跑得顺的写法在 Gemini CLI 上可能理解不了Copilot 对长指令的处理方式和 Claude 系工具也差别很大。我的解法是在 skill.yaml 里增加 per-engine 配置针对不同引擎提供定制版 promptengines: - name: claude-code prompt: | 你是一名代码审查工程师严格按以下流程输出P0/P1/P2结论... - name: gemini-cli prompt: | 请对代码执行审查以固定模板输出问题清单...这样投递到不同工具时适配器会自动选取对应版本而不是用同一段话生搬硬套。虽然维护成本稍微高了一点但换来的是各工具下的真实可用性这笔账很划算。4.3 跨平台迁移后路径和中文编码出问题Windows 的仓库拷到 macOS经常出现技能无法投递或脚本执行失败。几乎都是两个原因路径符号和文件编码。技能包里的脚本引用统一用相对路径比如 scripts/prepare.py禁止写 C:\Users\xxx\ 这种绝对路径。所有文件统一 UTF-8不带 BOMWindows 记事本可能默认带 BOM拷到 Linux 下解析时行首会出现奇怪字符。文件名不用中文、不用空格统一小写加连字符某些 Linux 工具对中文文件名支持没问题但脚本里引用时容易踩编码坑干脆从一开始就规避。再补一条如果确实要在提示词里给 Agent 指路径就给一个相对于技能目录的路径并说明脚本在技能目录下找。不要指望 Agent 自己脑补绝对路径它脑补出来的大概率是错的。4.4 多用户协作时技能互相覆盖团队共享同一个技能仓库最怕的就是 A 改了 B 也改最后互相覆盖。我的处理方式是把技能仓库放到 Git 仓库里桌面端操作本地文件版本控制兜底冲突。建议约定一套协作规范一个技能一个目录目录名即技能名一至两个核心文件。commit 信息统一格式比如 feat(skill): 新增 code-review v1.2便于追溯。每次从远端拉取后在应用里执行一次“重建索引”让 SQLite 台账同步到最新文件状态。这套流程跑顺后新人加入团队变得非常简单克隆仓库、设置技能仓库路径、选择自己用的工具再执行一遍投递三分钟就能获得与全团队一致的 Agent 能力基线。4.5 其他值得注意的坑速查再列一些零散但同样有价值的经验。大模型上下文有限技能包不宜贪多。同时启用太多技能Agent 注意力会被稀释主任务反而执行不稳定我一般控制在 5 到 8 个核心技能。某些工具需要重启会话才重新加载技能文件特别是配置型工具。改了配置不生效可以先重启试试别急着怀疑适配器。不用把业务敏感信息写进技能包正文。技能文件要进 Git 仓库早晚会被多人接触敏感信息放在脚本里读取环境变量别裸露在 SKILL.md 里。定期导出整个仓库为一个压缩包备份。虽然 Git 仓库有历史但本地方便的备份能让灾难恢复更快。最后再分享一点个人体会真正让这套机制跑起来的不是适配器代码也不是桌面界面的交互而是把团队里的技能内容沉淀成标准模块的过程。技能一旦脱离了工具格式的限制后续换大模型、换工具、新增成员都只是调一下适配器的事。如果你也在带团队推 AI 编程工具我建议把“统一技能层”当作第一步哪怕暂时不想引入桌面工具先把技能包按统一目录结构和命名规范管理起来收益也会立刻显现。