Drizzle ORM is a TypeScript ORM that gives you full SQL power with type safety. Unlike Prisma, Drizzle generates SQL you can read, runs queries you can predict, and adds zero runtime overhead.
Why Drizzle?
- SQL-like syntax — if you know SQL, you know Drizzle
- Zero overhead — thin typed layer over SQL, no query engine
- Serverless-ready — works with D1, Turso, Neon, PlanetScale
- Drizzle Kit — migrations, studio, push — all built-in
Quick Start
npm install drizzle-orm postgres
npm install -D drizzle-kit
// schema.ts
import { pgTable, serial, text, integer, timestamp } from 'drizzle-orm/pg-core';
export const users = pgTable('users', {
id: serial('id').primaryKey(),
name: text('name').notNull(),
email: text('email').unique().notNull(),
age: integer('age'),
createdAt: timestamp('created_at').defaultNow(),
});
export const posts = pgTable('posts', {
id: serial('id').primaryKey(),
title: text('title').notNull(),
content: text('content'),
authorId: integer('author_id').references(() => users.id),
});
CRUD Operations
import { drizzle } from 'drizzle-orm/postgres-js';
import { eq, like, and, desc } from 'drizzle-orm';
import postgres from 'postgres';
import { users, posts } from './schema';
const client = postgres('postgresql://localhost:5432/mydb');
const db = drizzle(client);
// Insert
const newUser = await db.insert(users).values({
name: 'Alice',
email: 'alice@example.com',
age: 30,
}).returning();
// Select
const allUsers = await db.select().from(users);
const alice = await db.select().from(users).where(eq(users.email, 'alice@example.com'));
// Update
await db.update(users).set({ age: 31 }).where(eq(users.id, 1));
// Delete
await db.delete(users).where(eq(users.id, 1));
Joins
const usersWithPosts = await db
.select({
userName: users.name,
postTitle: posts.title,
})
.from(users)
.leftJoin(posts, eq(users.id, posts.authorId))
.where(like(users.name, '%Ali%'))
.orderBy(desc(posts.createdAt))
.limit(10);
Relations (Query API)
import { relations } from 'drizzle-orm';
export const usersRelations = relations(users, ({ many }) => ({
posts: many(posts),
}));
export const postsRelations = relations(posts, ({ one }) => ({
author: one(users, {
fields: [posts.authorId],
references: [users.id],
}),
}));
// Query with relations
const result = await db.query.users.findMany({
with: {
posts: true,
},
where: eq(users.age, 30),
});
Migrations
// drizzle.config.ts
export default {
schema: './schema.ts',
out: './drizzle',
dialect: 'postgresql',
dbCredentials: {
url: 'postgresql://localhost:5432/mydb',
},
};
npx drizzle-kit generate # Generate migration SQL
npx drizzle-kit migrate # Apply migrations
npx drizzle-kit push # Push schema directly
npx drizzle-kit studio # Visual database browser
Need to store scraped data? Check out my Apify actors for web scraping + database pipeline, or email spinov001@gmail.com for custom data solutions.
Drizzle or Prisma — which ORM do you use? Share below!
Top comments (0)