跳至主要内容

将 Prisma ORM 与 Next.js 结合使用的综合指南

Prisma ORM 和 Next.js 结合使用,可以构建现代的服务器端渲染和 API 驱动的 Web 应用程序。 本指南整合了各种提示和策略,以帮助您最大限度地发挥它们的潜力。 无论您是在寻找最佳实践、单体仓库设置指南还是动态使用策略,我们都能满足您的需求。


在开发中使用 Prisma Client 的最佳实践

避免多个 Prisma Client 实例

在开发 Next.js 应用程序时,一个常见的问题是意外地创建了多个 Prisma Client 实例。 这通常是由于 Next.js 在开发中的热重载功能引起的。

为什么会发生这种情况

Next.js 的热重载功能会频繁重新加载模块,以立即反映代码更改。 但是,这可能导致创建多个 Prisma Client 实例,从而消耗资源并可能导致意外行为。

为了避免这种情况,请通过使用全局变量创建一个单独的 Prisma Client 实例

// lib/prisma.ts
import { PrismaClient } from "@prisma/client";

const globalForPrisma = global as unknown as { prisma: PrismaClient };

export const prisma =
globalForPrisma.prisma || new PrismaClient();

if (process.env.NODE_ENV !== "production") globalForPrisma.prisma = prisma;

使用这种方法可以确保即使在开发中进行热重载时,也只有一个 Prisma Client 实例存在。


在单体仓库中设置 Prisma ORM

在单体仓库中使用 Prisma ORM 的挑战

单体仓库允许多个项目共享代码和依赖项,这使它们成为现代开发的流行选择。 但是,在单体仓库中使用 Prisma ORM 可能会带来与依赖项解析和模式管理相关的挑战。

主要问题

  1. 依赖项解析:如果单体仓库中的多个包使用不同版本的 Prisma ORM,则可能会导致冲突。
  2. 模式集中化:跨多个项目管理单个 Prisma Schema 可能会很复杂。

单体仓库集成的最佳实践

  • 集中 Prisma Schema:将 schema.prisma 文件放在共享包中,例如 @myorg/db,以确保一致性。

  • 为生成的客户端使用自定义输出目录:为生成的 Prisma Client 定义自定义输出目录,以保持跨包的一致性。

  • 在根目录中安装依赖项:为防止版本冲突,请在单体仓库的根目录中安装 Prisma ORM。 如果单个包需要直接访问 Prisma(例如,用于本地客户端生成),请也在这些包中安装它。 您可以使用像 Turborepo 这样的单体仓库工具,遵循其最佳实践,或者采用类似的策略来保持应用程序中依赖项的同步。

  • 使用 NPM 脚本进行生成:

      {
    "scripts": {
    "prisma:generate": "prisma generate --schema=./packages/db/schema.prisma"
    }
    }

此方法使您的 Prisma Schema 和生成的客户端在单体仓库中的所有项目中保持同步。


在 Next.js 中动态使用 Prisma Client

处理动态场景

在使用 Prisma ORM 和 Next.js 时,动态用例(例如使用特定于租户的数据库)需要额外考虑。

问题

每个租户可能都有自己的数据库,因此需要在运行时创建单独的 Prisma Client。 由于 Next.js 的混合渲染模型,这可能很复杂。

解决方案

使用工厂函数基于特定于租户的配置动态创建 Prisma Client

// lib/prismaDynamic.ts
import { PrismaClient } from "@prisma/client";

type TenantConfig = {
databaseUrl: string;
};

export function createPrismaClient(config: TenantConfig): PrismaClient {
return new PrismaClient({
datasources: {
db: {
url: config.databaseUrl,
},
},
});
}

确保您管理动态创建的 Prisma Client 的生命周期,以避免资源耗尽。