Most “the AI built me a bad website” stories are really “I wrote a bad spec” stories. The model is rarely the problem. With Claude Opus 4.7 scoring 87.6% on SWE-bench Verified and GPT-5.5 hitting 82.7% on Terminal-Bench 2.0 (as of June 2026), today’s agents can hold an entire site in their head. What they cannot do is guess the decisions you never wrote down. This guide gives you a persistent spec file (the CLAUDE.md / AGENTS.md your tool already reads) plus a per-task prompt structure that keeps an agent on rails across dozens of edits.
TL;DR
Put your stack, conventions, and hard “never do this” rules in a spec file at the repo root — CLAUDE.md for Claude Code, AGENTS.md for Codex, Cursor, Copilot, Gemini CLI, and ~20 other tools. Keep it under ~150 lines. Then drive every task with a 3-part prompt: context (point at the spec), task (one deliverable), constraints (explicit negatives). Small diffs, plan-then-execute for multi-file changes, and update the spec the moment reality changes. That single habit eliminates most agent drift.
What “drift” actually is
Drift is the agent quietly changing your design system, route conventions, or content schema from one task to the next. It is not a bug in the model — it happens because each new task lacks the anchor of what came before. The fix is to make the spec explicit (written, not implied), persistent (survives across sessions), and narrow (one job per prompt).
You are drifting if:
- The agent generates code that contradicts code from a previous task.
- You re-explain your stack at the top of every session.
- Your folder structure slowly diverges from your intended layout.
- The agent invents UI components or routes you never asked for.
- The same prompt produces meaningfully different output across sessions.
Which spec file does your tool read?
The two formats below cover essentially every agentic coding tool shipping in mid-2026. They are plain Markdown — no special build step, no schema to satisfy.
| File | Read natively by | Frontmatter? | Notes (as of June 2026) |
|---|---|---|---|
CLAUDE.md | Claude Code (Opus 4.7 / Sonnet 4.6) | No | Hierarchy: ~/.claude/CLAUDE.md (you) → repo-root → nested-dir. Supports @path imports and # quick-add. |
AGENTS.md | Codex, Cursor, GitHub Copilot, Gemini CLI, Aider, Zed, Windsurf, Jules, and 20+ others | No | Open standard, ~60k+ public repos. The closest file to the edited file wins; explicit chat prompts override everything. |
.cursor/rules/*.mdc | Cursor (optional, more granular) | Yes (description, globs, alwaysApply) | Use when you want path-scoped rules (e.g. API rules that load only inside src/api/). |
Practical rule: pick one primary spec file so you have a single source of truth. If you switch agents, point the other format at it — Claude Code can @AGENTS.md from inside CLAUDE.md, so you maintain one file and both tools read it.
Before you start
- Decide the spec filename your tooling reads (
CLAUDE.md,AGENTS.md, or both via an import). - Your stack and conventions are decided, not discovered — write them down first.
- Budget 30-60 minutes to draft the spec. It pays for itself within a week.
Step by step
- Create one source-of-truth spec at the repo root. Keep it tight: files over ~200 lines measurably reduce instruction adherence because every line is loaded on every turn. Template:
# CLAUDE.md (or AGENTS.md — same content, both are plain Markdown)
## Stack
- Framework: Astro 5 (Content Collections, MDX)
- Styling: Tailwind v4 (NO CSS modules, NO styled-components)
- Hosting: Firebase Hosting (static; `firebase.json` is canonical)
- Languages: en, zh — parallel folders under src/content/articles/
## Conventions
- Slugs: `^[a-z0-9-]+$`, kebab-case, no dates, no category prefix
- Folder layout: src/content/articles/[lang]/[hub]/[slug].mdx
- Content schema: defined in src/content/config.ts; do not modify without an explicit ask
- Image refs: use the `image()` helper, never `/public/...`
## Article shape (mdx files)
- Required frontmatter (schema): title, description, urlSlug, category, tags, publishedAt, lang, translationKey
- Body section order: Lead, Background, How to tell, Step by step, FAQ, Related
## Build & test
- `npm run audit:content` before build
- Build with `NODE_OPTIONS=--max-old-space-size=8192 npm run build`
## Never do (hard constraints)
- Add an npm package without asking
- Edit files outside the path the user provided
- Rename any frontmatter field
- Invent a new component when one in src/components/mdx/ would do
Add this verbatim, with your real values. The “Never do” block is the part that actually stops drift, so do not skip it.
- Drive each task with a 3-part prompt: context (point at the spec), task (one deliverable), constraints (explicit negatives). Template:
[CONTEXT]
Repo conventions are in CLAUDE.md. The article schema is in src/content/config.ts. We use Astro Content Collections.
[TASK]
Add a new article at src/content/articles/en/indie-dev/[slug].mdx that follows the article shape in CLAUDE.md.
Title: "[title]". Primary keyword: "[keyword]". Length 600-900 words.
Include at least one bash code block and one config code block.
[CONSTRAINTS]
- Do NOT modify src/content/config.ts.
- Do NOT add npm dependencies.
- Do NOT touch other articles.
- Slug must match the filename and pass /^[a-z0-9-]+$/.
- Do NOT put a bare brace in prose (MDX brace bug). Wrap any literal braces in backticks.
Reply with the file content only; I will commit.
-
Keep each task small enough to read in one diff in two minutes. A 200-line diff is the soft cap. Larger than that and you start approving code you did not actually read — which is how the next task inherits a mistake.
-
Use explicit negative constraints. The constraints section is where most of your leverage is. Keep a reusable library:
Constraint library
─────────────────────────────
DO NOT add npm/pip dependencies
DO NOT modify files outside [path]
DO NOT change [named-config-file]
DO NOT introduce client-side JS for [page-type]
DO NOT rename any export/symbol used elsewhere
DO NOT silently bump package versions
DO NOT add comments that restate obvious code
- When the output is close but wrong, send a diff, not a fresh prompt. Agents follow targeted edits far more reliably than “redo it with these changes,” which re-rolls the whole file. Format:
Apply this diff and produce the updated file:
@@ src/content/articles/en/indie-dev/foo.mdx @@
- Some sentence with a problem
+ The corrected sentence
-
After each accepted change, update the spec if anything in it implicitly shifted. A two-line edit today beats a two-hour drift debug a month from now. In Claude Code you can do this mid-session by starting a line with
#— it asks where to store the note and writes it into the rightCLAUDE.md. -
For multi-file refactors, ask for a plan first, approve it, then execute. Template:
Before editing any file, list:
1. Files you will change
2. The one-line nature of each change
3. Risks / order dependencies
Wait for me to say "go" before producing diffs.
- Save successful prompts as templates. Keep a
prompts/directory and store the ones that worked. Your prompt library compounds faster than your codebase — and a saved prompt is a reproducible result.
Why explicit beats remembered
Conversational memory is not a spec. In Claude Code, the root CLAUDE.md is re-injected after a /compact, but nested directory files are not re-loaded until the agent next reads a file in that directory, and anything you only said in chat is fair game to forget once the context window fills. For Cursor and Codex, the same logic applies: AGENTS.md is concatenated into every turn, but loose chat instructions are not. So the rule is simple — if a decision must survive across sessions, it belongs in the file, not the conversation.
Run /memory in Claude Code at any time to see exactly which instruction files are loaded and in what order. If a rule keeps getting ignored, check that it is in a file that is actually being read.
Verify it worked
- A fresh agent session, fed the same spec + task prompt, produces a near-identical diff. Low variance is the signal that drift is gone.
- The agent declines or asks for clarification when a task would violate a spec rule, instead of plowing ahead.
- Your spec-file diffs line up with the feature changes you accepted.
Common pitfalls
- Writing prompts as conversations, not specs. “Can you make the nav nicer?” gets you nice-feeling, unpredictable output.
- Letting the spec go stale. If
CLAUDE.mdstill says Tailwind but you switched to CSS modules, the agent will pull Tailwind back in on the next task. - Asking for too much at once. “Fix routing and add OG tags and update the footer” gets one of the three right and the rest wrong.
- Skipping constraints because “obviously it wouldn’t do that.” It will do that.
- Trusting in-session memory. Long sessions lose early context; restate the parts that matter.
- Approving large diffs unread. The next task branches from whatever you accepted.
- Bloating the spec. Past ~150-200 lines, adherence drops. Split into
CONTENT.md/DESIGN.mdand import them rather than growing one giant file.
FAQ
- How long should the spec file be?: Aim for under 150 lines; treat ~200 as a hard ceiling. Every line is loaded on every turn, so past that point you are paying context tax and losing adherence. Split into per-area files and reference them from the top-level spec.
- CLAUDE.md or AGENTS.md — which one?:
CLAUDE.mdif you live in Claude Code;AGENTS.mdif you use Codex, Cursor, Copilot, or Gemini CLI (it is an open standard read by 20+ tools, ~60k+ public repos as of June 2026). To support both, keep one file and@-import it from the other. - Do
.cursor/rulesfiles replace AGENTS.md?: No — they complement it. UseAGENTS.mdfor project-wide rules and.cursor/rules/*.mdc(withglobsandalwaysApply) when you want rules that load only for specific paths, like API-only conventions insidesrc/api/. - Does this work the same for Codex and Cursor?: Yes. The principles are model-agnostic. The only difference is the filename your tool reads and that Codex/Cursor concatenate
AGENTS.mdfrom the repo root down (closest file wins). - I’m not technical enough to write a spec. Now what?: Have the agent draft v1 by interviewing you about your stack and conventions, then edit it. Bootstrapping is fine — the spec just has to exist.
- Should I include examples in the spec?: Yes. One concrete example (a real slug, a real frontmatter block) beats five abstract rules.
External references: Claude Code memory docs and the AGENTS.md open standard.
Related
- Using Claude Code to Build a Content Site End-to-End
- Doing an SEO Review of Your Site with Codex
- Scaling Content with AI Without Tanking Quality
- Site QA with AI checklists
- Find content gaps with AI
Tags: #Indie dev #AI-assisted build #Claude Code #Codex #Workflow