Fix production build failure: lazy Prisma client initialization
The Prisma client was constructed eagerly at module load, which called
new URL(process.env.DATABASE_URL!) during Next.js 16 "Collect page data".
When DATABASE_URL wasn't in the build environment (production), this threw
TypeError: Invalid URL { input: 'undefined' } and failed the build for
routes like /api/auth/forgot-password.
Use a Proxy to defer client construction until the first property access,
so build-time module evaluation no longer touches DATABASE_URL.
Made-with: Cursor
This commit is contained in:
parent
3e0a4458fe
commit
8ae013879b
1 changed files with 27 additions and 4 deletions
|
|
@ -6,8 +6,14 @@ const globalForPrisma = globalThis as unknown as {
|
|||
prisma: PrismaClient | undefined;
|
||||
};
|
||||
|
||||
function createPrismaClient() {
|
||||
const url = new URL(process.env.DATABASE_URL!);
|
||||
function createPrismaClient(): PrismaClient {
|
||||
const dbUrl = process.env.DATABASE_URL;
|
||||
if (!dbUrl) {
|
||||
throw new Error(
|
||||
"DATABASE_URL is not set. Prisma client cannot be initialized."
|
||||
);
|
||||
}
|
||||
const url = new URL(dbUrl);
|
||||
url.searchParams.delete("sslmode");
|
||||
const pool = new pg.Pool({
|
||||
connectionString: url.toString(),
|
||||
|
|
@ -18,6 +24,23 @@ function createPrismaClient() {
|
|||
return new PrismaClient({ adapter });
|
||||
}
|
||||
|
||||
export const prisma = globalForPrisma.prisma ?? createPrismaClient();
|
||||
function getPrismaClient(): PrismaClient {
|
||||
if (!globalForPrisma.prisma) {
|
||||
globalForPrisma.prisma = createPrismaClient();
|
||||
}
|
||||
return globalForPrisma.prisma;
|
||||
}
|
||||
|
||||
if (process.env.NODE_ENV !== "production") globalForPrisma.prisma = prisma;
|
||||
// Lazy proxy so that importing `prisma` does NOT construct the client
|
||||
// at module load. This lets Next.js collect page data during build even
|
||||
// if DATABASE_URL isn't present in the build environment.
|
||||
export const prisma = new Proxy({} as PrismaClient, {
|
||||
get(_target, prop, receiver) {
|
||||
const client = getPrismaClient();
|
||||
const value = Reflect.get(client, prop, receiver);
|
||||
return typeof value === "function" ? value.bind(client) : value;
|
||||
},
|
||||
has(_target, prop) {
|
||||
return Reflect.has(getPrismaClient(), prop);
|
||||
},
|
||||
}) as PrismaClient;
|
||||
|
|
|
|||
Loading…
Reference in a new issue