主题
概述
Prisma 是下一代 Node.js 和 TypeScript ORM。它通过声明式的 Schema 定义和自动生成的类型安全客户端,让数据库操作变得简单、安全、高效。
适用后端框架
| 框架 | 支持状态 |
|---|---|
| NestJS NestJS | ✅ 完全支持 |
| Express Express | ✅ 完全支持 |
技术特性
| 特性 | 说明 |
|---|---|
| 类型安全 | 完整的 TypeScript 类型自动生成 |
| 数据库支持 | PostgreSQL, MySQL, SQLite, MongoDB, SQL Server |
| 迁移方式 | 声明式 Schema + 自动迁移 |
| 关系处理 | 自动处理外键和关联查询 |
| 可视化工具 | Prisma Studio 数据管理 |
Schema 定义
Prisma 使用 .prisma 文件定义数据模型:
schema.prisma
prisma
datasource db {
provider = "postgresql" // sqlite, mysql, postgresql
url = env("DATABASE_URL")
}
generator client {
provider = "prisma-client-js"
}
model User {
id String @id @default(cuid())
email String @unique
name String?
password String
role Role @default(USER)
posts Post[]
createdAt DateTime @default(now())
updatedAt DateTime @updatedAt
@@map("users")
}
model Post {
id String @id @default(cuid())
title String
content String?
published Boolean @default(false)
author User @relation(fields: [authorId], references: [id])
authorId String
createdAt DateTime @default(now())
@@index([authorId])
@@map("posts")
}
enum Role {
USER
ADMIN
}常用命令
bash
$
pnpm prisma migrate dev --name init
创建并应用数据库迁移。
bash
$
pnpm prisma generate
重新生成 Prisma Client(Schema 变更后需要执行)。
bash
$
pnpm prisma studio
打开可视化数据库管理界面。
bash
$
pnpm prisma db push
快速同步 Schema 到数据库(不创建迁移文件,适合开发阶段)。
CRUD 操作
基础 CRUD
typescript
import { PrismaClient } from '@prisma/client'
const prisma = new PrismaClient()
// 创建
const user = await prisma.user.create({
data: { email: 'test@example.com', name: 'Test' },
})
// 查询单个
const user = await prisma.user.findUnique({
where: { id: 'user-id' },
})
// 查询列表
const users = await prisma.user.findMany({
where: { role: 'USER' },
orderBy: { createdAt: 'desc' },
take: 10,
skip: 0,
})
// 更新
const user = await prisma.user.update({
where: { id: 'user-id' },
data: { name: 'New Name' },
})
// 删除
await prisma.user.delete({
where: { id: 'user-id' },
})关联查询
关联查询
typescript
// 查询用户及其文章
const userWithPosts = await prisma.user.findUnique({
where: { id: 'user-id' },
include: {
posts: true,
},
})
// 只查询部分字段
const user = await prisma.user.findUnique({
where: { id: 'user-id' },
select: {
id: true,
name: true,
posts: {
select: { title: true },
where: { published: true },
},
},
})
// 嵌套创建
const user = await prisma.user.create({
data: {
email: 'author@example.com',
name: 'Author',
posts: {
create: [
{ title: 'First Post' },
{ title: 'Second Post' },
],
},
},
include: { posts: true },
})事务处理
事务
typescript
// 交互式事务
const result = await prisma.$transaction(async (tx) => {
const user = await tx.user.create({
data: { email: 'new@example.com', name: 'New User' },
})
await tx.post.create({
data: { title: 'Welcome', authorId: user.id },
})
return user
})
// 批量操作事务
await prisma.$transaction([
prisma.post.deleteMany({ where: { authorId: 'user-id' } }),
prisma.user.delete({ where: { id: 'user-id' } }),
])数据库连接配置
.env
bash
# SQLite(开发环境推荐)
DATABASE_URL="file:./dev.db"
# PostgreSQL(生产环境推荐)
DATABASE_URL="postgresql://user:password@localhost:5432/mydb?schema=public"
# MySQL
DATABASE_URL="mysql://user:password@localhost:3306/mydb"NestJS 集成
prisma.service.ts
typescript
import { Injectable, OnModuleInit, OnModuleDestroy } from '@nestjs/common'
import { PrismaClient } from '@prisma/client'
@Injectable()
export class PrismaService extends PrismaClient implements OnModuleInit, OnModuleDestroy {
async onModuleInit() {
await this.$connect()
}
async onModuleDestroy() {
await this.$disconnect()
}
}prisma.module.ts
typescript
import { Global, Module } from '@nestjs/common'
import { PrismaService } from './prisma.service'
@Global()
@Module({
providers: [PrismaService],
exports: [PrismaService],
})
export class PrismaModule {}最佳实践
开发建议
- 使用 select/include:只查询需要的字段,避免过度获取
- 添加索引:为常用查询条件添加
@@index - 事务处理:关联操作使用事务保证一致性
- 软删除:添加
deletedAt字段实现软删除 - 生产迁移:使用
prisma migrate deploy而非migrate dev