← Course home · Module 07 · Week 4

Prompting & Structured Output

D4 TS 4.1 · 4.2 · 4.3 · 4.4 · 4.5 · 4.6  ·  ~6 hrs  ·  Skip to quiz →

1 · From asking to specifying: the three levels

Warm-up · Loops

An overnight automation needs a definition of done it can check itself. What was that definition called, and what makes one good?

A finish line, and checkable is the whole job: "tests pass" beats "code is better" because software can verify one and only argue about the other. Hold that word. This module applies it to every output Claude hands you.

Warm-up · Tools

A tool gets picked correctly or incorrectly based on what evidence?

The name and description. The model never sees tool code, so the interface is the whole ballgame. This module runs the same logic in the other direction: what you write in the prompt is all the model has about what you want back.

▶ Watch: the same request at three levels · 3 min

Before you read

You ask Claude to summarize the same meeting twice, in two fresh sessions, with the same prompt. The two summaries come back organized differently. Is something broken?

No. A model generates fresh text every time, and an open ended prompt leaves the shape of the answer up to it. If the shape matters, the prompt has to say so. That is this module.

Consultants already know this problem from delegation. Tell a junior colleague "write up the vendor meeting" and you get their guess at what you wanted: maybe a narrative, maybe bullets, maybe two pages when you needed five lines. Hand the same person a template with five labeled boxes and you get the five boxes, filled in, every time. Nothing about their talent changed. The request changed.

Claude works the same way, and the same fix applies. Every request you make sits at one of three levels:

LevelWhat you provideWhat you get backWhen it is enough
The askA description of what you wantClaude's best guess at shape and contentOne-off work you will read and fix yourself
The specificationThe ask, plus explicit criteria the output must hitOutput that hits the criteria, checkable by eyeRepeated work a person reviews
The contractThe specification, plus a structure enforced by softwareOutput in an exact shape, validated, retried on failureWork another tool or person consumes without you in between

Each level costs more to set up and buys more consistency. The skill this module teaches is picking the level the work deserves, then writing it. You have been asking all course. The other two levels are the difference between work you fix and work you hand off, and the exam gives them a whole domain: 20 percent of the questions, six task statements, walking this exact ladder.

Quick check

A weekly report that your teammate reads and lightly edits before sending. Which level does that work deserve?

The specification. Repetition is what makes criteria worth writing down, and a human reviewer is the safety net that makes software enforcement unnecessary. The contract level earns its cost when the output feeds a tool or ships without review.

2 · Explicit criteria: the rubric the model can hit (TS 4.1)

Before you read

"Summarize this meeting" and "summarize this meeting in five bullets, each naming who committed to what by when" take the same effort to type. Why does the second one produce work you can forward?

Because it carries the definition of done. The first prompt makes Claude guess what a good summary is. The second states it, so the output can be checked against something.

An ask leaves quality undefined. A specification defines it, as criteria: statements about the output that are either met or not met. "Make it good" is not a criterion, because two people could disagree about whether it was hit. "Every bullet names an owner and a date" is a criterion, because nobody can disagree.

The same meeting note, at both levels:

> summarize the pbm renewal meeting note

The summary comes back readable and organized however Claude organized it. Some runs lead with the discussion, some with the decisions. Nothing is wrong, and nothing is dependable either.

> summarize the pbm renewal meeting note. criteria: five bullets or fewer.
  every bullet names who committed to what, with the date if one was said.
  anything unresolved goes under a separate "Open" heading. no other headings.

Now the output has a definition of done, and you can check it in ten seconds: count the bullets, scan for names and dates, look for exactly one extra heading. When a criterion is missed, you say which one, and the fix is one turn.

Is it a criterion? Judge each, then flip.

The discipline, in four rules:

Criteria name categories, never confidence levels. The exam grounds this in a scenario worth knowing on its own merits: automated review, where the output is a list of findings and the failure mode is false alarms. "Check that the comments are accurate" is the vague version. "Flag a comment only when the behavior it claims contradicts what the code actually does" is the criterion, and the difference is that the second names the exact category of finding to report. What does not work is turning adjectives into dials: "be conservative" and "only report high-confidence findings" fail to improve precision, because the model's confidence is not a setting you can adjust with a word. And false alarms are not cosmetic: when one category of finding cries wolf, readers stop trusting the accurate categories too. The working move when a category runs hot is to turn it off while its criteria get rewritten, which keeps the trustworthy categories trusted.

