codez.guru

Why Use Zod with TypeScript

Zod is a TypeScript-first validation library that lets you:

  • Validate data at runtime (like req.body)
  • Automatically generate TypeScript types from schemas
  • Reduce duplication between validation and type declarations

Perfect for full-stack TypeScript projects.


Installing Zod

npm install zod

Creating and Using Schemas

import { z } from "zod";

const UserSchema = z.object({
  name: z.string(),
  age: z.number().min(18)
});

Now you can validate and parse input:

const result = UserSchema.safeParse(req.body);

if (!result.success) {
  return res.status(400).json(result.error);
}

const user = result.data;

Inferring Types from Zod Schemas

Use z.infer<typeof schema> to generate matching types:

type User = z.infer<typeof userschema>;

const createUser = (user: User) =&gt; {
  // fully typed, matches schema exactly
};

This ensures type and validation are always in sync.


Validating API Request Data

You can validate:

  • req.body
  • req.query
  • req.params

Example:

const QuerySchema = z.object({
  page: z.string().regex(/^d+$/)
});

const queryResult = QuerySchema.safeParse(req.query);

Reusable Middleware for Express

Create a custom middleware:

function validate(schema: z.ZodTypeAny) {
  return (req: Request, res: Response, next: NextFunction) =&gt; {
    const result = schema.safeParse(req.body);
    if (!result.success) {
      return res.status(400).json(result.error.flatten());
    }
    req.body = result.data;
    next();
  };
}

// Usage:
app.post("/users", validate(UserSchema), (req, res) =&gt; {
  const user = req.body; // now fully typed + validated
  res.status(201).json(user);
});

Summary

  • Zod is the ideal partner for TypeScript APIs
  • Define your schema once — and infer types automatically
  • Use .safeParse() for clean validation with no exceptions
  • Build reusable middleware to keep your Express routes clean

Next up: Lesson 19 – Integrating TypeScript with Zustand or Redux