Structuring the Agent Prompt: Context, Spec, Constraints
You have a spec. Now you have to deliver it to an agent in a way the agent can actually execute. A perfect spec buried in a sloppy prompt still produces sloppy output. The order, the framing, and what you include around the spec all change the result.
This lesson is about packaging. The spec is the payload; the prompt is the envelope. Get the envelope right and any agent — terminal, IDE, or autonomous — executes more reliably.
What You'll Learn
- The three layers of an effective agent prompt
- Why order matters: context before spec before constraints
- How to give just enough context without drowning the agent
- How to ask for a plan before code on larger tasks
- A practice exercise you can run in the prompt playground
The three layers
Every strong agent prompt has the same three layers, in this order.
- ContextWhere the work lives, what already exists
- SpecThe checkable requirements from the last lesson
- ConstraintsGuardrails and how to respond
Context comes first because the agent reads top to bottom and uses early information to interpret what follows. Constraints come last because they are the final word — the rules the agent should carry into every decision it makes while building.
Layer 1: context
Context is the orientation the agent needs but cannot infer. It answers: where does this code live, what is already there, and what is the intent behind the task?
Good context is relevant, not complete. You are not dumping the whole repo. You are pointing at the few things that matter:
- The file or module the change belongs in.
- The existing pattern to follow ("errors are thrown as
AppError, seeerrors.ts"). - The shape of nearby data the new code interacts with.
- The reason behind the task, so the agent connects it to real intent.
A useful framing: give the reason, not just the request. "I'm adding discount codes because marketing needs a holiday promo by Friday; it has to work with the existing cart totals" tells the agent far more about acceptable trade-offs than "add discount codes" does.
Most agents can read files themselves, so you often do not paste code — you name it. "Follow the validation style in validators.ts" lets the agent go look. That keeps your prompt short and your context current.
Layer 2: the spec
This is the spec from the previous lesson, dropped in verbatim. Acceptance criteria, edge cases, prior decisions. You already know how to write it. The only packaging note: keep the headings. The structure helps the agent parse requirements into a mental checklist, and it helps you when you come back to verify.
Layer 3: constraints and response shape
The final layer holds the guardrails plus instructions for how to respond. The guardrails are the constraints from your spec — no new dependencies, only touch these files, do the simplest thing. The response-shape instructions tell the agent what you want back:
- "Show me the plan before writing any code."
- "After implementing, run the tests and report the results."
- "List any assumptions you had to make."
That last one is quietly powerful. Asking the agent to surface its assumptions turns silent guesses into visible decisions you can correct before they become bugs.
Plan-first for anything non-trivial
For a one-line function, ask for the code directly. For anything larger — a feature, a multi-file change, a refactor — ask for a plan first.
A plan-first prompt ends with something like:
Before writing code, give me:
1. The files you'll create or change.
2. The approach for each acceptance criterion.
3. Any assumptions or ambiguities you want me to resolve.
Wait for my go-ahead before implementing.
This costs you one extra round trip and saves you several. You catch a wrong approach when it is three bullet points, not when it is 300 lines across four files. It also surfaces ambiguity in your spec — if the agent's plan reveals it misread a criterion, that criterion was unclear, and you fix the spec.
A complete prompt, assembled
Here is all three layers together for the discount-code task from the last lesson.
## Context
I'm working in cart.ts in our checkout service. Discount codes and their
percentOff live in the existing CODES constant in that file. Errors elsewhere
in this file are returned as values, not thrown — match that style. This is
for a holiday promo, so keep it simple and shippable.
## Spec
Task: Apply a percentage discount code to the cart total.
Acceptance criteria:
- applyCode("SAVE10") reduces the subtotal by 10% and returns the new total.
- An unknown code returns the unchanged total and { applied: false }.
- A valid code returns { applied: true, code, percentOff }.
Edge cases:
- Empty/whitespace code -> treated as unknown, total unchanged.
- Code is case-insensitive.
- Only one code active; a second replaces the first.
Discount applies to subtotal before tax.
## Constraints & response
- Only modify cart.ts. No new dependencies. No speculative abstractions.
- Show me your plan (files, approach per criterion, assumptions) before
writing code. Wait for my go-ahead.
Compare this envelope to "add discount codes to cart.ts please." Same agent, same model, wildly different reliability. The structure is doing the work.
What not to include
Three things bloat a prompt without helping:
- The whole codebase. Name what is relevant; let the agent read the rest.
- Restating the obvious. The agent knows what a unit test is. Spend words on your requirements, not on tutorials.
- Aggressive over-instruction. Modern agents follow instructions closely. Piling on "CRITICAL: YOU MUST ALWAYS..." tends to backfire and cause overtriggering. State it once, plainly.
Practice in the playground
Open the prompt playground in this lesson and try this exercise. Take a tiny task you understand well — say, "a function that converts a list of {name, score} objects into a leaderboard string." First write the vague one-liner. Then rewrite it with the three layers: context (where it lives, what format you want), spec (criteria for ties, empty list, ordering), constraints (no dependencies, plan first). Notice how much more of your intent survives into the result.
Key Takeaways
- An effective agent prompt has three layers in order: context, spec, constraints.
- Context orients the agent — name the relevant files and the reason behind the task; let the agent read code itself.
- Drop the spec in verbatim with its headings; the structure helps the agent build a checklist.
- The constraint layer also defines the response shape — ask for assumptions and a plan.
- For anything non-trivial, ask for a plan before code; it catches wrong approaches and unclear specs cheaply.
- Do not bloat the prompt with the whole codebase, the obvious, or aggressive over-instruction.

