Nest
Nest

How to use Zod with NestJS pipes for runtime schemas?

March 18, 2026

NestJS integrates Zod via custom pipes that parse/validate incoming data against schemas at runtime, providing client-bundleable validation separate from TypeScript types. Create ZodValidationPipe using zod.toParsedSchema() for transformation; ZodPipe handles safeParse/coercion. Apply via @Body(new ZodPipe(schema)) in controllers for automatic validation with detailed ZodError responses. Combines inference (z.infer<typeof schema>) for typesafety with tree-shakable bundles; outperforms class-validator for frontend reuse. Supports async parsing and custom error maps for i18n.

Example:

Step 1: Install & Schema

Code

npm i zod class-transformer @nestjs/class-validator
      

Step 2: ZodPipe (Custom Pipe)

Code

// pipes/zod.pipe.ts
import { PipeTransform, Injectable, ArgumentMetadata, BadRequestException } from '@nestjs/common';
import { ZodSchema, ZodError } from 'zod';
import { plainToClass } from 'class-transformer';

@Injectable()
export class ZodPipe<T> implements PipeTransform {
  constructor(private schema: ZodSchema<T>) {}

  transform(value: any, metadata: ArgumentMetadata) {
    const result = this.schema.safeParse(value);
    if (!result.success) {
      throw new BadRequestException('Validation failed', result.error.flatten());
    }
    return plainToClass(Object, result.data);  // Optional: DTO transform
  }
}
      

Step 3: Controller Usage

Code

// dto/create-user.dto.ts
import { z } from 'zod';
export const createUserSchema = z.object({
  email: z.string().email('Invalid email'),
  name: z.string().min(2).max(50),
  age: z.coerce.number().min(18)
});
export type CreateUserDto = z.infer<typeof createUserSchema>;

// user.controller.ts
import { Body, Post, UsePipes } from '@nestjs/common';
import { ZodPipe } from '../pipes/zod.pipe';
import { createUserSchema, CreateUserDto } from './dto/create-user.dto';

@Controller('users')
export class UserController {
  @Post()
  @UsePipes(new ZodPipe(createUserSchema))
  create(@Body() body: CreateUserDto) {  // Typed automatically
    return { id: 1, ...body };
  }
}
      
Hire Now!

Need Help with Nest Development ?

Ready to leverage the power of conversational AI? Start your project with Zignuts expert AI developers.
bg-image
download-image
Company Deck
PDF, 3MB
© 2026 Zignuts Technolab. All Rights Reserved.
branch imagesbranch imagesbranch imagesbranch imagesbranch imagesbranch images