Zod | Typescript
- Zod | Typescript
📦 O que é o Zod?
Zod é uma biblioteca TypeScript-first para validação de esquemas (schemas). Permite validar e transformar dados com tipagem forte em tempo de desenvolvimento e em tempo de execução.
🛠️ Instalação
npm install zod
Ou com yarn:
yarn add zod
Não precisa de outras dependências.
✅ Validação Básica
String
import { z } from 'zod';
const nameSchema = z.string();
nameSchema.parse("João"); // ok
nameSchema.parse(123); // throws
Number
const ageSchema = z.number().min(18).max(99);
Boolean
const activeSchema = z.boolean();
Arrays
const tagsSchema = z.array(z.string());
Objetos
const userSchema = z.object({
name: z.string(),
age: z.number(),
});
🧩 Recursos Avançados
Valores opcionais
const userSchema = z.object({
name: z.string(),
age: z.number().optional(),
});
Valores com null
const nullableSchema = z.string().nullable(); // string ou null
Valores default
const schema = z.object({
role: z.string().default("user"),
});
União (OR)
info
Define que o tipo pode ser uma coisa ou outra
const schema = z.union([z.string(), z.number()]);
// const schema = z.string().or().number();
Interseção (AND)
const schema = z.intersection(
z.object({ id: z.string() }),
z.object({ name: z.string() })
);
🔁 Transformações
const trimmedString = z.string().transform((val) => val.trim());
🔎 Safe Parse
Evita exceções. Retorna { success, data | error }.
const result = schema.safeParse(data);
if (result.success) {
console.log(result.data);
} else {
console.error(result.error.errors);
}
🧪 Custom Validação (refine)
const passwordSchema = z.string().refine(val => val.length >= 8, {
message: "A senha deve ter no mínimo 8 caracteres",
});
📘 Exemplo completo
import { z } from 'zod';
const userSchema = z.object({
id: z.string().uuid(),
name: z.string().min(2),
email: z.string().email(),
age: z.number().int().min(18),
isAdmin: z.boolean().optional().default(false),
tags: z.array(z.string()).optional(),
});
type User = z.infer<typeof userSchema>;
const result = userSchema.safeParse({
id: "123e4567-e89b-12d3-a456-426614174000",
name: "Maria",
email: "maria@email.com",
age: 25,
});
if (result.success) {
const user: User = result.data;
console.log("Usuário válido:", user);
} else {
console.error("Erros:", result.error.format());
}
📚 Dicas Extras
z.infer<typeof schema>gera o tipo TypeScript automaticamente.- Use
schema.partial()para tornar todos os campos opcionais. - Combine com bibliotecas como React Hook Form ou tRPC para validação full-stack.
🔒 .strict()
strict() faz com que nenhuma chave extra seja permitida no objeto.
Se vier algo além do definido no schema, o Zod retorna erro.
Exemplo
import { z } from "zod";
const userSchema = z.object({
name: z.string(),
age: z.number(),
}).strict();
userSchema.parse({
name: "Ana",
age: 30
}); // OK
userSchema.parse({
name: "Ana",
age: 30,
extra: "não pode"
});
// ❌ throws: Unexpected key "extra"
🔓 .passthrough()
passthrough() permite chaves extras, e elas são incluídas no objeto final.
Exemplo
import { z } from "zod";
const userSchema = z.object({
name: z.string(),
age: z.number(),
}).passthrough();
const result = userSchema.parse({
name: "Ana",
age: 30,
extra: "permitido"
});
console.log(result);
// ✔ { name: 'Ana', age: 30, extra: 'permitido' }
Comparação rápida
| Modo | Comportamento | Exemplo |
|---|---|---|
| strict() | ❌ Rejeita chaves desconhecidas | { name, age, extra } → erro |
| passthrough() | ✔ Aceita e mantém chaves extras | { name, age, extra } → ok |
| strip() (default) | ✔ Aceita chaves extras, mas remove | { name, age, extra } → { name, age } |