上一篇我们拆开了 omp 的 Session Tree——为什么它能跑几个小时不丢上下文。但光有载体还不够:你还需要在载体上注入约束,让 agent 按你的项目规范走。
这就是 Rules 系统要解决的问题。
问题:隐性规范让 agent 犯错
你写代码时脑子里有一堆”常识”:
- 这个项目禁止用 Google Fonts(国内构建会失败)
- 发布前必须跑
astro check && npm run build - 不准手维护
SUMMARY.md,让系统自动生成 - SSH 操作不能直接连 root,得用普通用户 + sudo
这些约束你记得住,但 agent 不知道。它看到 fontProviders.google() 就往上写,看到 SUMMARY.md 缺了就帮你建——每个都是”正确”操作,但在这个项目里是错的。
传统做法是反复纠正:“不要用 Google Fonts”、“我说过不要用”、“看 CLAUDE.md”。几轮下来 agent 记住了,换个项目又忘。
Rules 的做法:把约束写成文件,让系统自动注入。
规则文件长什么样
Rule 是带 YAML frontmatter 的 Markdown 文件,放在 .omp/rules/ 目录下:
---description: Astro 7 移除了 @astrojs/db 和多个 astro:transitions API,禁止使用condition: "@astrojs/db|astro db|astro login|TRANSITION_BEFORE_PREPARATION"globs: ["src/**/*.ts", "src/**/*.astro"]---以下 API 在 Astro 7 中已移除,使用会导致编译错误:
| 已移除 | 替代方案 ||--------|---------|| `@astrojs/db` 包 | 用 Content Collections + Zod schema || `astro db` CLI | 无(数据库功能已移除) |三个关键字段:
| 字段 | 作用 |
|---|---|
description | 简述规则用途,出现在 rulebook 列表里 |
globs | 文件路径模式,限定规则适用范围 |
condition | 正则条件,匹配 agent 输出时触发中断(这就是 TTSR,下一篇展开) |
规则从哪里来
omp 自动扫描多个位置,兼容主流 AI 编程工具的格式:
| 位置 | 级别 | 兼容来源 |
|---|---|---|
.omp/rules/*.md | 项目级 | omp 原生 |
.omp/RULES.md | 项目级 | omp 原生(sticky) |
~/.omp/agent/rules/*.md | 用户级 | omp 原生 |
.cursor/rules/*.mdc | 项目级 | Cursor |
.windsurf/rules/*.md | 项目级 | Windsurf |
.clinerules | 项目级 | Cline |
.github/instructions/*.instructions.md | 项目级 | GitHub Copilot |
从 Cursor 转过来?你的规则文件直接能用,不用改格式。
三种触发模式
规则按 frontmatter 字段分成三类:
1. Rulebook(按需查阅)
有 description 但没有 condition 和 alwaysApply 的规则。agent 在系统 prompt 里看到一个规则列表,需要时用 read rule://<name> 读取完整内容。
这是最轻量的模式——agent 知道规则存在,但不会每轮都读。
2. Always-apply(每轮注入)
alwaysApply: true 的规则每轮对话都注入系统 prompt。适合硬约束:
---alwaysApply: true---发布前必须通过 `astro check && npm run build`本项目的 .omp/RULES.md 就是这种模式——开篇那堆”禁止”、“必须”,agent 每轮都能看到。
3. TTSR(实时中断)
有 condition 的规则被注册到 TTSR 系统,实时监控 agent 的输出流。一旦 agent 说出或执行了匹配的内容,立刻中断、注入提醒、重试。
这是 Rules 系统最硬核的模式——不是”agent 应该遵守”,而是”agent 必须遵守,否则被打断”。
TTSR 的细节足够单独一篇展开,下一篇会讲。
实战:这个博客项目的规则
我自己项目里的规则分两类:
硬约束(sticky rule)
.omp/RULES.md 每轮注入,包含:
## 发布闸门- 发布前必须通过 `astro check && npm run build`- 禁止未确认就 `git push` 或 `ssh` 部署- SSL 证书剩余 < 14 天禁止部署
## 内容- 禁止手维护 SUMMARY.md- 禁止 Hugo 风格 frontmatter
## 字体- 禁止用 fontProviders.google()——国内构建会失败这些是铁律,agent 每轮都看到,没有借口说”不知道”。
条件规则(TTSR)
.omp/rules/ 下放了 7 条 Astro 7 兼容性规则,每条都有 condition:
---description: Astro 7 移除了 @astrojs/db,禁止使用condition: "@astrojs/db|astro db|astro login"globs: ["src/**/*.ts", "src/**/*.astro"]---agent 写代码时一旦准备输出 @astrojs/db,TTSR 立刻中断,注入替代方案。比”你之前说过不要用”靠谱得多。
写规则的经验
跑了几个月后,我总结了几条:
1. 规则要具体,不要泛泛
坏:「写高质量代码」——agent 不知道什么算高质量
好:「禁止 fontProviders.google(),用 fontProviders.fontsource()」——二选一,没有歧义
2. 给替代方案,不要只说禁止
坏:「不要用 @astrojs/db」——agent 不知道用什么 好:「@astrojs/db 已移除,用 Content Collections + Zod schema」——直接告诉它怎么做
3. 轻重分离
- 硬约束(每轮可见)放
RULES.md - 条件约束(匹配触发)放
.omp/rules/*.md - 轻量参考(按需查阅)只给
description
不是所有规则都要 alwaysApply——噪音太大会让 agent 麻木。
4. 从错误里提炼
好规则不是预设的,是从 agent 犯错里长出来的。第一次犯错就写规则,第二次就不会再犯。
怎么检查规则是否生效
# 列出当前项目加载的所有规则omp ttsr list
# 测试特定文本会触发哪些规则omp ttsr test --source text "ssh user@host rm -rf /"
# 测试 bash 命令omp ttsr test --source tool --tool bash "ssh admin@server reboot"写完规则先 omp ttsr list 确认加载了,再 omp ttsr test 确认触发条件——别等 agent 犯错才发现规则没生效。
下一步
Rules 解决了”agent 不知道约束”的问题,但它有一个局限:agent 可能看到了规则但还是犯错——毕竟规则只是在 prompt 里,不强制。
下一篇我们讲 TTSR(Time Traveling Stream Rules)——实时流中断机制:agent 输出到一半,规则系统发现违规,立刻打断、注入提醒、让它”时间旅行”回去重新生成。这是 Rules 的硬核形态。
本文是「omp 编程工具使用探讨」专栏第 3 篇。规则文件来自这个博客本身的 .omp/ 目录。