Provides comprehensive Drizzle ORM patterns for schema definition, CRUD operations, relations, queries, transactions, and migrations. Proactively use for any Drizzle ORM development including defining database schemas, writing type-safe queries, implementing relations, managing transactions, and setting up migrations with Drizzle Kit. Supports PostgreSQL, MySQL, SQLite, MSSQL, and CockroachDB.
Expert guide for building type-safe database applications with Drizzle ORM. Covers schema definition, relations, queries, transactions, and migrations for all supported databases.
| Database | Table Function | Import |
|---|---|---|
| PostgreSQL | pgTable() | drizzle-orm/pg-core |
| MySQL | mysqlTable() |
drizzle-orm/mysql-core |
| SQLite | sqliteTable() | drizzle-orm/sqlite-core |
| MSSQL | mssqlTable() | drizzle-orm/mssql-core |
| Operation | Method | Example |
|---|---|---|
| Insert | db.insert() | db.insert(users).values({...}) |
| Select | db.select() | db.select().from(users).where(eq(...)) |
| Update | db.update() | db.update(users).set({...}).where(...) |
| Delete | db.delete() | db.delete(users).where(...) |
| Transaction | db.transaction() | db.transaction(async (tx) => {...}) |
relations() or defineRelations()import { pgTable, serial, text } from 'drizzle-orm/pg-core';
import { drizzle } from 'drizzle-orm/node-postgres';
import { eq } from 'drizzle-orm';
export const users = pgTable('users', {
id: serial('id').primaryKey(),
name: text('name').notNull(),
email: text('email').notNull().unique(),
});
const db = drizzle(process.env.DATABASE_URL);
const [user] = await db.select().from(users).where(eq(users.id, 1));
import { eq } from 'drizzle-orm';
// Insert
const [newUser] = await db.insert(users).values({
name: 'John',
email: '[email protected]',
}).returning();
// Update
await db.update(users)
.set({ name: 'John Updated' })
.where(eq(users.id, 1));
// Delete
await db.delete(users).where(eq(users.id, 1));
await db.transaction(async (tx) => {
const [from] = await tx.select().from(accounts)
.where(eq(accounts.userId, fromId));
if (from.balance < amount) {
tx.rollback();
}
await tx.update(accounts)
.set({ balance: sql`${accounts.balance} - ${amount}` })
.where(eq(accounts.userId, fromId));
});
See references/transactions.md for advanced transaction patterns.
$inferInsert / $inferSelectgenerate + migrate in production, push for developmentdeletedAt timestamp instead of hard deletes when possible.limit() and .where() to fetch only needed data() => table.column to avoid circular dependency issuestx.rollback() throws an exception - use try/catch if needed.returning() - check your dialect compatibility