fix(ci): hoisted node_modules + alpine binary target for Prisma in Docker
All checks were successful
Build and Deploy / build-and-deploy (push) Successful in 5m45s
All checks were successful
Build and Deploy / build-and-deploy (push) Successful in 5m45s
Root cause (from build log): 1. Prisma 6 generates client into @prisma/client package dir (not .prisma/client) 2. pnpm default isolated linker puts everything in .pnpm/ store with symlinks at top-level — Docker COPY of @prisma followed broken/incomplete symlinks 3. node:22-alpine needs linux-musl-openssl-3.0.x engine binary Fixes: - .npmrc: node-linker=hoisted → flat node_modules, COPY behaves like npm - schema.prisma: add linux-musl-openssl-3.0.x to binaryTargets - Dockerfile: drop dead .prisma/client checks, copy only @prisma (where Prisma 6 actually writes the client) plus standalone output Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
parent
409c4c4b50
commit
7506372abd
3
.npmrc
Normal file
3
.npmrc
Normal file
@ -0,0 +1,3 @@
|
||||
# 让 pnpm 用扁平 node_modules,避免 .pnpm/ 软链结构导致 Docker COPY 断裂
|
||||
node-linker=hoisted
|
||||
auto-install-peers=true
|
||||
20
Dockerfile
20
Dockerfile
@ -7,14 +7,16 @@ WORKDIR /app
|
||||
RUN corepack enable && corepack prepare pnpm@latest --activate \
|
||||
&& pnpm config set registry https://registry.npmmirror.com
|
||||
|
||||
COPY package.json pnpm-lock.yaml pnpm-workspace.yaml ./
|
||||
# .npmrc 必须先 COPY,否则 pnpm install 看不到 node-linker=hoisted
|
||||
COPY .npmrc package.json pnpm-lock.yaml pnpm-workspace.yaml ./
|
||||
COPY prisma ./prisma
|
||||
|
||||
# pnpm 10+ 在 root/CI 环境默认不跑 lifecycle scripts,因此显式调用 prisma generate
|
||||
# pnpm 10+ 在 root/CI 默认跳过 lifecycle scripts,因此显式调用 prisma generate
|
||||
# Prisma 6 直接把 client 写入 @prisma/client 包目录(不再用 .prisma/client)
|
||||
RUN pnpm install --frozen-lockfile --ignore-scripts \
|
||||
&& pnpm exec prisma generate \
|
||||
&& ls -la /app/node_modules/.prisma/client/ \
|
||||
&& ls -la /app/node_modules/@prisma/client/
|
||||
&& ls -la /app/node_modules/@prisma/client/ \
|
||||
&& ls /app/node_modules/@prisma/client/ | grep -E "(libquery_engine|schema.prisma|index.js)" || true
|
||||
|
||||
# ───────────── 2. builder:Next.js 构建(standalone 产物) ─────────────
|
||||
FROM node:22-alpine AS builder
|
||||
@ -27,10 +29,11 @@ COPY --from=deps /app/node_modules ./node_modules
|
||||
COPY . .
|
||||
|
||||
ENV NEXT_TELEMETRY_DISABLED=1
|
||||
# 再次保险生成(COPY . . 会覆盖 prisma/ schema 的最新版本),然后构建
|
||||
# COPY . . 会覆盖 prisma/schema 的最新版本,需要再 generate 一次确保 client 同步
|
||||
RUN pnpm exec prisma generate \
|
||||
&& pnpm exec next build \
|
||||
&& ls -la /app/node_modules/.prisma/client/
|
||||
&& ls -la /app/node_modules/@prisma/client/ \
|
||||
&& ls -la /app/.next/standalone/
|
||||
|
||||
# ───────────── 3. runner:最小运行时镜像 ─────────────
|
||||
FROM node:22-alpine AS runner
|
||||
@ -45,13 +48,12 @@ ENV HOSTNAME=0.0.0.0
|
||||
RUN addgroup --system --gid 1001 nodejs \
|
||||
&& adduser --system --uid 1001 nextjs
|
||||
|
||||
# Next.js standalone 输出 + 静态资源 + public
|
||||
# Next.js standalone 自带通过 tracing 解析出的运行时依赖(含 @prisma/client)
|
||||
COPY --from=builder /app/public ./public
|
||||
COPY --from=builder --chown=nextjs:nodejs /app/.next/standalone ./
|
||||
COPY --from=builder --chown=nextjs:nodejs /app/.next/static ./.next/static
|
||||
|
||||
# Prisma:生成的 client + schema(运行时 db:push / 迁移可能用到)
|
||||
COPY --from=builder --chown=nextjs:nodejs /app/node_modules/.prisma ./node_modules/.prisma
|
||||
# 显式补 Prisma:tracing 有时会漏掉 engine 二进制和 schema
|
||||
COPY --from=builder --chown=nextjs:nodejs /app/node_modules/@prisma ./node_modules/@prisma
|
||||
COPY --from=builder --chown=nextjs:nodejs /app/prisma ./prisma
|
||||
|
||||
|
||||
@ -5,6 +5,9 @@
|
||||
|
||||
generator client {
|
||||
provider = "prisma-client-js"
|
||||
// native:本地开发(macOS / linux-glibc)
|
||||
// linux-musl-openssl-3.0.x:容器运行时(node:22-alpine)
|
||||
binaryTargets = ["native", "linux-musl-openssl-3.0.x"]
|
||||
}
|
||||
|
||||
datasource db {
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user