AGENTS.md is seven design decisions in a trench coat. Each one has a token bill.

Most write-ups of the spec stop at "radical simplicity, single file, no frontmatter". That is true and useless. The interesting question is what each decision costs you per turn when your AGENTS.md is the system prompt of a long-running session. Seven decisions, seven consequences. The whole spec is on one page at agents.md; the per-turn cost is not.

M
Matthew Diakonov
6 min
Direct answer (verified 2026-05-21)

What design choices shaped AGENTS.md?

Seven explicit decisions in the published spec: (1) plain markdown only, no YAML or schema; (2) a single root-level file, not a directory; (3) no required fields or sections; (4) the literal filename AGENTS.md chosen over earlier candidates like AI.md and BOT.md; (5) nested subdirectory files override by concatenation (an OpenAI Codex extension), not by replacement; (6) a 32 KiB default cap on the file body the loader reads; (7) no @-import or include syntax in the base spec. Verified against agents.md and OpenAI's Codex documentation on 2026-05-21. The full breakdown, with per-turn cost consequences, is the rest of this page.

The seven decisions, in one place

Left column is the decision and what it cost; right column is what the alternative would have cost. Same axis: tokens, cache, or loader behavior.

FeatureThe road not takenAGENTS.md decision
1. Plain markdown only (no YAML frontmatter, no schema)GitHub Copilot's instruction files use YAML frontmatter. JSON Schema for prompts has been proposed in several places.AGENTS.md is just standard Markdown. No required fields, no validator, no parser. The cost is no machine-readable scope. The benefit is zero migration work to adopt.
2. Single root-level file (no .agents/ directory)Cursor uses .cursor/rules/*.mdc. Anthropic uses .claude/skills/<name>/SKILL.md. Both shard rules across many files.One file at the repo root. Subdirectory AGENTS.md files are allowed but optional. The cost is no per-feature granularity. The benefit is one place to read.
3. No required fields or sectionsMost agent-config formats want at least a title, a 'rules' block, or a glob pattern. AGENTS.md requires none of it.Use any headings you like; the agent parses the text you provide. The cost is that two AGENTS.md files in the wild look nothing alike. The benefit is the file does whatever the project needs without ceremony.
4. The literal name 'AGENTS.md'Earlier candidates included AI.md, BOT.md, and CONTRIBUTING-AI.md. Cursor uses .cursorrules. Anthropic uses CLAUDE.md.Plural noun, all-caps in the style of README.md, with a .md extension. The cost is no vendor-specific signal. The benefit is one filename your repo can ship that any compliant tool can read.
5. Nested subdirectory files override by concatenationCLAUDE.md uses @-import to inline another file's body. Cursor's .mdc files have explicit glob scoping. Both replace, do not concatenate.OpenAI Codex concatenates AGENTS.md files from the root down, joining with blank lines. Files closer to the working directory appear later in the prompt and therefore win on conflict. The cost is the prompt grows linearly with directory depth.
6. 32 KiB default cap (project_doc_max_bytes)Anthropic's loader has no documented hard cap on CLAUDE.md size; it just loads the whole file and lets you pay for it.Codex truncates at 32 KiB unless you raise the ceiling. 32 KiB at 4 chars per token is about 8,000 tokens. At Opus 4.7 input rates on a 30-turn session that is roughly $3.60 worst-case.
7. No @-import or include syntax in the base specClaude Code resolves @path/to/file.md up to a five-hop limit before injecting into the system prompt. The wrapper file can stay one line while the resolved blob grows.Out of the box, AGENTS.md is its own contents and nothing else. To get composition, you write to disk (concatenate manually) or rely on nested directory discovery. The cost is no DRY mechanism in the file itself.

1. Plain markdown only

The spec page is explicit: "AGENTS.md is just standard Markdown. Use any headings you like; the agent simply parses the text you provide." No YAML frontmatter, no JSON Schema, no XML wrapper. The decision is one line in the spec and one entire class of features deleted.

The trade-off is real. Frontmatter would have let you tag a rule as "only fire when editing TypeScript" or "only inject for subagents". Without it, every line of your AGENTS.md fires for every task, on every turn, for every tool call. The token cost of that decision scales linearly with file size: a 4,000-token AGENTS.md that could have been split with frontmatter is 4,000 tokens injected unconditionally instead of 800 tokens injected conditionally.

The benefit, also real, is that any tool that can read a markdown file can read AGENTS.md the day it ships. No parser version, no validator, no migration. That is the trade.

2. Single root file, not a directory

Cursor stores rules in .cursor/rules/*.mdc, one file per concern, with explicit glob patterns. Anthropic ships skills as .claude/skills/<name>/SKILL.md, loaded on demand. AGENTS.md rejected both shapes: one file, one place, no manifest.

The token consequence is that AGENTS.md cannot do conditional load. Every byte you put in the file is a byte the host can choose to include in every prompt. There is no metadata that lets a host say "skip the database section for this task". That is the price of one place to read.

The benefit is auditability. If the file is one file, you can read it. If it is a directory of fifteen .mdc files with glob scopes, you have to mentally execute the loader to know what the model will see. For a deeper look at this drift, see AGENTS.md host context drift.

3. No required fields, no schema

You can ship an AGENTS.md that is one line. You can ship one that is 1,200 lines and starts with a poem. Both pass. There is no validator because there is nothing to validate against. The spec authors say this in plain text on the homepage: "The beauty of agents.md is its flexibility, there are no required fields."

That decision pushes all responsibility for what makes a good AGENTS.md onto the writer. There is no "your file is malformed" error. The file is whatever you wrote. The closest thing to a standard rubric in public is Karpathy's 12-rule list for what a useful agent-config file should contain. ccmd applies that rubric to any AGENTS.md paste and reports the pass count. The first time most people audit their file they score 2 or 3 out of 12, because the spec never told them what good looked like.

4. The name "AGENTS.md" (plural, all caps, not vendor-specific)

The plural noun is a deliberate signal: the file is for any agent that wants to read it, not for one specific product. The all-caps convention matches README.md and CONTRIBUTING.md, which the spec authors explicitly cite as the precedent. The decision to not use AI.md, BOT.md, or CONTRIBUTING-AI.md was about adoption: the name has to be visually distinct from human docs but read like a peer to README.

The cost is no vendor-specific signal in the filename. Compare with CLAUDE.md, which ties the file to Anthropic, or .cursorrules, which ties the file to Cursor. AGENTS.md is the only filename a repo can ship that any compliant tool reads, which is also the only filename ccmd's detector finds without help. As of the Linux Foundation announcement in December 2025, over 60,000 open-source projects already ship one.

5. Nested files concatenate, they do not replace

This is the one Codex-specific decision in the list. OpenAI's docs describe it directly: "Codex concatenates files from the root down, joining them with blank lines. Files closer to your current directory override earlier guidance because they appear later in the combined prompt."

The mechanism is loader order, not file precedence. There is no "subdirectory file wins" rule in the spec. There is just "later in the prompt wins because LLMs weight later instructions higher." The token consequence is that the prompt grows linearly with how deep in the directory tree you are working. Open a file in src/billing/refunds/ in a repo with AGENTS.md at every level and Codex injects four AGENTS.md bodies into the system prompt, joined by blank lines.

Cursor and Claude Code do not implement this concatenation. A subdirectory-only AGENTS.md is invisible to them. That is one of the most common drifts we see when teams ship multiple AGENTS.md files and assume every tool reads them. See AGENTS.md and CLAUDE.md import drift for a worked example.

6. The 32 KiB default cap

OpenAI Codex truncates AGENTS.md at 32 KiB by default, controlled by the project_doc_max_bytes setting. The docs note that you should "raise the limit or split instructions across nested directories when you hit the cap."

32 KiB at the standard 4-chars-per-token estimate is about 8,000 tokens. If your AGENTS.md is at the cap and fires every turn through Codex, that is roughly 8,000 input tokens per turn. On a 30-turn uncached session at Opus 4.7's $15 per million input rate, that is about $3.60 for the system prompt alone. The cap exists because the spec authors knew people would write 50 KiB AGENTS.md files; the truncation forces a quality conversation instead of a silent bill. If you have not measured your file's size, paste it into the analyzer at the homepage and read the totalTokens number. More on that calibration step in AGENTS.md token audit cost.

7. No @-import in the base spec

Anthropic's CLAUDE.md supports @path/to/file.md imports up to a five-hop recursion limit. A one-line CLAUDE.md that just says @AGENTS.md is a complete CLAUDE.md as far as the loader is concerned. AGENTS.md itself has no equivalent. The spec is the file contents; the file contents are the spec.

The trade is composition vs simplicity. Imports would have given you a DRY mechanism (write shared rules once, reference them from many AGENTS.md files). The cost would have been a parser, a hop limit, a cycle-detection rule, and a resolution model that every host has to re-implement. The decision was to skip all of that and let users either inline (copy-paste, accept drift) or rely on nested-directory concatenation (Codex-specific). For shops that want both, the common pattern is to maintain AGENTS.md as the source of truth and ship a one-line CLAUDE.md that imports it. The wrapper stays one line; the analyzed body is the AGENTS.md.

What ccmd's analyzer inherited from these decisions

When the analyzer reads a paste, the format-detection routine treats AGENTS.md, CLAUDE.md, .cursorrules, and .grokrules as different labels on the same underlying problem. The reason is decision 3: the spec has no schema, so there is nothing format-specific to score against. The rubric and the per-line findings apply to all four.

src/lib/analyzer.ts
Three pastes, three labels, identical scores

That is the design decision behind the analyzer: the label on the report is cosmetic. The real audit, the 12-rule rubric and the per-line bloat and aspirational and missing-why checks, is format-agnostic. The same way AGENTS.md itself is.

Want a second pair of eyes on your AGENTS.md?

Paste yours into ccmd.dev for the free audit. If the score and the seven decisions on this page do not line up with what you expected, book a call and we will walk through it line by line.

Questions about the decisions

Who decided these design choices?

AGENTS.md emerged from the Amp team at Sourcegraph and is now jointly driven by OpenAI, Google, Cursor, and Factory. It was donated to the Linux Foundation under the Agentic AI Foundation in December 2025. The seven decisions on this page come from two authoritative sources: the spec page at agents.md (the project's published rationale) and OpenAI's Codex docs at developers.openai.com/codex/guides/agents-md (the host-specific extensions). Both pages are linked at the bottom.

Why no YAML frontmatter when GitHub Copilot uses it?

Frontmatter is a tax on the writer. Every YAML block is a place to put a typo that silently breaks parsing in one host while another host happily ignores it. The AGENTS.md design choice was to eat the cost of zero machine-readable metadata in exchange for zero adoption friction. The trade-off is real: you cannot, for example, tag a rule as 'only fire when editing TypeScript' inside the file itself. You either write that constraint into the prose and hope the model honors it, or you push the constraint into a nested subdirectory AGENTS.md.

Why a single file when Cursor uses a directory of .mdc files?

Two reasons stated by the spec authors. First, READMEs are for humans and AGENTS.md is the same shape (one file, root level, immediately discoverable). Second, sharding configuration across a directory means the agent now has to read N files, decide which ones apply to the current task, and merge them. That logic lives in the host. AGENTS.md punts it: one file, you read it, done. Codex's nested discovery (decision 5) re-introduces sharding for monorepos, but only as an opt-in extension.

What changes if I move my AGENTS.md from the root to a subdirectory?

Under OpenAI Codex specifically: nothing, as long as you also keep the root one. Codex walks from project root down to the current working directory and concatenates one AGENTS.md per level (joined by blank lines). Files closer to your cwd appear later in the combined prompt and therefore override earlier guidance on conflict. Under Cursor or Claude Code, which do not implement nested AGENTS.md discovery, a subdirectory-only file is invisible. This is the most common drift: a project ships an AGENTS.md in src/billing/ and assumes every agent reads it. Only Codex does.

Does ccmd's analyzer treat AGENTS.md differently from CLAUDE.md?

No, and that is on purpose. The detector at src/lib/analyzer.ts:41 reads the first 300 characters and returns one of four labels: agents.md, claude.md, .cursorrules, or .grokrules. The rubric (12 Karpathy-style checks) and the per-line findings (bloat, vague, aspirational, duplicate, missing-why, cache-bust) all run identically. The label only changes the header on the report. The reason: the underlying problems with these files are token bloat, missing exceptions, and aspirational absolutes. None of those care which spec your file claims to follow.

What is the practical cost of the 32 KiB cap?

32 KiB is roughly 8,000 tokens (at the standard 4-chars-per-token estimate the analyzer uses). If your AGENTS.md is at or above the cap and fires every turn through Codex, you pay ~8,000 input tokens per turn. At Opus 4.7's $15 per million input on a 30-turn uncached session that is about $3.60 just for the system prompt. The default exists because the spec authors knew people would write 50 KiB AGENTS.md files; the truncation forces a quality conversation instead. If you have not measured your file, paste it into ccmd.dev and read the totalTokens number off the textarea.

If AGENTS.md has no @-import, how do I share rules across files?

Three options, none of them clean. (1) Manually inline: copy the shared block into AGENTS.md by hand. The cost is drift the moment one copy is updated and the other is not. (2) Use the nested directory mechanism (Codex only): put global rules in the root AGENTS.md and project-specific rules in subdirectory AGENTS.md files. The cost is non-portable: Cursor and Claude Code do not concatenate. (3) Author a CLAUDE.md that uses Anthropic's @AGENTS.md import for Claude Code, and let Codex read the AGENTS.md directly. The cost is two source files to keep in sync, but every host sees the same body.

How did this page land for you?

React to reveal totals

Comments ()

Leave a comment to see what others are saying.

Public and anonymous. No signup.