跳转到主要内容

升级到 Prisma ORM 6

从早期 Prisma ORM 版本升级时,Prisma ORM v6 引入了许多重大更改。本指南解释了此升级可能对你的应用程序产生的影响,并提供了关于如何处理任何更改的说明。

prisma@prisma/client 包升级到 v6

要从早期版本升级到 Prisma ORM v6,你需要更新 prisma@prisma/client

npm install @prisma/client@6
npm install -D prisma@6
危险

在升级之前,请查看下面的每个重大更改,以了解升级可能对你的应用程序产生的影响。

重大更改

本节概述了 Prisma ORM v6 中的重大更改。

最低支持的 Node.js 版本

Prisma ORM v6 的新最低支持 Node.js 版本为:

  • 对于 Node.js 18,最低支持版本为 **18.18.0**
  • 对于 Node.js 20,最低支持版本为 **20.9.0**
  • 对于 Node.js 22,最低支持版本为 **22.11.0**

正式支持 Node.js 16、17、19 和 21。

最低支持的 TypeScript 版本

Prisma ORM v6 的新最低支持 TypeScript 版本为:**5.1.0**。

信息

此模式更改仅适用于 PostgreSQL。
如果你正在使用 CockroachDB,则无需执行任何操作 — 隐式多对多关系模式保持不变。

PostgreSQL 上隐式多对多关系的模式更改

如果你正在使用 PostgreSQL 并在你的 Prisma 模式中定义隐式多对多关系,Prisma ORM 会在后台为你维护关系表。此关系表具有 AB 列,以表示属于此关系的模型的表。

Prisma ORM 的先前版本曾经在这两列上创建唯一索引。在 Prisma v6 中,为了简化默认副本标识行为,此唯一索引正在更改为主键。

展开以查看示例

例如,考虑以下 Prisma 模式,其中在 PostTag 模型之间具有隐式多对多关系

model Post {
id Int @id @default(autoincrement())
title String
categories Tag[]
}

model Tag {
id Int @id @default(autoincrement())
name String
posts Post[]
}

在这种情况下,Prisma ORM 在后台为你维护以下关系表

-- CreateTable
CREATE TABLE "_PostToTag" (
"A" INTEGER NOT NULL,
"B" INTEGER NOT NULL
);

-- CreateIndex
CREATE UNIQUE INDEX "_PostToTag_AB_unique" ON "_PostToTag"("A", "B");

-- CreateIndex
CREATE INDEX "_PostToTag_B_index" ON "_PostToTag"("B");

-- AddForeignKey
ALTER TABLE "_PostToTag" ADD CONSTRAINT "_PostToTag_A_fkey" FOREIGN KEY ("A") REFERENCES "Post"("id") ON DELETE CASCADE ON UPDATE CASCADE;

-- AddForeignKey
ALTER TABLE "_PostToTag" ADD CONSTRAINT "_PostToTag_B_fkey" FOREIGN KEY ("B") REFERENCES "Tag"("id") ON DELETE CASCADE ON UPDATE CASCADE;

在 Prisma v6 中,UNIQUE INDEX 正在更改为 PRIMARY KEY

-- CreateTable
CREATE TABLE "_PostToTag" (
"A" INTEGER NOT NULL,
"B" INTEGER NOT NULL,

CONSTRAINT "_PostToTag_AB_pkey" PRIMARY KEY ("A","B")
);

-- CreateIndex
CREATE INDEX "_PostToTag_B_index" ON "_PostToTag"("B");

-- AddForeignKey
ALTER TABLE "_PostToTag" ADD CONSTRAINT "_PostToTag_A_fkey" FOREIGN KEY ("A") REFERENCES "Post"("id") ON DELETE CASCADE ON UPDATE CASCADE;

-- AddForeignKey
ALTER TABLE "_PostToTag" ADD CONSTRAINT "_PostToTag_B_fkey" FOREIGN KEY ("B") REFERENCES "Tag"("id") ON DELETE CASCADE ON UPDATE CASCADE;

如果你在你的 Prisma 模式中定义了隐式多对多关系,你将创建的下一个迁移将包含 所有 属于这些关系的关系表的 ALTER TABLE 语句。这些语句将类似于这样

-- AlterTable
ALTER TABLE "_PostToTag" ADD CONSTRAINT "_PostToTag_AB_pkey" PRIMARY KEY ("A", "B");

-- DropIndex
DROP INDEX "_PostToTag_AB_unique";

为了隔离这些模式更改(并且不将它们与你的下一个迁移捆绑在一起),我们建议你在升级到 Prisma v6 之后立即创建一个新的迁移

npx prisma migrate dev --name upgrade-to-v6

这样,你就有了一个单独的专用迁移来处理此模式更改,否则可以保持你的迁移历史记录的清洁。

PostgreSQL 上的全文搜索

