For AI agents: this page as Markdown · llms.txt · JSON Schema
#Writing rules for your repository
A Rerail rule checks a coding agent's work as it goes. When the work breaks a rule, Rerail tells the agent in the session ("steers" it), and the agent fixes it.
Start with /rerail-create in your coding agent ($rerail-create in Codex):
| You type | What happens |
|---|---|
/rerail-create |
The agent suggests rules from this repo's sessions and written standards, and writes the ones you pick |
/rerail-create use our logger, not console.log |
The agent writes that rule |
/rerail-create the no-sync rule keeps telling you to use fs/ |
The agent tunes that rule, or offers to switch it to Log |
The agent tests each draft, reads it back, and adds it only after you say yes.
Where the agent's method comes from
Every path ends the same way: test, read back, add on your yes. The agent follows the skill in
skills/rerail-create/, which ships in the package. The skill's references are the
detailed guide to everything on this page: which rules to write, how to write and test them, and how to fix one that
misfires.
#Which rules are worth having
Rules from your repo's own conventions pay off; generic style rules do not.
A rule is worth writing when:
- you have corrected the agent on it, or written it down as a standard;
- the repo already follows it almost everywhere;
- following the steer can never break working code;
- nothing else (a linter, formatter or type-checker) enforces it.
How Rerail measured this
Rerail replayed 69 real pull requests with steering off and on:
| Rule type | Result |
|---|---|
| The repo's own conventions or docs | Violations left at the end fell to zero, for 1% to 15% more cost |
Cheap defects fixed on the first steer (an async function that never awaits) |
Paid for themselves |
| Generic style rules that clash with the repo | Steered again and again; no fix made the code more correct |
| Rules that go against the repo's convention | Quality fell and cost rose by half |
Suggesting rules has the full scoring.
#Evidence from your sessions
rerail rules evidence lists what Rerail recorded for the repository that could become rules. It changes nothing.
rerail rules evidence [--repo <dir>] [--days <n>] [--limit <n>] [--json]What it lists, with sample output
It covers the last 30 days, across every coding agent and every worktree of the repository.
| It lists | Which can become |
|---|---|
| Your corrections, with what the agent had just done | A code rule, or a command rule |
| Risky commands the agent ran: force pushes, skipped hooks, hard resets, recursive deletes, publishes | A command rule |
| How often each rule steered | A rule to tune, not a new one |
| Standards files (CLAUDE.md, AGENTS.md, CONTRIBUTING.md, linter configs, Cursor and Copilot instructions) | Rules from the standards they state |
● acme-web: 42 sessions in the last 30 days (claude-code 30, codex 12), 310 prompts.
Corrections: 9.
2026-10-12 claude-code [standing instruction] Don't use console.log, we use the logger in src/log.ts
after: Edit src/api/orders.ts
Risky commands:
force push ×2 git push --force origin feature/x
Steers by rule:
n-no-sync ×12
Standards files: AGENTS.md, CONTRIBUTING.md, eslint.config.js#Two kinds of rule
Code rules check the files the agent edits; command rules check the commands it runs.
- A code rule is a
rerail.policy/v1document: globs for scope, clauses that match text, paths or syntax. - A command rule is a conversation rule that matches
input.command.
What each kind catches
- Code rules catch cross-layer imports, a call that bypasses a helper, a blocking call in async code, an old path
still written in a
Justfile, or a file in the wrong folder. A clause is aregexover a file's text or path, afilequery, or a syntax query over Python, JavaScript, TypeScript, PHP or Blade. - Command rules catch force pushes,
--no-verifyor publishing.
Guides:
- Writing a code rule
- Writing path and text rules: text and paths in any file
- Architecture rule examples: rules that hold a design in place
- Writing a command rule
- tool-call-rules.md: regex technique for command rules
#Testing a draft
A draft is the rule plus the cases it must catch and pass; test it before adding it.
rerail rules test and rerail rules add read this envelope, not the bare rule. rerail rules test --help prints it.
{
"kind": "code",
"rule": { "format": "rerail.policy/v1", "id": "local:…", "revision": 1, "mode": "steer", "description": "…", "scope": { "include": ["…"], "exclude": [] }, "clauses": ["…"] },
"cases": {
"caught": [{ "path": "src/a.ts", "content": "…" }],
"passed": [{ "path": "src/a.ts", "content": "…" }]
}
}Draft fields
| Field | What it holds |
|---|---|
kind |
code |
rule |
the rule document |
folder |
optional: the repository folder to add the rule at, instead of the whole repository |
cases.caught, cases.passed |
files the rule must catch, and must let pass: { "path", "content" } |
Writing path and text rules has complete drafts to start from.
rerail rules test draft.json # validate, run the cases, list the matches across the repo; writes nothing
rerail rules test draft.json --json # the same, listing every match and every file the rule could not check
rerail rules add draft.json # store it in your library and add it, on, to this repo
rerail rules approve <id> # after reading it: it steers instead of running in Log
rerail rules export --output rules.json # your rules, to read or edit oneWhat the report shows and skips
The text report shows the first five matches and the count; --json lists all. Path and file matches name the file
with no line. Binary files in scope are counted; no rule reads them.
The repo pass skips, and counts without naming:
- hidden files and folders;
- files whose names usually hold secrets (
*.pem,id_rsa*,.ssh/, …); - files Git ignores, unless the repository's Follow .gitignore setting is off.
Reference has the full list.
Before adding a draft, check:
- Cases. All pass, including a near miss: code that looks like a violation but is not.
- Repo matches. Each is a real violation, and there are a handful, not hundreds. Hundreds mean the repo's convention says otherwise.
- Message. Following it cannot break working code.
Rule quality has the gates, the five kinds of harmful steering, and the fix ladder for a misfiring rule.
#Steer or Log
A rule's mode decides whether the agent hears about a violation.
- Steer (
steer) tells the agent in the session. Use it when you are sure of the rule. - Log (
log) records it and tells no one. Use it on trial, or when existing code breaks it too often.
A rule from /rerail-create is never block. It belongs to the repository it was made in, unless you keep it to one
worktree.
#Approving a rule
A rule you add with rerail rules add, or an agent writes, runs in Log until a person approves its message.
Say yes to /rerail-create after its read-back, or approve on the rule's page in the dashboard. An edit needs approval
again.
Why, and what else waits for approval
Every coding agent in the repository acts on a steer, so a person reads it first. On your yes, /rerail-create runs
rerail rules approve <id>. The same approval applies to a worktree's own rules and to packs Rerail does not publish
(approval).
#A rule for one worktree only
A JSON file in the worktree's .rerail/rules/ folder is a rule that runs in that worktree only.
Use it for a branch experiment, a migration in progress, or a convention on trial. Each file holds one rule document
(the draft's rule, without the cases).
feature/ a linked worktree of the repository
└── .rerail/
└── rules/
├── no-legacy-client.json
└── use-new-logger.jsonKeep the folder out of Git unless you mean to share it: add .rerail/rules/ to .git/info/exclude.
How worktree rules run
- Scope. Each rule is on, in its own mode, for every folder in the worktree. The main checkout and other worktrees never see it.
- Edits. A changed file applies at the agent's next edit, with nothing else to do.
- Setup. Nothing to install or add, but the worktree must be started and its repository set up, as for any rule.
- Approval. Each rule runs in Log until you run
rerail rules approve <id>in the worktree, and again after each edit. - Git. A committed
.rerail/rules/runs in every checkout of that branch with Rerail started, and its messages reach the coding agent there.
/rerail-create writes a rule here when you ask for this worktree only, or pick it under Change something in the
read-back.
Checking what Rerail loaded
rerail rules test .rerail/ validates a hand-written file and counts its repo matches, as it does a
draft. It has no cases to run, so a draft with cases is still how you prove a rule.
rerail packs list in the worktree shows what Rerail loaded, whether it runs, and why a file was left out (invalid, an id
another rule already has, a rule the engine cannot run):
This worktree's own rules, in /src/acme-web-feature/.rerail/rules (pack worktree, here only): 2
Not running: this repo is not set up yet, so no rule runs here. `rerail start` sets it up.
local:no-legacy-client (code, steer)
waiting for approval, runs in Log until then: rerail rules approve local:no-legacy-client
local:use-new-logger (code, log)
left out: draft.json: clauses Too small: expected array to have >=1 itemsThe Not running line shows only while Rerail is off in the worktree or the repo is not set up.
In the dashboard for the worktree (rerail manage), these rules are the pack This worktree. Turning the pack or a
rule on or off there changes this worktree only. Its Overview lists each left-out file and why, until it is fixed or
removed.
A worktree's own rules has every check Rerail makes.