<Task> in Smithers produces a structured output that is validated and persisted to SQLite. This guide explains the full validation flow, from schema definition through auto-retry on failure.
Schema-Driven Output
When you usecreateSmithers, each Zod schema becomes an output table. The agent must return JSON that matches the schema shape.
The outputSchema Prop
TheoutputSchema prop provides additional schema information to the agent. When your <Task> children are a React or MDX element, Smithers auto-injects a schema prop containing a JSON example derived from the Zod schema:
props.schema is a formatted JSON string the agent can reference:
outputSchema prop still participates in validation and cache key computation.
Validation Flow
When a task executes, Smithers validates the agent’s output through the following steps:- JSON extraction — The agent’s response is parsed for JSON. Smithers tries structured output first, then raw JSON, then code-fenced JSON blocks, and finally balanced-brace extraction. If no JSON is found, a follow-up prompt asks the agent to return just the JSON.
-
Auto-populated column stripping — Columns that Smithers manages automatically (
runId,nodeId,iteration) are stripped from the agent’s response before validation. This means the agent does not need to include these fields, and if it does include them, they are ignored. -
Schema validation — The extracted JSON is validated against the Zod schema (if
outputSchemais set) and against the Drizzle table schema (column types and nullability). -
Auto-retry on failure — If validation fails, Smithers sends up to 2 schema-retry prompts to the agent with the Zod error details appended. This gives the agent a chance to self-correct:
-
Persistence — On successful validation, the output is written to the SQLite table with
runId,nodeId, anditerationauto-populated.
Auto-Populated Columns
Every output table has three columns that Smithers manages:| Column | Type | Description |
|---|---|---|
runId | string | The current run’s ID |
nodeId | string | The task’s id prop |
iteration | integer | The current Ralph loop iteration (0 for non-loop tasks) |
- Auto-added to the table when using
createSmithers(you do not define them in your Zod schema). - Stripped from the agent’s response before validation. If the agent returns
{ "runId": "...", "summary": "..." }, therunIdis silently removed. - Auto-populated when the row is written to SQLite.
Agent Prompt Tips
Help the agent produce valid output by being explicit in your prompts:- List every field with its type and expected format.
- Use enum values explicitly (e.g.,
"low" | "medium" | "high"). - Specify array item shapes for nested objects.
- Include “or empty array” for optional array fields to avoid null responses.
- Ask for “ONLY the JSON object” to reduce extraneous text that complicates parsing.
Static Mode Validation
Tasks without anagent prop are static — the children value is written directly to the database. Static outputs are still validated against the table schema:
JSON Mode Columns
For columns that store arrays or complex objects, use Drizzle’s{ mode: "json" } option when working with the manual Drizzle API. With createSmithers, Zod arrays and objects are automatically stored as JSON text columns:
Combining Zod and Drizzle Schemas
When using the manual Drizzle API (withoutcreateSmithers), you can pair a Drizzle table with a Zod outputSchema for double validation:
outputSchema validates the JSON structure (including the risk range), and the Drizzle table validates column types and nullability.
Next Steps
- Error Handling — What happens when validation fails after all retries.
- Patterns — Schema organization conventions for larger projects.
- Data Model — Required columns and primary key conventions.