Why this earns its place in your week: criteria are reusable. Written once, they belong in a skill file, and every future summary comes back in the same shape without retyping a word. The specification is an asset, and the ask never is.

Quick check

Your extraction keeps inventing due dates for commitments that never had one. Which single criterion fixes it?

The third. It is the only one that names the exact case and the exact move. The other two are wishes, and the model was already trying to be accurate; what it lacked was a legal way to say "there is no date here."

3 · Show it examples: few-shot prompting (TS 4.2)

Before you read

You have described your status report format three times and the output still drifts. What is usually faster than describing it a fourth time?

Pasting in two finished examples and saying "match this format." Examples carry formatting decisions no description thinks to mention.

Few-shot prompting is the practice of including worked examples in the prompt. The name is jargon with a plain meaning: a "shot" is one example, so few-shot means showing a few. Instructions tell the model about the output. Examples show the output, and they carry a hundred small decisions (punctuation, tone, ordering, how dates get written, what gets left out) that instructions never think to state.

The everyday version, in your own repo:

> write this week's status update from my notes in 30 Meetings. match the
  format of these two exactly:

  WEEK OF AUG 11 · PBM RENEWAL
  Done: rate tables reconciled (owner: consulting team)
  Next: legal review of clause 7, due Aug 22
  Risk: vendor slow on data feed. escalated Aug 13.

  WEEK OF AUG 4 · PBM RENEWAL
  Done: kickoff complete, access granted
  Next: rate table reconciliation
  Risk: none this week

The description of that format would run a paragraph and still miss the middle dot in the header and the lowercase "due." The two examples carry all of it. On how many: the official prompting docs suggest three to five varied examples, and the exam guide's own numbers are two to four targeted ones. The honest rule underneath both: a few examples chosen to cover the cases that actually vary beat a pile of examples that all look alike.

Examples have a second job beyond format, and the exam leans on it: showing how to handle the ambiguous case. An example that demonstrates the borderline call, with a line of reasoning for why it went the way it went ("this is discussion, not a commitment, because nobody is named"), teaches judgment the model can generalize to cases you never showed it. And in extraction work, examples drawn from differently shaped source documents measurably cut both invented fields and empty ones, because the model has seen what each shape of input should produce.

Three rules keep examples working for you:

Quick check

Your instruction says "five bullets or fewer" but the example you pasted has seven bullets. What does the model do?

It picks, and you cannot count on which. Neither instructions nor examples reliably win a disagreement; the reliable move is making them agree before the prompt ships. Prompt drift that "comes from nowhere" very often comes from exactly this.

4 · The contract: structured output (TS 4.3)

Before you read

You need Claude's output to land in a tracking spreadsheet, so you add "please return the answer as JSON" to the prompt. Some runs come back perfect and some come back with an extra sentence of explanation before the data. What is the difference between asking for a format and enforcing one?

Asking is a request the model almost always honors. Enforcing means software checks the shape and malformed output cannot get through. When another program consumes the output, "almost always" is the problem.

Flagged as field experience: production teams across the industry report that prompt-only JSON fails somewhere between one run in twenty and one run in five: code fences around the data, a stray comma, a polite sentence in front. The fix that stuck is exactly this section's contract: a schema, a validator, and a retry that carries the error. One practitioner trick worth stealing while you are here: give the output a reasoning field ahead of the answer fields, so the model thinks before it fills in the form. Forcing the answer first measurably costs quality on hard extractions.

First, the words. JSON is a plain text format for structured data: labeled fields and their values, wrapped in braces. It is what software uses to hand data to other software, and one commitment from a meeting note looks like this in it:

{
  "commitment": "legal review of clause 7",
  "owner": "vendor counsel",
  "due": "2026-08-22",
  "source_note": "2026-08-11 pbm-renewal.md"
}

A schema is the written contract for that shape: which fields must exist, what type each holds, and whether extras are allowed. For the record above:

