255 个 agent 全装进全局目录,代价是什么
一、现象:你只想要几个 agent,命令却按”全部”理解
agency-agents 这个仓库(github.com/msitarzewski/agency-agents)的 README 在 Quick Start 里给的第一条脚本命令很短:
./scripts/install.sh --tool claude-code
短到很容易让人再省一步,直接敲 ./scripts/install.sh。而 install.sh 的 USAGE 段写得很清楚:裸调用等于把所有 team 装到所有检测到的工具;在 TTY 下默认会进交互向导。
这里的”所有”是多大一坨?按仓库各 division 目录下带 frontmatter 的 agent markdown 统计(核对日 2026-08-09),是 255 个 agent,分布在 17 个 division。Engineering 一个 division 就占 58 个,Specialized 57 个,Marketing 36 个。顺带提醒一个数字陷阱:仓库里 markdown 文件总数约 316,比 255 大——差额是 README、CONTRIBUTING、strategy/ 下的编排文档、examples/ 这些非 agent 文件。看到 316 就说”316 个 agent”是错的。
于是典型的处境是这样几种:
- 想撤回,但不知道该删目标目录下哪一批文件,因为不确定当初写进去了什么;
- 以为装在了当前项目里,回头在家目录发现一堆东西(或者反过来);
- 换了个工具(比如 Aider),发现目标位置根本不是”一堆文件”,而是一个被写满的单文件,跟预期对不上。
这三种都指向同一个根因:没有先确认”这次安装到底要写哪些产物、写到哪个 scope”就落盘了。下面按”确认 → 处置 → 验证 → 排除”走一遍。
二、怎么确认是这个问题:三个不落盘的动作
排查的第一原则是先别写磁盘。install.sh 提供了三个只读动作,足够把问题定死。
动作 1:--dry-run 打印计划但不写任何东西。
./scripts/install.sh --dry-run
USAGE 里对 --dry-run 的定义就是”只打印计划、不写任何东西”。在往 ~/.claude/agents/ 这类共享目录批量落盘之前,这是成本最低的一步。
动作 2:--list 列出后退出。
./scripts/install.sh --list tools
./scripts/install.sh --list teams
./scripts/install.sh --list agents
--list 接 tools|teams|agents 三个值之一,列完就退出。它回答的是”脚本在这台机器上检测到了哪些工具""可选的 team 和 agent 分别有哪些”。如果你裸跑时被装了一堆意料之外的工具,--list tools 就是那份意料之外的名单。
动作 3:回 tools.json 看 installKind 那一列。
这一列决定产物形态,是最容易被跳过、也最容易导致”对不上”的地方。tools.json 的 _note 把 installKind 定义为安装机制,并说明它是上游真相、对每个消费方都成立:
| installKind | 产物形态 | 例子 |
|---|---|---|
per-agent | 每个 agent 渲染出一个文件或一个目录 | Claude Code:.claude/agents/{slug}.md |
roster | 所有 agent 合并成一个文件 | Aider:CONVENTIONS.md;Windsurf:.windsurfrules |
plugin | 一个构建出来的产物,不能按 agent 渲染成字符串 | Hermes:.hermes/plugins/agency-agents-router |
这张表怎么读:如果目标工具是 per-agent,那么”全装”字面意义上就是 255 份产物;如果是 roster,产物只有一个文件,但那一个文件里是全部 agent 的内容;plugin 则只有 Hermes 一个,_note 明确它不能按 agent 渲染成字符串,在所有消费方都只能走 CLI。
至于每个 agent 正文有多大,花名册导出里带了词数,量级大致在千词上下(例如 Academic division 里,academic-narratologist 约 884 词,academic-statistician 约 1669 词)。这只是文件层面的事实,我们没有测过它对任何工具的上下文占用或启动加载有多大影响,也不打算给一个编出来的数字。
动作 4(同样只读):确认 scope 到底是家目录还是当前目录。
install.sh 的注释列出了各工具的落点,其中有一个很容易踩的差别:opencode、cursor、aider、windsurf 这四个写的是当前目录(.opencode/agents/、.cursor/rules/、CONVENTIONS.md、.windsurfrules),而 claude-code、codex、gemini-cli、osaurus、hermes、vibe 等多为家目录。所以”我在项目里跑的命令,为什么东西跑到账户级去了”这类困惑,答案通常不在参数,而在你选的是哪个工具。
顺带说明一点口径:tools.json 里 opencode 的用户级路径是 .config/opencode/agents/{slug}.md,与 install.sh 注释写的”当前目录 .opencode/agents/”不是同一个位置——这两处分别对应不同 scope。要断言某个具体路径,回源文件按当前 scope 核对,别把两者混着说。
三、脚本语义给出的处置:把范围收窄,或者把落点挪走
确认之后,处置手段全在 USAGE 里,分三类。
收窄选择范围(选择器可自由组合,全空等于全装):
| 参数 | 含义 |
|---|---|
--tool <a,b> | 只装这些工具 |
--division <a,b> | 只装这些 division |
--agent <slug,slug> | 只装指定 agent |
--agents-file <path> | 从文件读 agent 列表,每行一个 slug 或名字,支持 # 注释 |
--agents-file 是这几个里最适合团队用的:一份可以提交进版本库、可以写注释说明为什么留这几个的清单,比每次手敲一长串 slug 靠谱。
挪走落点:
--path <dir>覆盖安装目录(单一目标)。- 环境变量覆盖:
CLAUDE_CONFIG_DIR、COPILOT_AGENT_DIR、CURSOR_RULES_DIR、GEMINI_AGENTS_DIR、OPENCODE_AGENTS_DIR、OPENCLAW_DIR、QWEN_AGENTS_DIR、CODEX_AGENTS_DIR、OSAURUS_SKILLS_DIR、HERMES_HOME、HERMES_PLUGIN_DIR、VIBE_HOME。脚本注释说明这些变量在硬编码默认值之前被检查,所以想先看看产物长什么样,可以把它们指到一个自己控制的目录。
其它行为开关:--link 用符号链接代替拷贝(脚本说明是改动会自动传播);--no-convert 在集成文件缺失时不自动跑 convert.sh;--parallel 并行安装各工具、输出按工具缓冲,--jobs N 控制最大并行数(默认取 nproc 或 4)。
一个把”先看再装”串起来的组合:
# 第一步:只看计划,不落盘
./scripts/install.sh --tool claude-code --division engineering --dry-run
# 第二步:确认计划无误后去掉 --dry-run
./scripts/install.sh --tool claude-code --division engineering
以上为按官方参数语义组合的示例,未逐项实测,以官方文档与 ./scripts/install.sh --help 的实际输出为准。
平台方面,脚本注释写的支持范围是 Linux、macOS(需要 bash 3.2+)、Windows Git Bash / WSL。Windows 用户注意这一条:这是 Shell 脚本,PowerShell 或 cmd 里直接敲不是它的预期用法,得在 Git Bash 或 WSL 里跑。
四、处置后怎么验证
按顺序检查四处,前两处不需要落盘就能做:
- 重跑
--dry-run,看计划里的目标路径和条目是不是收窄到了你要的范围。 这是唯一能在写盘前拿到的证据。 - 对照
installKind判断计划形态是否合理。 目标是per-agent却只看到一个文件,或者目标是roster(Aider、Windsurf)却看到一长串文件,说明你选的工具和你的预期不是一回事,先回第二节动作 3。 - 确认落点的 scope。 家目录的
~/.claude/agents/与项目目录里的同名路径是两个位置;.cursor/rules/、CONVENTIONS.md、.windsurfrules按注释是当前目录。看错目录就会得出”没装上”的错误结论。 - 如果用了
--path或环境变量,确认产物出现在你指定的那个目录,而不是默认位置。脚本注释说明这些环境变量在硬编码默认值之前被检查,所以设了变量就不会再落到默认路径上;至于--path与环境变量同时给出时谁优先,注释里没写,别猜,回install.sh现读。
五、什么情况说明不是”装太多”这个原因
这一步比前面几步更重要——下面这些症状看着像”装多了”,实际根因完全不同,按”装少点”去治是白费力气。
症状:Cursor 里装完像没装,规则不生效。 这不是数量问题。convert.sh 渲染 cursor-mdc 时,frontmatter 里的 globs: "" 和 alwaysApply: false 是写死的,也就是说转换出来的规则默认不会自动生效,需要在 Cursor 里按需引用。装 1 个和装 255 个在这一点上没有区别。
症状:Aider 或 Windsurf 那边”只有一个文件”,怀疑没装全。 这是 installKind: roster 的设计:所有 agent 合并成一个文件(CONVENTIONS.md / .windsurfrules)。同理,“为什么 Aider 里没法只装某一个 agent”的答案也在这里——它的产物形态就不是一 agent 一文件。
症状:Hermes 这边用图形化方式装不上。 tools.json 的 _note 说明 plugin 类是构建出来的产物、不能按 agent 渲染成字符串,在所有消费方都只能走 CLI。这是机制限制,不是你装多了。
症状:装的内容看起来是旧的 / 和源 markdown 对不上。 这条要往 convert 那边查。链路是「源 agent markdown → convert.sh 渲染成各工具格式 → integrations/ → install.sh 拷贝到目标目录」,integrations/ 是产物目录不是源目录。install.sh 在集成文件缺失时默认会自动调 convert.sh,但”过期”和”缺失”不是一回事——如果你之前加过 --no-convert,或者产物是旧的,问题在转换环节而不是安装范围。
症状:某个目录明明有 md 文件,却没被当成 division。 这也不是安装问题。divisions.json 的 _note 写明并非每个顶层目录都是 division:integrations/、strategy/、examples/、scripts/ 在 scripts/check-divisions.sh 里通过 NON_DIVISION_DIRS 被排除;一个目录要成为 division,必须至少包含一个带 frontmatter 的 agent 文件。strategy/ 放的是 playbook 和 runbook,没有 agent frontmatter,本来就不是可安装对象。
最后一条通用提醒:这个仓库在 2026-08-09 的快照里有 140729 star、22985 fork、110 个 open issue。关注度高是事实,但不能由 star 数推导出它适合你的项目、质量如何或是否稳定。同样,agent markdown 里那些”You’ve built and deployed ML systems at scale”式的句子是写给模型的人设文本,不是任何人的真实履历,别当成能力背书。真正值得你花五分钟的,是先跑一次 --dry-run。
延伸阅读
本文依据 agency-agents 官方仓库(github.com/msitarzewski/agency-agents)的 README、
tools.json、divisions.json、scripts/ 下的安装与校验脚本整理,核对日 2026-08-09。
本文内容为仓库源码与文档口径,我们没有安装或运行过其中任何 agent。
目录、脚本与安装路径随上游更新而变动,请以仓库最新内容与 ./scripts/install.sh --help 的实际输出为准。