If you use Prisma, you already know it's a fantastic ORM with excellent developer experience. But there's a common friction point almost all of us hit when building real-world APIs: input validation and sanitization.
Prisma is strict. If a user passes an unknown field in a .create() or .update() payload (like an injected isAdmin: true), Prisma throws an error. So what do you do? You end up writing tedious mapping functions, picking fields manually, or writing massive Zod schemas by hand to validate and strip out the junk before it reaches Prisma.
What if your Prisma schema could just... do it all for you?
Enter Prisma Guard 🛡️.
What is Prisma Guard?
Prisma Guard is the ultimate Prisma companion designed to bridge the gap between database models and API validation. It does two main things:
- Runtime Protection (The Guard): A Prisma Client extension that silently strips unknown fields from your queries at runtime.
-
Schema Generation (The Magic): Automatically transforms your
.prismamodels into robust, decorated Zod schemas with complete type-safety.
It's completely zero-config out of the box (it even manages your .gitignore and Prettier formatting for generated files), but offers immense power for those who need custom validation logic.
✌️ Two Ways to Use It
Depending on your needs, you can use Prisma Guard in two modes.
Mode 1: Runtime Protection Only (The Quick Fix)
If you just want to stop Prisma from throwing errors when random fields are passed from the frontend, just add the extension to your client:
import { PrismaClient } from "@prisma/client";
import { prismaGuard } from "@explita/prisma-guard";
const prisma = new PrismaClient().$extends(prismaGuard());
// Any extra fields passed to 'data' will be silently stripped
await prisma.user.create({
data: {
email: "user@example.com",
poisonField: "will be removed", // Poof! Gone.
},
});
Mode 2: Full Validation & Schema Generation (Recommended)
This is where the real magic happens. By running npx prisma-guard, it reads your Prisma schema and generates perfect Zod schemas.
Your Prisma Schema:
model User {
id String @id @default(cuid())
email String @unique
password String
createdAt DateTime @default(now())
}
What you get:
export const UserCreateSchema = z.object({
email: z.string().trim().min(1, { message: "This field is required" }),
password: z.string().trim().min(1),
// id and createdAt are managed by Prisma defaults or omitted entirely depending on your config!
});
💎 Advanced Type Ergonomics & Dual Schemas
One of the biggest headaches with schema generation is that a "public" API schema shouldn't include sensitive internal database fields (like secretApiKey or tenantId).
Prisma Guard handles this beautifully by generating Dual Schemas for every model:
-
Public Schemas (
UserCreateSchema): Respects your omission rules. Perfect for API request validation. -
Scalar Schemas (
UserCreateScalarSchema): Includes every database field. Perfect for internal services and database operations.
It also exports a suite of ergonomic TypeScript types (UserCreate, UserUpdate, UserCreateRequired) so your service layers are always perfectly typed.
🎨 The Power of Decorators (and the v proxy)
Sometimes z.string() isn't enough. You need .email(), .min(8), or custom refinement logic. Prisma Guard lets you define this cleanly using triple-slash comments (///).
Instead of polluting your Prisma schema with massive strings of Zod code, Prisma Guard introduces the v proxy in a prisma-guard.config.js file:
// prisma-guard.config.js
import { defineConfig, v } from "@explita/prisma-guard";
export default defineConfig({
decorators: {
// Chain validations onto the inferred Prisma type
email: v.chain.email().trim().toLowerCase(),
// Completely override a type
strongPassword: v.string().min(12).regex(/[A-Z]/),
},
});
Then, you just use them in your Prisma schema!
model User {
id String @id
/// @zod.use(email)
email String
/// @zod.use(strongPassword)
password String
}
IDE Superpowers 🪄
No one likes typing out decorators from memory. Prisma Guard includes an incredible npx prisma-guard metadata --vscode command that automatically installs VS Code snippets for every Zod method. You literally get autocompletion inside your .prisma files!
⚡ Blazing Fast Performance
You might be thinking: "Doesn't a runtime guard slow down my queries?"
The answer is no. The runtime guard is designed for ultra-low latency. It uses strict $O(n)$ complexity (looping only over predefined schema fields instead of arbitrary user input), memoized whitelists, and hot-path early exits.
In benchmarks of 100,000 recursive sanitization iterations on a complex payload:
-
Total duration:
221.26ms -
Average per query:
2.21 microseconds(0.0022ms)
If your database query takes 10-50ms, adding 0.0022ms introduces virtually 0% overhead.
🚀 Get Started in 2 Minutes
Stop wasting time manually maintaining Zod schemas that drift out of sync with your database.
- Install the package:
npm install @explita/prisma-guard
- Initialize your config:
npx prisma-guard init
- Generate the magic:
npx prisma-guard
Check out the full documentation, advanced relation handling, and custom schema generation features on our GitHub Repository.
If Prisma Guard saves you time, I'd deeply appreciate a ⭐ on GitHub! Let me know what you think in the comments below. Happy coding! 🚀
Top comments (0)