FieldTypeThe rule the schema enforces
commitmenttextMust be present, never empty
ownertextMust be present, never empty
duedate or "none stated"YYYY-MM-DD, or the literal words "none stated"
source_notetextMust name an actual file
No other fields allowed. A record missing any field, or carrying an extra one, fails the check by name.

A schema is checkable by software, which is the whole point: a program can look at a piece of JSON and say yes, this conforms, or no, and say exactly where it fails. Why a consultant cares: the moment output stops being read by you and starts being consumed by something else (a tracker, a spreadsheet, a dashboard, a next step in an automation), format failures stop being cosmetic. A missing field does not look wrong; it breaks whatever reads it, at whatever hour it reads it. The contract level exists for exactly that handoff.

In your own chair, the contract move is asking for output to land as a structured file with named columns, and stating the schema in plain words:

> extract every commitment from the notes in 30 Meetings into
  commitments.csv. columns: commitment, owner, due, source_note.
  every row must fill all four. if the note names no due date, write
  "none stated". no columns other than these four.

At the API level, which is what the exam asks about, the enforcement is mechanical. This block is exam material: your teammates will never touch it, and the exam tests it directly. Two routes exist, and the exam centers on the first:

Two boundaries the exam draws around this, both worth having straight:

One more control, exam-labeled: tool_choice sets how hard the platform pushes. "auto" lets the model answer in text or call a tool, "any" requires it to call some tool (which is how structured output gets guaranteed), and naming a specific tool forces exactly that one. And headless Claude Code runs speak the same language: claude -p with --output-format json returns the run's result as machine-readable JSON, and adding --json-schema with your schema puts a conforming answer in the result's structured_output field, ready for the next step in a pipeline.

Say it back

A teammate asks: "I already wrote 'please return JSON' in the prompt. Why isn't that enough for the dashboard feed?" Answer in two sentences, out loud or in the box, then compare.

Something like: "Please return JSON is a request, and the model honors it almost every time, but almost is what breaks a dashboard at 7am. Enforcement means software checks the output against a schema, so a malformed answer gets caught and retried instead of shipping." The load bearing idea: a request usually works; a contract is checked.

The one sentence version, and it maps this to something you already know: a schema does for output what a tool description does for input. It replaces "the model usually gets it right" with "the shape is checked."

5 · Trust, then verify: validation, retry, feedback (TS 4.4)

Before you read

An extraction run pulls forty commitments out of forty notes, and one of the forty due dates appears in no note anywhere. What kind of check catches that, given that the date is perfectly formatted?

A source check. Schema validation confirms the shape is right; only checking each claim against the note it came from confirms the content is real. The invented date passes the first check and fails the second.

A schema catches malformed output. It cannot catch fluent, well formed, wrong output: the plausible date that was never said, the owner who was in the meeting but made no commitment. Extraction quality needs a second kind of check, and a loop around both. Four stations:

1 · Extract criteria + examples + schema 2 · Validate shape: fits the schema? grounding: in the source? 3 · Retry, with the failure attached specific error, real correction 4 · Cap two or three tries, max Needs review · a person looks uncertain rows go here, never into the tracker
The loop. Station 2 has two gates because shape and truth are different checks. Everything that survives neither retry nor the cap lands in needs review, which is the safety property: uncertain rows have somewhere legal to go, so they stop showing up disguised as certain ones.

One judgment call sits inside station 3, and the exam tests it directly: knowing when a retry cannot help. A retry fixes what the model got wrong about information it has: format mistakes, structure mistakes, a value it misread. A retry cannot conjure information the source never contained. When the note states no date, no number of retries produces the date, and every attempt is a fresh invitation to invent one. Rows that fail because the information is absent skip the retry entirely and go straight to the flagged pile, marked as gaps rather than errors.

The strong version of the validation station asks the model to check itself in ways software can then verify: extract the stated total and compute the sum of the line items as separate fields, and a mismatch between them flags itself. A "conflict_detected" field does the same for sources that disagree. The pattern: design the output so that inconsistency has to show up as two fields that fail to match, because two fields that fail to match is something a check can catch mechanically.

