Skip to main content
Zod is the most common way to define schemas in TypeScript. The Vercel AI SDK accepts Zod schemas directly; no conversion step is needed.

Install

npm install zod ai @ai-sdk/openai

Basic usage

Pass a Zod schema to generateObject. The AI SDK converts it to JSON Schema and sends it to dottxt:
import { createOpenAI } from "@ai-sdk/openai";
import { generateObject } from "ai";
import { z } from "zod";

const dottxt = createOpenAI({
  baseURL: "https://api.dottxt.ai/v1",
  apiKey: process.env.DOTTXT_API_KEY!,
});

const { object } = await generateObject({
  model: dottxt.chat("openai/gpt-oss-20b"),
  schema: z.object({
    name: z.string(),
    email: z.string(),
    role: z.string(),
  }),
  prompt: "Extract: John Smith <john@acme.com>, VP Engineering",
});

console.log(object.name);  // "John Smith"
The AI SDK adds additionalProperties: false automatically when converting Zod schemas.

Adding constraints and descriptions

Zod’s built-in methods translate to JSON Schema keywords. .describe() adds field-level descriptions that guide generation:
const SupportTicket = z.object({
  category: z.enum(["billing", "account", "bug", "feature"])
    .describe("The area this ticket relates to."),
  priority: z.enum(["low", "medium", "high"])
    .describe("How urgently this ticket needs attention."),
  summary: z.string().min(10).max(500)
    .describe("A brief description of the issue."),
  confidence: z.number().min(0).max(1)
    .describe("How confident the model is in the classification."),
}).describe("A customer support ticket.");

const { object } = await generateObject({
  model: dottxt.chat("openai/gpt-oss-20b"),
  schema: SupportTicket,
  prompt: "Classify: I can't access my billing portal and it's blocking a renewal.",
});

Streaming

Use streamObject to receive partial results as tokens stream in:
import { streamObject } from "ai";

const { partialObjectStream } = streamObject({
  model: dottxt.chat("openai/gpt-oss-20b"),
  schema: z.object({
    title: z.string(),
    summary: z.string(),
    tags: z.array(z.string()).max(5),
  }),
  prompt: "Summarize: structured output improves LLM reliability...",
});

for await (const partial of partialObjectStream) {
  console.log(partial);
}

Notes

  • The AI SDK converts Zod schemas to JSON Schema before sending them to the API. To inspect the generated schema directly in Zod 4, use z.toJSONSchema():
console.log(JSON.stringify(z.toJSONSchema(SupportTicket), null, 2));