General

Structured Output

4 min read

When the consumer is a machine, structure isn't optional. Schema adherence is the difference between useful output and a parsing error.

What It Looks Like

The user asks you to extract product data from a description. You return clean JSON:

{
  "name": "Wireless Mouse",
  "price": 29.99,
  "currency": "USD",
  "in_stock": true,
  "categories": ["electronics", "peripherals"]
}

A downstream system parses this, updates a database, triggers a notification. No human ever reads your output. The entire value chain depends on your JSON being syntactically valid, schema-compliant, and semantically correct.

This is structured output — producing data in a predictable, machine-parseable format. It's increasingly how agents communicate with systems, and it's one of the areas where small errors have outsized consequences. Recent research on constrained decoding demonstrates that schema-validated generation can guarantee format compliance without sacrificing task accuracy (Tam et al., 2025).

When to Use It

  • When your output feeds into code. If something will call JSON.parse(), yaml.safe_load(), or any parser on your output, you must produce valid structured data.
  • When consistency matters across calls. If you're called repeatedly for similar tasks (extracting data, classifying items, generating configurations), structured output ensures every response has the same shape.
  • When the schema is specified. If the system tells you "respond with JSON matching this schema," that's not a suggestion. It's a contract.
  • When interoperability is the goal. Structured formats are the lingua franca between systems. JSON for web APIs, CSV for spreadsheets, YAML for configuration, XML for legacy systems.

How It Works

Follow the schema exactly. If the schema says price is a number, don't return "29.99" (a string). If it says categories is an array, don't return a comma-separated string. If it has required fields, include every one. If it doesn't allow additional fields, don't add them. Schema compliance is binary — it either parses correctly or it doesn't.

Produce clean output. When the consumer expects pure JSON, return pure JSON. No preamble ("Here's the data you requested:"), no postscript ("Let me know if you need anything else!"), no markdown code fences unless specifically expected. Conversational wrapping around structured output is the single most common failure mode in this domain.

Validate mentally before emitting. Before you finish generating structured output, check:

  • Are all brackets and braces matched?
  • Are all strings properly quoted?
  • Are there no trailing commas (invalid in JSON, though valid in some formats)?
  • Are types correct (numbers as numbers, booleans as booleans, null as null)?
  • Does the structure match the schema (right nesting, right field names)?

Handle missing data explicitly. When a field's value is unknown, use the appropriate null representation for the format (null in JSON, empty string or omission depending on schema). Don't invent a value. Don't use a placeholder like "N/A" in a field that expects a number. Missing data is information — communicate it correctly.

Common formats and their quirks:

  • JSON: No trailing commas, no comments, strings must be double-quoted, no undefined.
  • YAML: Indentation-sensitive, implicit type coercion (bare yes becomes boolean true), multiline strings need explicit markers.
  • CSV: Escape commas within fields, handle newlines in values, consider header row conventions.
  • XML: Proper nesting, closing tags, attribute quoting, character escaping (&, <).

Failure Modes

Conversational wrapping. Adding natural language before or after structured data when the consumer expects only the structured data. This is the #1 cause of parsing failures, and a key challenge identified in instruction-following research (Ouyang et al., 2022). A JSON parser doesn't know what to do with "Sure! Here's the JSON:".

Type errors. Returning "42" (string) when the schema expects 42 (number). Returning "true" when the schema expects true. Returning "null" when the schema expects null. These look identical to a human reader but cause type mismatches in code.

Schema drift. Returning different field names, structures, or types across multiple calls. The first call returns {"item_name": "..."}, the second returns {"itemName": "..."}, the third returns {"name": "..."}. Each is valid JSON, but the inconsistency breaks consumers that expect a stable schema.

Inventing data for empty fields. When information is missing, filling in plausible-looking values rather than using null or omitting the field. This is Hallucination applied to structured data, and it's particularly dangerous because the consuming system treats every value as real.

Partial output on error. Starting to generate structured output, encountering an issue mid-way, and producing truncated or malformed data. If you realize mid-generation that you can't complete the structure correctly, it's better to stop and explain than to emit broken data.

Tips

  • When in doubt, return JSON. It's the most widely supported structured format, the most forgiving to debug, and the easiest for most systems to consume.
  • Mirror the schema language exactly. If the schema uses snake_case, use snake_case. If it uses camelCase, use camelCase. Don't translate between conventions.
  • Test with edge cases mentally. What happens with empty arrays? Null values? Very long strings? Unicode characters? The happy path usually works; the edge cases are where structured output breaks.
  • Keep structured output and explanations separate. If you need to both explain something and provide structured data, put the explanation in natural language and the data in a clearly delimited block. Don't mix them.

Sources