Flagged as field experience: the most widely used extraction tooling in the industry ships this section's loop as its default behavior: validate against the schema, feed the named error back, cap the retries at three. And published reports of real extraction failures read like this section's checklist: invented values for fields the document never filled, relative dates quietly resolved into specific ones, commitments attributed to the wrong person. What this section teaches is the mainstream production architecture.

What this changes about your asks: you stop requesting extractions and start requesting extractions with their checks attached. One prompt shape covers it:

> extract the commitments per the tracker skill. then check every row
  against its source note and list any row you cannot support, with the
  reason. fix what you can, cap the fixes at two passes, and put anything
  still unsupported in a "needs review" section instead of the tracker.
Quick check

A row fails the grounding check. Which retry message gets a real correction?

The specific one. The retry message is the model's entire knowledge of what went wrong, exactly like a tool error: name what failed, why, and the legal moves. The other two messages buy you a fresh guess, which may fail differently.

6 · Scale: batch processing and the second pass (TS 4.5 · 4.6)

Before you read

Four hundred call transcripts need the same extraction. It is not urgent; you need it by Monday. What is wrong with feeding all four hundred into one session this afternoon?

One session means one context window carrying four hundred documents, and quality degrades as it fills. Independent items want independent processing, and non-urgent volume wants the batch lane, which costs half as much.

Batch processing means running the same operation over many items. Two decisions matter: how items are grouped, and which lane they run in.

Grouping. Independent items get independent runs. Forty notes through one extraction each beats one session holding all forty, because each run starts with a clean context window and one document's worth of attention, and one bad note fails alone instead of contaminating a shared session. You have seen this shape before: it is the same reason a subagent gets its own window. In your chair, the ask is plain:

> process each note in 30 Meetings separately: same tracker skill, one
  note at a time, appending each result to commitments.csv

The lane, which is exam material. The API has a dedicated batch lane, the Message Batches API: submit up to 100,000 requests as one batch, get results asynchronously within 24 hours (most far sooner), at half the price of the standard API. Each request in the batch carries a custom_id you choose, and results come back keyed by that id, in no particular order, so the id is how you match answers to inputs. The tradeoff is latency for cost: nothing about a batch is interactive.

The workThe laneWhy
Forty notes, results wanted nowA loop of independent runs in your sessionInteractive, you watch the trail
Four hundred transcripts by MondayMessage Batches APIHalf price, overnight is fine
One document, one answerA single askNo batch anything

The second pass (TS 4.6). Volume work adds a quality tool that single documents rarely need: another instance. Two patterns, both built on a fact you already know, that separate sessions share nothing:

Flagged as field experience: two honest findings worth carrying into client conversations. First, reviewers checking a yes-or-no criterion ("does every row trace to a source?") beat reviewers assigning 1-to-10 scores, because model-rated scores drift from run to run while a pass or fail holds still. Second, a controlled study of experienced developers found the group using AI assistance felt 20 percent faster and measured 19 percent slower. Feeling fast is not evidence. The check is the evidence, and that is the strongest argument anywhere in this course for the review pass.
Quick check

In a Message Batches run, results come back in a different order than you submitted. How do you match each answer to its input?

The custom_id. It exists for exactly this: batch results arrive in any order, so every request carries an id you chose, and answers come back wearing it. Matching by position is the classic batch bug.

Quick check

A single high-stakes contract clause needs extraction, and being wrong is very expensive. Which pattern fits?

Multi-instance. The cost of extra runs is trivial next to the cost of a wrong answer, and independent agreement is real evidence in a way one confident answer is not. The batch lane is about price, and price was never this question's problem.

7 · Case study: the commitments tracker

The five consultant team at the regional health plan had forty meeting notes and a recurring embarrassment: commitments made in meetings kept resurfacing late, because they lived in prose nobody reread. The fix they wanted was a tracker: every commitment, owner, and due date, in one file the whole team checked on Mondays.

The first attempt was an ask. "Go through the meeting notes and pull out the commitments into a table." The table came back, and it was different every week: columns appeared and disappeared, owners were sometimes people and sometimes departments, dates arrived in three formats, and one week the table politely included a "sentiment" column nobody asked for. Usable, with twenty minutes of cleanup, every single week.

