部署:传统服务器、Serverless 与边缘
本教程共 54 篇 · 第 49 篇 · 更新于 2026-08-11 · 约 5 分钟阅读
本节目标:分清三种部署形态对 Prisma 的不同要求,掌握 Docker 部署、无服务器平台和边缘运行时的要点,学会部署前的迁移顺序。
三种部署形态
Prisma 官方把部署分成三类,每类的连接管理策略完全不同:
| 形态 | 运行方式 | 连接策略 | 典型平台 |
|---|---|---|---|
| 传统服务器 | Node.js 进程常驻,同时处理多请求 | 单例 Client + 连接池,一次建好长期复用 | 云主机、Kubernetes、Fly.io |
| 无服务器(Serverless) | 请求到达才启动函数,一个请求一个函数实例 | 每次冷启动建连接,必须用连接池 | Vercel、AWS Lambda、Netlify |
| 边缘(Edge) | 函数分布在全球靠近用户的区域 | 受限运行时,走 HTTP 驱动或托管服务 | Cloudflare Workers、Vercel Edge |
选型看流量形态:持续平稳的流量适合传统服务器;突发尖峰适合无服务器。边缘环境没有完整 Node.js API,直接连数据库(TCP)受限,通常搭配 Prisma Postgres 或 Accelerate。
Docker 多阶段构建
Docker 部署属于传统形态。多阶段构建让最终镜像只含运行产物,体积小、攻击面小:
FROM node:22-alpine AS builder
WORKDIR /app
COPY package.json package-lock.json ./
RUN npm ci
COPY . .
RUN npx prisma generate && npm run build
FROM node:22-alpine
WORKDIR /app
ENV NODE_ENV=production
COPY --from=builder /app/node_modules ./node_modules
COPY --from=builder /app/dist ./dist
COPY --from=builder /app/src/generated ./src/generated
COPY --from=builder /app/prisma ./prisma
COPY package.json ./
EXPOSE 3000
CMD ["sh", "-c", "npx prisma migrate deploy && node dist/server.js"]
关键顺序:migrate deploy 必须在应用启动之前。容器先建好表结构,应用进程再连库查询。
Note官方 Docker 指南的示例是 CommonJS
require写法,属 v6 残留。v7 是 ESM-only,package.json必须设"type": "module",代码用import。
生产环境只允许 migrate deploy。它只应用未执行的迁移,幂等、无交互提示。绝不能用 migrate dev——它检测到漂移会重置数据库,在生产是灾难。
Vercel 与 Netlify
这类平台的坑是依赖缓存。postinstall 钩子被缓存跳过,部署会带上过期的 Prisma Client。修复方法(二选一):
{
"scripts": {
"postinstall": "prisma generate"
}
}
或者在构建命令前手动拼上 prisma generate && next build。更完善的 CI 流程在构建脚本里加上迁移:
{
"scripts": {
"vercel-build": "prisma generate && prisma migrate deploy && next build"
}
}
Tip无服务器平台每个函数实例都会开连接,直连数据库很快耗尽连接上限。生产环境务必把
DATABASE_URL指向连接池(Accelerate、PgBouncer 或数据库自带的池化地址)。
Fly.io:传统形态的简单选项
Fly.io 部署 Node.js 长驻服务,体验接近传统服务器。核心命令就一条:
fly launch
它会自动识别项目、创建 fly.toml,应用启动命令里同样先跑 migrate deploy 再启动进程。连接管理按传统服务器处理:单例 Client 复用连接池即可,无需外部池化服务。
Cloudflare Workers 与 D1
Workers 是边缘运行时,两个特殊点:生成器要声明边缘运行时,且每个请求都要新建 Client(与长驻服务器相反):
generator client {
provider = "prisma-client"
runtime = "cloudflare"
output = "../src/generated/prisma"
}
// src/index.ts
import { PrismaClient } from "./generated/prisma/client";
import { PrismaD1 } from "@prisma/adapter-d1";
export default {
async fetch(request: Request, env: Env, ctx: ExecutionContext): Promise<Response> {
const prisma = new PrismaClient({ adapter: new PrismaD1(env.DB) });
const users = await prisma.user.findMany();
ctx.waitUntil(prisma.$disconnect());
return Response.json(users);
},
};
请求结束时显式 $disconnect() 释放资源,否则 Worker 可能内存耗尽。D1 是 Cloudflare 的 SQLite 数据库,Prisma Migrate 无法直接连它,迁移改用 migrate diff 生成 SQL、用 Wrangler 应用:
npx prisma migrate diff --from-empty --to-schema prisma/schema.prisma --script > prisma/migrations/0001_init.sql
npx wrangler d1 execute my-db --remote --file="./prisma/migrations/0001_init.sql"
连接传统 PostgreSQL 的 Workers 需要 nodejs_compat 兼容标志,或用 Prisma Postgres 的 HTTP 驱动绕开 TCP 限制。
多环境、备份与回滚
多环境管理遵循一环境一库:开发用本地 Docker,预览用分支数据库,预发布复刻生产结构,生产独立集群。每个环境单独配 DATABASE_URL。
备份看数据库服务商能力:快照备份(每日)+ 时间点恢复(PITR,持续归档 WAL)。定期做恢复演练,别等事故才发现备份不可用。
回滚遵循「前向修复优于回滚」:应用回滚直接重新部署旧镜像,但数据库要向前兼容(新迁移已应用的字段旧代码要能忽略);数据库变更出错时写一个新的修复迁移,而不是删掉已应用的迁移。恢复快照是最后手段,接受数据丢失。
参考来源
- Prisma 官方文档:Deploy Prisma ORM(部署范式总览)、Docker 指南、Cloudflare Workers/D1 指南
- Prisma 官方文档:Deploy to Vercel、Deploy to Fly.io
- Mapagam:Deploying Prisma Applications
- Tech Insider:Prisma ORM Tutorial(Docker 多阶段构建章节)