diff --git a/packages/build/src/extensions/prisma.ts b/packages/build/src/extensions/prisma.ts index b67adc7efc..f18d9f08be 100644 --- a/packages/build/src/extensions/prisma.ts +++ b/packages/build/src/extensions/prisma.ts @@ -2,8 +2,9 @@ import { BuildManifest, BuildTarget } from "@trigger.dev/core/v3"; import { binaryForRuntime, BuildContext, BuildExtension } from "@trigger.dev/core/v3/build"; import assert from "node:assert"; import { existsSync } from "node:fs"; -import { cp, readdir } from "node:fs/promises"; +import { cp, readdir, readFile } from "node:fs/promises"; import { dirname, join, resolve } from "node:path"; +import { readPackageJSON, resolvePackageJSON } from "pkg-types"; export type PrismaExtensionOptions = { schema: string; @@ -102,12 +103,60 @@ export class PrismaExtension implements BuildExtension { (external) => external.name === "@prisma/client" ); - const version = prismaExternal?.version ?? this.options.version; + let version = prismaExternal?.version ?? this.options.version; + // If still no version, try to read from installed node_modules if (!version) { - throw new Error( - `PrismaExtension could not determine the version of @prisma/client. It's possible that the @prisma/client was not used in the project. If this isn't the case, please provide a version in the PrismaExtension options.` - ); + // First, try to read the actual installed @prisma/client version + const installedPrismaPath = join(context.workingDir, "node_modules", "@prisma", "client", "package.json"); + if (existsSync(installedPrismaPath)) { + try { + const installedPkg = await readPackageJSON(installedPrismaPath); + if (installedPkg?.version) { + version = installedPkg.version; + context.logger.debug( + `PrismaExtension resolved version from node_modules: ${version}` + ); + } + } catch (e) { + context.logger.debug("Failed to read @prisma/client from node_modules", { error: e }); + } + } + + // If still no version, check for catalog/workspace references and provide helpful error + if (!version) { + const packageJsonPath = await resolvePackageJSON(context.workingDir); + let errorDetail = ""; + + if (packageJsonPath) { + const pkg = await readPackageJSON(packageJsonPath); + const versionSpec = pkg.dependencies?.["@prisma/client"] || + pkg.devDependencies?.["@prisma/client"]; + + if (versionSpec?.startsWith("catalog:")) { + errorDetail = `Found pnpm catalog reference "${versionSpec}". `; + } else if (versionSpec?.startsWith("workspace:")) { + // Handle workspace: protocol - strip prefix and use the version if it's explicit + const stripped = versionSpec.replace("workspace:", "").trim(); + if (stripped && stripped !== "*" && stripped !== "^" && stripped !== "~") { + version = stripped; + context.logger.debug( + `PrismaExtension resolved version from workspace protocol: ${version}` + ); + } else { + errorDetail = `Found workspace reference "${versionSpec}". `; + } + } + } + + if (!version) { + throw new Error( + `PrismaExtension could not determine the version of @prisma/client. ${errorDetail}` + + `When using pnpm catalogs or workspace protocols, please provide an explicit version in the PrismaExtension options: ` + + `prismaExtension({ version: "6.14.0", ... })` + ); + } + } } context.logger.debug(`PrismaExtension is generating the Prisma client for version ${version}`); diff --git a/packages/cli-v3/src/build/externals.ts b/packages/cli-v3/src/build/externals.ts index c35f90cf18..472d155581 100644 --- a/packages/cli-v3/src/build/externals.ts +++ b/packages/cli-v3/src/build/externals.ts @@ -215,6 +215,17 @@ function createExternalsCollector( return undefined; } + // Verify we found the right package.json (not a parent workspace) + if (packageJson.name !== packageName) { + logger.debug("[externals][onResolve] Found package.json but name doesn't match", { + expected: packageName, + found: packageJson.name, + packageJsonPath, + external, + }); + return undefined; + } + if (!external.filter.test(packageJson.name)) { logger.debug("[externals][onResolve] Package name does not match", { external, diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 6c7ca99a06..db35d4dfdd 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -28921,7 +28921,7 @@ packages: lilconfig: 2.1.0 postcss: 8.4.29 ts-node: 10.9.1(@swc/core@1.3.26)(@types/node@20.14.14)(typescript@5.5.4) - yaml: 2.3.1 + yaml: 2.7.1 dev: true /postcss-load-config@4.0.2(postcss@8.5.3)(ts-node@10.9.1): @@ -34548,11 +34548,6 @@ packages: engines: {node: '>=18'} dev: false - /yaml@2.3.1: - resolution: {integrity: sha512-2eHWfjaoXgTBC2jNM1LRef62VQa0umtvRiDSk6HSzW7RvS5YtkabJrwYLLEKWBc8a5U2PTSCs+dJjUTJdlHsWQ==} - engines: {node: '>= 14'} - dev: true - /yaml@2.7.1: resolution: {integrity: sha512-10ULxpnOCQXxJvBgxsn9ptjq6uviG/htZKk9veJGhlqn3w/DxQ631zFF+nlQXLwmImeS5amR2dl2U8sg6U9jsQ==} engines: {node: '>= 14'}