The fix took one afternoon, and nobody touched the notes. The team changed two things: the request became a skill with criteria and two worked examples, and the output got a contract.

Before (the ask)After (in the skill)
"pull out the commitments"A commitment is a stated promise by a named person or party to do a specific thing. Discussion is not a commitment.
(column shape left to chance)Exactly four columns: commitment, owner, due, source_note.
(dates in any format)Dates as YYYY-MM-DD. A commitment with no stated date gets "none stated".
(owner sometimes a department)Owner is the most specific party named.

Two worked example rows went into the skill under the criteria, one with a date and one with "none stated", so both cases had a model to match.

Replay one note through both worlds. The August 11 note contains "vendor counsel will complete the legal review of clause 7 the week after next." The old world produced Legal review | Vendor | soon in whichever columns that week's table had. The new world produces one row: legal review of clause 7 | vendor counsel | none stated | 2026-08-11 pbm-renewal.md, and "none stated" is there because the note says "week after next," and the criteria forbid converting a relative phrase into an invented date.

The near miss

The first full run, before the validation pass was added, did exactly that conversion: one row carried due: 2026-08-25, a real looking date computed from "week after next." Play it forward a week to see what that row costs. The tracker goes to the client sponsor on Monday. The sponsor's team plans the clause 7 review around August 25. The vendor's counsel, who said "week after next" loosely and committed to nothing, hears about a deadline they never gave, in a document with the consulting firm's name on it. The conversation that follows is about whether the tracker can be trusted, which is the conversation that ends trackers.

What actually happened: the grounding pass ("find the sentence that supports each row") failed that row, it landed in the needs review pile, and a person changed it to "none stated" in thirty seconds. The team then wrote the rule into the skill: relative dates are never converted; they are quoted or marked.

What the working pipeline looks like now, start to finish: each Monday, one prompt runs the tracker skill over the week's notes, one note at a time. Every row carries its source. A grounding pass checks each row and routes failures to needs review, capped at two fix attempts. A second session, fresh window, reads the final tracker against the notes before it leaves the building. Twenty minutes of weekly cleanup became four, and the four are spent on flagged rows, which is where a person's judgment actually earns something.

Decision scenario

Friday, 4pm. The tracker is freshly built and the client sponsor asked for it today. A teammate says: "The extraction looked clean when I skimmed it. Send it now, run the validation passes Monday." Pick your move, then read what follows from it. Try all three.

The near miss, chosen on purpose. Skimming checks shape, and shape was never the risk; the invented date looked perfect in a skim. If one unsupported row is in there, it ships under your firm's name to the person planning around it. You saved one business day and bet the tracker's credibility on forty rows all being right the first time.
The professional move. The grounding pass takes minutes, not days. The client gets a tracker where every row is source-checked, plus an honest "under review" section, which reads as rigor rather than delay. This is the same discipline as the needs review pile, applied under deadline pressure, which is when it earns its keep.
Safe, and slower than it needed to be. Nothing bad ships, and something useful sits in a drawer all weekend. The validation pass is fast enough to run before sending; holding everything treats checked and unchecked rows the same, which undersells the work the pipeline already did.

8 · Watch it built, then run it yourself

▶ Watch the demo: the extraction pipeline · 4 min

The prompt pack: every demo prompt, cleaned and explained

The demo builds the commitments tracker in the second brain repo, from the user's chair, in three parts. Part one writes the contract: the tracker skill gets its criteria, its two worked examples, and the four column schema, all by one ask. Part two runs and validates: the extraction over the notes one at a time, the grounding pass catching one row whose date appears in no source, the specific retry message, and the row landing in needs review instead of the tracker. Part three proves it: a fresh session runs the whole pipeline on a new note, the tracker gains one source backed row, and the deliberately planted trap (a note with a vague date) lands in needs review instead of shipping.

Then run the pack in your own repo. The prompt pack linked above holds every prompt from the demo, cleaned up and explained. Copied as is or rephrased in your own words, check what the demo checked as you go:

9 · Wrap-up: what you should be able to do cold

Take the Module 07 quiz →  then hit the Study App for Domain 4 reps.