fullTextSearch 预览功能仅针对 MySQL 推广到正式可用。这意味着如果你正在使用 PostgreSQL 并且当前正在使用此预览功能,现在你需要使用新的 fullTextSearchPostgres 预览功能

之前

schema.prisma
datasource db {
provider = "postgresql"
url = env("DATABASE_URL")
}

generator client {
provider = "prisma-client-js"
previewFeatures = ["fullTextSearch"]
}

之后

schema.prisma
datasource db {
provider = "postgresql"
url = env("DATABASE_URL")
}

generator client {
provider = "prisma-client-js"
previewFeatures = ["fullTextSearchPostgres"]
}

Buffer 的用法

为了提高 Prisma 与新的现代 JavaScript 运行时之间的兼容性,我们正在逐步放弃使用 Node.js 特定的 API,转而使用标准 JavaScript。

Prisma v6 将使用 Buffer 替换为 Uint8Array 来表示类型为 Bytes 的字段。请确保将所有出现的 Buffer 类型替换为新的 Uint8Array

展开以查看如何在 BufferUint8Array 之间进行转换

BufferUint8Array 的转换

你可以直接将 Buffer 实例用作 Uint8Array

const buffer: Buffer = Buffer.from([1, 2, 3, 4]);
const uint8Array: Uint8Array = buffer; // No conversion needed

Uint8ArrayBuffer 的转换

你可以使用 Buffer.fromUint8Array 创建 Buffer

const uint8Array: Uint8Array = new Uint8Array([1, 2, 3, 4]);
const buffer: Buffer = Buffer.from(uint8Array.buffer);

之前

import { PrismaClient } from '@prisma/client'

async function main() {
const prisma = new PrismaClient()
await prisma.user.deleteMany()

const bytesCreated = await prisma.user.create({
data: {
bytes: Buffer.from([1, 2, 3, 4]),
},
})
// ^^^^^^^^^^^^^^^^^^^^^^^^^^
// `bytesCreated` used to have type: {
// bytes: Buffer
// id: number
// }

for (const bytesFound of await prisma.user.findMany()) {
bytesFound.bytes // Buffer [ 1, 2, 3, 4 ]
}
}

main()

之后

import { PrismaClient } from '@prisma/client'

async function main() {
const prisma = new PrismaClient()
await prisma.user.deleteMany()

const bytesCreated = await prisma.user.create({
data: {
bytes: Uint8Array.from([1, 2, 3, 4]),
},
})
// ^^^^^^^^^^^^^^^^^^^^^^^^^^
// `bytesCreated` now has type: {
// bytes: Uint8Array
// id: number
// }

for (const bytesFound of await prisma.user.findMany()) {
bytesFound.bytes // Uint8Array [ 1, 2, 3, 4 ]
}
}

main()

删除了 NotFoundError

在 Prisma v6 中,我们移除了 NotFoundError,转而使用带有错误代码 P2025PrismaClientKnownRequestError,该错误代码会在 findUniqueOrThrow()findFirstOrThrow() 中抛出。如果你的代码依赖于捕获 NotFoundError 实例,你需要相应地调整代码。

之前

import { PrismaClient, NotFoundError } from '@prisma/client';

// inside an `async` function
try {
const user = await prisma.user.findUniqueOrThrow({
where: { id: 42 },
});
console.log(user);
} catch (error) {
if (error instanceof NotFoundError) {
console.error("User not found!");
}
else {
console.error("Unexpected error:", error);
}
}

之后

import { PrismaClient, Prisma } from '@prisma/client';

// inside an `async` function
try {
const user = await prisma.user.findUniqueOrThrow({
where: { id: 42 },
});
console.log(user);
} catch (error) {
if (
error instanceof Prisma.PrismaClientKnownRequestError &&
error.code === 'P2025' // Specific code for "record not found"
) {
console.error("User not found!");
}
else {
console.error("Unexpected error:", error);
}
}

新的关键字不能用作模型名称:async, await, using

在此版本中,你不能再使用 asyncawaitusing 作为模型名称。

预览功能升级为正式版

在此版本中,我们将多个 预览 功能升级为 正式版

fullTextIndex

如果你的应用使用了 全文索引 功能,现在可以从 Prisma schema 中的 previewFeatures 中移除 fullTextIndex

generator client {
provider = "prisma-client-js"
previewFeatures = ["fullTextIndex"]
}

fullTextSearch

如果你的应用在 MySQL 中使用了 全文搜索 功能,现在可以从 Prisma schema 中的 previewFeatures 中移除 fullTextSearch

generator client {
provider = "prisma-client-js"
previewFeatures = ["fullTextSearch"]
}

如果你在 PostgreSQL 中使用它,你需要将功能标志的名称更新为 fullTextSearchPostgres

generator client {
provider = "prisma-client-js"
previewFeatures = ["fullTextSearchPostgres"]
}