PRODUCT THINKING

Writing PRDs for AI Agents: Why Narrative Specs Break Cursor and Claude Code

Narrative PRDs written for human engineers confuse AI coding agents. The specific writing patterns that produce coherent AI-generated code — and the four things you must never write in an agent-ready spec.

Jul 21, 2026Updated: Jul 21, 20269 min readBy Scriptonia

A PRD written for human engineers contains narrative prose, business rationale, and implicit assumptions that engineers fill from experience. These same characteristics make a PRD an unreliable input for AI coding agents. Narrative descriptions produce inconsistent implementations; implicit assumptions produce bugs; business rationale consumes token budget without contributing to implementation quality. An agent-ready spec is a different document: structured, explicit, and implementation-focused. This guide covers the specific writing patterns that produce coherent AI-generated code.

4
Patterns in narrative PRDs that consistently cause AI coding agents to make wrong implementation decisions
3–5×
Fewer correction prompts when using structured vs. narrative specs as AI coding context

The four patterns that break AI coding agents

Pattern 1: Conceptual field names

Narrative PRD: "The system should store a token that expires after 15 minutes."

What the AI does: Creates a field called token, reset_token, or authToken — whichever pattern it has seen most often. If your existing schema uses tokenHash and expiresAt, the AI creates inconsistent names that don't match your conventions.

Agent-ready spec: "Create a PasswordResetToken record with fields: tokenHash (string, SHA-256 of raw token), expiresAt (DateTime, 15 minutes from creation), usedAt (DateTime, nullable)."

Pattern 2: Implicit library choices

Narrative PRD: "Send a transactional email when the user requests a password reset."

What the AI does: Chooses an email library based on training data frequency — often Nodemailer, SendGrid, or whichever is most common. If your codebase uses Resend with a wrapper function in lib/email.ts, the AI creates a duplicate, inconsistent email path.

Agent-ready spec: "Send email using the existing sendTransactionalEmail() function in lib/email.ts. Do not create a new email utility."

Pattern 3: Narrative error handling

Narrative PRD: "Handle the case where the email doesn't exist in the system appropriately."

What the AI does: "Appropriately" means different things in different contexts. The AI may return a 404, a 400, a 200 with an error body, or a 200 with a generic message — each is defensible in isolation, none is consistent with your API conventions.

Agent-ready spec: "If the email is not in the User table: return HTTP 200 with body {"message": "If this email is registered, you will receive a reset link."}. Do not return 404 or 400 (prevents account enumeration). Log the attempt with log.info('password_reset_attempt', {email, found: false})."

Pattern 4: Business rationale as context

Narrative PRD: "We are building this feature to reduce support ticket volume. Our current support load is 1,200 tickets per month from authentication issues. The business goal is to reduce this by 60% within 60 days of launch, which represents a $48,000 annual savings in support costs."

What the AI does: This paragraph consumes token context without providing implementation guidance. The AI acknowledges it, then ignores it. In a long PRD, business rationale in the early sections pushes the implementation details (data model, API contracts) later in the context, where they may be weighted less heavily or truncated.

Agent-ready spec: Remove business rationale entirely from agent context. Keep it in the PRD for stakeholder communication; strip it when generating the agent-ready spec.

The six elements of an agent-ready spec

1. Exact entity and field names

Use the exact names from your existing data model. If your schema uses created_at (snake_case), use created_at — not createdAt. Consistency with existing naming prevents migration conflicts and ORM issues.

2. Explicit file and function references

Tell the AI exactly which existing utilities to use. Format: "Use functionName() in path/to/file.ts." If there are multiple similar functions, name the one to use and explicitly prohibit creating new ones: "Do not create a new [utility type]."

3. Enumerated constraints

Every constraint that affects the implementation must be listed explicitly as a numbered item. If you write constraints as prose ("the token should be secure and should expire reasonably quickly"), the AI interprets "reasonably quickly" based on training data priors. "Token expires 15 minutes after creation — check expiresAt < Date.now() before processing" is unambiguous.

4. Explicit negative space

