Prisma 中文文档 下载 App

生产环境部署:migrate deploy 与 CI/CD 集成

migrate dev vs migrate deploy

开发环境用 migrate dev,生产环境只用 migrate deploy。

migrate devmigrate deploy
目的生成新迁移 + 应用只应用已有的迁移
能否连接开发数据库✅ 是可以,但没必要
能否连接生产数据库⚠️ 不推荐✅ 应该
会读取 Schema 吗✅ 会(对比差异生成新迁移)❌ 不会(只看 migrations/ 目录)
会改数据库结构吗生成 + 应用只应用未执行的

migrate dev 不应该连接生产数据库——它有能力根据 Schema 变化生成新迁移并直接执行,而你不希望它在生产环境生成和应用新 SQL。生产数据库应该只执行 migrations/ 目录里已经在开发环境审阅和测试过的迁移文件。

标准生产部署流程

1. 开发环境:改 Schema → migrate dev --name xxx → git commit migrations/
2. CI 环境:拉代码 → npm ci → 运行 migrate deploy → 跑测试
3. 生产环境:拉代码 → npm ci → 运行 migrate deploy → 重启应用

迁移文件跟着代码一起提交到 Git。部署时只需要在应用启动前(或同时)执行 migrate deploy。

Vercel 部署示例

在 Vercel 的项目设置里:

  1. Build Command:保持默认(Next.js 通常是 next build)
  2. Output Directory:.next
  3. Pre-build Command(或在 Build Command 里加):npx prisma migrate deploy

或者在 Next.js 的 API Route 或 Middleware 里做启动时检查:

// src/lib/ensure-db.ts
// 服务器启动前跑一次
await prisma.$connect()
// 也可以自动部署迁移:
// await prisma.$migrate.deploy()  // 内部就是 migrate deploy

注意 Vercel 的 Serverless Functions 是无状态的、可能被并行调用。不要在每个函数实例启动时都跑 migrate deploy——应该通过 Vercel 的 Pre-build Command 或单独的 CI/CD 步骤执行一次。

Docker 部署

# Dockerfile 片段
FROM node:20-alpine

WORKDIR /app
COPY package*.json ./
RUN npm ci
COPY . .
RUN npx prisma generate
RUN npm run build

# 生产环境容器启动时
CMD ["sh", "-c", "npx prisma migrate deploy && npm start"]

--schema 参数指定路径

如果你的 schema.prisma 不在默认位置:

npx prisma migrate deploy --schema=./path/to/schema.prisma

迁移版本控制

migrate deploy 怎么知道哪些迁移已经应用过了?它在数据库里维护一张表 _prisma_migrations:

字段含义
migration_name迁移目录名
finished_at完成时间
rolled_back_at如果回滚了,回滚时间
started_at开始时间
checksummigration.sql 的 hash(防篡改)

每次 migrate deploy 都会:

  1. 列出 migrations/ 目录下的所有迁移
  2. 对比 _prisma_migrations 表,找出未应用的
  3. 按顺序执行,一个成功才下一个

如果某个迁移执行失败,后面的都不会执行,已执行的不会回滚(这与 Prisma 7 的"每个迁移独立事务"有关)。

部署前验证

npx prisma migrate status --env=production

确认生产数据库的迁移历史与本地一致、没有 pending 未应用的迁移再部署。