这篇能做出什么
跟着做完,仓库里会多出四样东西:
1. 根目录一份 AGENTS.md,写清项目的安装命令、测试命令、代码约定和禁区。
2. 一份薄薄的 CLAUDE.md,只负责把 Claude Code 引到 AGENTS.md。
3. 一条薄薄的 Cursor 规则 .cursor/rules/agents.mdc,同样只做指引。
4. 一套明确的冲突裁决顺序,三个工具同时开着也不会各说各话。
成果是:同一个任务丢给不同工具,它们跑的命令、遵守的边界、提交的风格基本一致,你不用再维护三份互相矛盾的长文档。
前置条件清单
- 一个已经用 Git 管理的代码仓库,本地能正常 clone、安装、跑测试。
- 本地已经装好至少一款带仓库级规则的编码工具(Claude Code、Codex、Cursor 任选,多装几款更好验证)。
- 你清楚项目的真实命令:装依赖、起服务、跑测试、跑单测、类型检查、格式化。写不准的命令不要写进文件,先自己跑一遍。
- 能读仓库里的
package.json、Makefile、pyproject.toml、CI 配置或CONTRIBUTING.md,素材基本都在里面。 - 各工具对规则文件的读取方式会随版本变化,具体行为以官方文档当前版本为准。
第 1 步:先看清三套文件的定位
| 文件 | 谁来读 | 建议承担的角色 |
|---|---|---|
AGENTS.md | 遵循该约定的多款工具、也可当人读的文档 | 规则来源,写全部通用约定 |
CLAUDE.md | Claude Code 的项目记忆 | 薄壳,导入 AGENTS.md,只写 Claude 专属补充 |
.cursor/rules/*.mdc | Cursor 的项目规则 | 薄壳,声明规则来源,复述几条硬约束 |
.cursorrules | 较老版本的 Cursor 会读 | 能不用就不用,避免和新机制打架 |
核心思路一句话:通用规则只写一遍,放在 AGENTS.md;工具私有文件只做三件事——声明来源、复述硬约束、写该工具独有的行为要求。
为什么不干脆三份都写全?因为三份全量文档一定会漂移。某天你改了测试命令,只更新了 AGENTS.md,另外两个工具还在跑旧命令,报错排查半天,问题却出在文档上。
第 2 步:收集素材
在仓库里跑几个命令,把散落的信息捞出来:
```bash
看有哪些脚本可以当命令来源
cat package.json | grep -A 30 '"scripts"'
看最近的真实改动风格和提交信息格式
git log --oneline -30
看 CI 里实际跑了什么,这通常就是"提交前必须过"的清单
ls .github/workflows 2>/dev/null && cat .github/workflows/*.yml
看有没有现成的贡献指南
ls CONTRIBUTING.md docs/ 2>/dev/null
```
把结果整理成四类:命令、目录职责、代码约定、禁区。写不出禁区的项目,通常是因为没想过哪些改动会伤人——锁文件、数据库迁移、CI 密钥、发布流程,这些就是候选。
第 3 步:写 AGENTS.md
文件名大小写要一致,放在仓库根目录。用 Markdown 表格和列表,别写成长段落。下面是一份可直接改用的模板(Node/TypeScript 示例,换成你的技术栈即可):
```markdown
AGENTS.md
本文件是仓库内 AI 编码智能体的规则入口,规则对人和智能体一致。
项目概况
一句话说清这是什么、给谁用、核心模块有哪些。
环境准备
- 运行时版本以仓库内
.nvmrc/.tool-versions为准 - 安装依赖:
npm ci - 首次运行前把
.env.example复制为.env.local,该文件不提交
常用命令
| 目的 | 命令 |
|---|---|
| 启动开发服务 | npm run dev |
| 全部测试 | npm test |
| 单个测试文件 | npm test -- path/to/file.test.ts |
| 类型检查 | npm run typecheck |
| 代码检查 | npm run lint |
| 自动格式化 | npm run format |
| 构建 | npm run build |
改完代码至少执行:npm run typecheck && npm run lint && npm test,
并在回复里贴出实际结果,不要只说"已通过"。
目录地图
src/api/:HTTP 层,只做参数校验与转发,不写业务逻辑src/domain/:业务逻辑,不依赖 HTTP 框架与数据库驱动src/infra/:数据库、队列、外部服务客户端tests/:集成测试,按功能模块建文件
代码约定
- 缩进 2 空格、行宽 100,交给格式化工具,不要手工对齐
- TypeScript 开启 strict,禁止
any,拿不准用unknown再做类型收窄 - 导入顺序:标准库 → 第三方 → 仓库内绝对路径 → 相对路径,组间空一行
- 单个函数超过 40 行先拆分再提交
- 不吞异常,抛出带上下文的自定义错误;日志统一走
src/infra/logger.ts,不用console.log - 新增第三方依赖前先说明理由并等待确认
禁区
- 不修改锁文件,除非任务明确要求升级依赖
- 不修改
migrations/下已合并的迁移,新增迁移单独建文件 - 不提交
.env、密钥、令牌、真实用户数据 - 不改动
.github/workflows/中的密钥与发布配置 - 不执行
git push --force、git reset --hard、删除远程分支 - 不做与任务无关的全仓库重命名或格式化
工作方式
- 先读相关文件再改,不凭猜测写代码
- 一次只做一件事,改动范围与任务匹配
- 需求不清楚就问,不要自行扩大范围
- 提交信息遵循 Conventional Commits,例如
fix(api): 处理空响应 - 结束时说明:改了哪些文件、跑了哪些命令、结果如何
```
长度控制在 100~200 行之间比较稳妥。太长的规则文件,靠后的条目容易被忽略,所以把禁区放在中前部。
第 4 步:给 Claude Code 加薄壳 CLAUDE.md
Claude Code 默认读项目根的 CLAUDE.md。它支持用 @路径 的形式导入其它文件,所以把通用规则留在 AGENTS.md,这里只做转接:
```markdown
CLAUDE.md
@AI 词典:AGENTS.md">AGENTS.md
仅 Claude Code 的补充
- 涉及三个以上文件的改动,先给计划再动手
- 生成提交信息时正文用中文,标题保持英文类型前缀
- 回答里引用文件时给出相对路径和行号
```
两个注意点:@AGENTS.md 的路径是相对当前文件解析的,写错路径它会被当成普通文本,不报错但也不生效;另外不要在这里重复粘贴 AGENTS.md 的正文,重复就是漂移的开始。
第 5 步:给 Cursor 加薄壳规则
在仓库里新建 .cursor/rules/agents.mdc。.mdc 文件用 YAML frontmatter 控制生效方式,alwaysApply: true 表示始终注入:
```markdown
---
description: 仓库通用智能体规则,始终生效
alwaysApply: true
---
规则来源:仓库根目录 AGENTS.md。开始编辑前先读取并遵守它。
硬约束(与 AGENTS.md 冲突时以 AGENTS.md 为准):
- 不修改锁文件与
migrations/下已合并的迁移 - 不提交
.env与任何密钥 - 不执行
git push --force - 改完执行
npm run typecheck && npm run lint && npm test
仅 Cursor 的补充:涉及 UI 的改动,说明改了哪些组件与样式文件。
```
如果 Cursor 的当前版本能直接识别 AGENTS.md,这条规则可以作为冗余保险保留,成本很低。是否原生支持、frontmatter 字段有哪些,以官方文档当前版本为准。
第 6 步:定死读取与冲突顺序
三份文件同时存在时,按下面这套规则执行,写进 CONTRIBUTING.md,团队和智能体都照此办理:
1. 工具私有文件先被读取:CLAUDE.md、.cursor/rules/*.mdc 优先加载,但它们只负责指向 AGENTS.md。
2. AGENTS.md 是通用规则的权威来源,命令、约定、禁区一律以它为准。
3. 冲突时 AGENTS.md 优先,私有文件里只允许出现"补充",不允许出现"例外"。
4. 就近覆盖:monorepo 里子目录可以放自己的 AGENTS.md,描述该子包特有的命令与边界;它覆盖根目录的同名约定,不覆盖禁区。
5. 一条规则只写一遍,任何重复都要删掉一处。
第 7 步:落地验证
验证不要靠感觉,用只读问题提问,看三个工具回答是否一致:
```text
只读任务,不要修改任何文件。请回答:
1. 本仓库跑全部测试的确切命令是什么?
2. 哪些路径属于禁区?列出路径和原因。
3. 新增一个 HTTP 接口,应该改哪些目录、不该改哪些目录?
4. 提交信息的格式是什么?给一个例子。
```
再补一个行为验证:挑一个真实小任务,比如"给某个工具函数补一个边界值测试"。完成后检查三件事:
```bash
1. 有没有碰禁区文件
git status --short
2. 有没有跑它声称跑过的命令(自己复跑一遍)
npm run typecheck && npm run lint && npm test
3. 提交信息是否符合约定
git log --oneline -1
```
这一步能暴露大部分问题:规则写了但没生效、命令写过时了、禁区没写具体路径。发现问题就回到 AGENTS.md 改一处,而不是去三个文件里打补丁。
常见坑与排错
- 文件名或位置不对:
AGENTS.md要放在仓库根、大小写一致。放在docs/里有些工具扫不到。 - 规则太长导致后半段被忽略:砍掉形容词,保留命令和路径。能用命令表达的,别写成形容词。
- 空话规则不生效:"要写测试"改成"改完执行
npm test,并在回复里贴结果"。 - 三份文件内容不一致:立刻做减法,私有文件只留指引和补充。
@AGENTS.md导入无效:路径写错时不会报错,只是当普通文本。改完让工具复述一条AGENTS.md里的专属规则,能复述出来才说明导入成功。- Cursor 规则不生效:检查 frontmatter 是否漏写
alwaysApply,漏写时规则只在匹配特定文件模式时启用。 - 软链接方案:
ln -s AGENTS.md CLAUDE.md在 macOS/Linux 上省事,但在 Windows 和部分 CI 环境会出问题,团队里有 Windows 用户就老实用薄壳文件。 - 写死了会过期的信息:具体版本号、依赖清单别抄进规则,改成"以仓库内
.nvmrc与锁文件为准"。 - 把密钥或内网地址写进规则:规则文件会进 Git、也会进模型上下文,这类内容一律不写。
- CI 里跑的命令和文档不一致:挑一个当权威来源(通常是 CI),文档跟着 CI 改,反过来会一直对不上。
下一步建议
- 把
AGENTS.md加入 PR 检查清单:改动命令或目录结构时,同一条 PR 内更新它。 - 用 CI 兜底禁区:
migrations/、.github/workflows/这类路径加 CODEOWNERS 或分支保护,规则靠自觉,CI 靠强制。 - 把格式问题交给 pre-commit 钩子,规则文件里就不再需要写缩进和引号风格。
- 多仓库团队可以抽出公共片段文件,在
AGENTS.md和CLAUDE.md里用@导入,减少重复。 - 每隔一个季度回看一次:哪条规则从没被触发,哪条规则被违反过,删掉无效的,补上踩过的坑。规则文件的价值不在长,在于每条都能被执行和验证。