State what the implementation must not do. AI coding agents are optimistic — they tend to add features and utilities beyond what is specified. Explicit prohibitions prevent this: "Do not create a new authentication middleware — use the existing requireAuth() in middleware/auth.ts." "Do not add session invalidation — this will be handled in a separate ticket."

5. Observable success criteria

State what "done" looks like in terms of observable behavior. These double as test cases. Format: "Given [precondition], when [action], then [observable outcome]." The AI can use these to self-verify its implementation.

6. Ordered implementation steps (for complex features)

For features involving multiple files, database migrations, and API changes, an ordered implementation sequence prevents the AI from creating the route handler before the migration, or the component before the API exists. Format: "1. Create Prisma migration for PasswordResetToken. 2. Implement POST /api/auth/forgot-password route. 3. Implement POST /api/auth/reset-password route. 4. Add reset link to the login page."

Template: converting a narrative PRD section to an agent-ready spec

Narrative PRD (for humans)Agent-ready spec (for AI coding tools)
"Users should be able to reset their password"POST /api/auth/forgot-password — see endpoint contract in Section 3
"The reset link should expire"PasswordResetToken.expiresAt = now() + 15 minutes. Reject if expiresAt < now()
"Send the user an email"Use sendTransactionalEmail() in lib/email.ts. Template: 'password-reset'. Variables: {resetUrl, userName}
"Handle errors appropriately"Invalid token → HTTP 400, {error: 'invalid_token'}. Use apiError() in lib/api.ts
"Keep it secure"Store SHA-256(rawToken) in DB. Send rawToken in URL only. Single-use: check usedAt IS NULL

How to generate agent-ready specs at scale

Writing agent-ready specs manually takes 30–60 minutes per feature if you know the codebase well. Scriptonia's architecture blueprint generation produces the core sections — data model with exact field names, API endpoint contracts, state machines — in 15–25 seconds. The PM or tech lead adds the file references (Section 2) and verifies the constraint list. Total time: under 10 minutes per feature. The resulting spec is more consistently formatted than manual writing and covers edge cases that manual writing often misses.

Frequently asked questions

Why do narrative PRDs break AI coding agents?

Narrative PRDs use conceptual language ('store a token that expires') rather than exact field names ('PasswordResetToken.expiresAt'). They reference implicit library choices ('send an email') rather than specific utilities ('sendTransactionalEmail() in lib/email.ts'). They describe error handling vaguely ('handle appropriately') rather than explicitly ('return HTTP 200 with generic message to prevent enumeration'). Each ambiguity becomes an implementation decision the AI makes inconsistently with your existing codebase.

What is an agent-ready specification?

An agent-ready specification is a structured document designed for AI coding agents rather than human engineers. It contains: exact entity and field names from your data model, explicit file and function references for existing utilities to reuse, enumerated constraints as numbered items (not prose), explicit negative space (what the implementation must not do), observable success criteria in Given/When/Then format, and an ordered implementation sequence for complex features. Length: 200–400 words. Written before each AI coding session.

What should I remove from a PRD before using it as AI coding context?

Remove: (1) business rationale and cost/revenue impact — the AI doesn't need it and it consumes token budget; (2) stakeholder context ('the VP of Engineering requested this') — irrelevant to implementation; (3) historical context ('this replaces the old system that was built in 2021') — irrelevant; (4) conceptual descriptions where exact technical specifications exist. Keep only what directly constrains the implementation: data model, API contracts, file references, and explicit constraints.

How do I write acceptance criteria for AI coding agents?

Use Given/When/Then format with exact technical specifics rather than user-centric language. For a human audience: 'Given a user clicks an expired reset link, when they land on the reset page, then they see an expiry message.' For an AI coding agent: 'Given a POST /api/auth/reset-password request with a token where PasswordResetToken.expiresAt < now(), the endpoint returns HTTP 400 with {error: "invalid_token"} and does not update User.passwordHash.' The AI coding agent uses the second form to write the route handler and its tests.

Try Scriptonia free

Turn your next idea into a production-ready PRD in under 30 seconds. No account required to start.

Generate a PRD →
← All articles
Writing PRDs for AI Agents: Why Narrative Specs Break Cursor and Claude Code | Scriptonia