Guide
JSON schema output prompt examples for production
Structured outputs fail in boring ways: missing fields, wrong types, commentary wrapped around JSON, and silent inventing of enums. Production systems treat the model as a flaky serializer — the prompt states the contract, code validates it, and retries are budgeted. Below are patterns you can adapt. Pair with production system prompts and prompt engineering checklist.
Principles
- Schema in the prompt, validation in code — never trust parse success alone if business rules matter.
- One object shape per call when possible — unions and optional trees raise error rates.
- Show a minimal valid example — shorter than a lecture, clearer than adjectives.
- Say what to do when data is missing —
null, omit, or"UNKNOWN"— pick one. - Forbid prose wrappers — “Return ONLY a JSON object. No markdown fences unless required by the API channel.”
If your vendor offers native JSON/schema modes, use them and keep the prompt contract — defense in depth.
Pattern A: Extraction
TASK: Extract fields from CONTEXT into the schema.
RULES:
- Use null when absent; do not invent.
- dates: ISO-8601 date only (YYYY-MM-DD)
- Return ONLY JSON matching the schema.
SCHEMA:
{
"company": string|null,
"contact_email": string|null,
"renewal_date": string|null,
"arr_usd": number|null
}
CONTEXT:
""" ... """
Validate emails and date formats in code. On failure, retry once with the validator error message — then stop (backoff playbook).
Pattern B: Classification with allowed enums
TASK: Classify the ticket.
label MUST be one of: billing | outage | how_to | other
confidence: number from 0 to 1
rationale: <= 20 words, no PII
OUTPUT EXAMPLE:
{"label":"how_to","confidence":0.72,"rationale":"User asks where to reset MFA"}
Reject unknown labels in code even if the model “almost” matched. Do not expand enums in the prompt without versioning the consumer.
Pattern C: Tool arguments
When the model emits tool calls, mirror the tool schema in the system prompt and keep descriptions short. Bloated parameter descriptions burn tokens and drift from the real API (reduce prompt tokens).
Prefer:
- Exact parameter names from code
- Explicit required vs optional
- Examples of invalid calls the model must not invent
Pattern D: Batch items with a hard cap
Return {"items":[...]} with at most 10 items.
If more candidates exist, set "truncated": true and keep the 10 highest priority.
Each item: {"id": string, "title": string, "priority": 1|2|3}
Caps prevent 8k-token JSON blobs that time out parsers and inflate bills. Estimate size with the token estimator.
Validation loop (keep it short)
- Parse JSON (or vendor structured output)
- Validate against JSON Schema / Zod / equivalent
- If fail and retries remaining: send compact error (
"arr_usd must be number or null") — not the whole schema again - Else: fail the job, metric++ , dead-letter
Unbounded “fix your JSON” loops create cost incidents. Budget retries like any other LLM feature.
Anti-patterns
- Asking for “JSON or YAML, whatever you prefer”
- Embedding three conflicting examples
- Putting business essays inside the schema description
- Accepting markdown fences in some environments and not others without a normalizer
- Logging full payloads that contain PII at debug level forever
Prompt + code checklist
- Single primary schema versioned with the service
- Missing-data policy explicit
- Enum lists match code constants (generated if possible)
- Max depth / max array length stated
- Validator errors mapped to one retry then fail
- Token estimate updated when schema grows
- Cleaned prompts stored via prompt cleaner for review diffs
Minimal system-prompt fragment
You are a JSON-only encoder for service X.
Never include markdown fences or commentary.
Follow SCHEMA_v3 exactly. Unknown → null.
If CONTEXT lacks a required business fact, still return JSON with nulls;
do not ask questions in this mode.
Wire SCHEMA_v3 from the same source of truth as your validator. Prompts that drift from code are how production pages invent fields at 2 a.m.
Structured output is a contract. Write it small, validate it hard, and meter the retries — that combination beats another paragraph of “be careful with types.”
Worked mini-example: support triage
Input: a short ticket body in CONTEXT.
Desired output:
{
"label": "billing",
"confidence": 0.81,
"needs_human": true,
"reason_codes": ["refund_request"]
}
Production notes:
reason_codesmust be from a fixed list maintained in codeneeds_humanforced true when confidence < 0.6 in code, even if the model disagrees- Log schema_version with every stored prediction
This split — model proposes, code enforces policy — keeps prompts short and behavior testable.
Estimating tokens for schema-heavy prompts
Large schemas dominate system tokens. Practical tactics:
- Reference “SCHEMA_v3 identical to validator” and paste only a compact example in the prompt when native JSON mode binds the schema elsewhere
- Strip descriptions that duplicate TypeScript field names
- Measure with count tokens without an API key before adding another nested object
If schema growth is mandatory, re-forecast monthly cost with the token estimator the same week — do not wait for the invoice.
Hubs: All guides · Tools · Start here
Tool links point to free client-side utilities on this site. Third-party product links may be affiliates — affiliate disclosure.