# syntax=docker/dockerfile:1 # --------------------------------------------------------------------------- # deps: vollstaendiger Abhaengigkeitsbaum, gemeinsam genutzt von "dev" und # "build". Bleibt auf dem vollen node-Image, weil better-sqlite3 beim # Installieren eine Toolchain braucht. # --------------------------------------------------------------------------- FROM node:24 AS deps WORKDIR /app COPY package*.json ./ RUN npm ci # --------------------------------------------------------------------------- # dev: Ziel fuer compose.dev.yaml. Behaelt devDependencies, damit tsx, # drizzle-kit und "next dev" verfuegbar sind. Die Quellen kommen zur Laufzeit # ueber Bind-Mounts, das COPY hier ist nur der Ausgangsstand. # --------------------------------------------------------------------------- FROM deps AS dev ENV NODE_ENV=development COPY . . RUN mkdir -p data EXPOSE 3000 3001 CMD ["npm", "run", "dev:api"] # --------------------------------------------------------------------------- # build: API nach dist/ und Frontend nach .next/ uebersetzen, danach die # devDependencies entfernen, damit das Laufzeit-Image nur noch traegt, was es # auch ausfuehrt. Die Migrationsskripte kommen mit drizzle-orm und # better-sqlite3 aus, beides sind regulaere dependencies. # --------------------------------------------------------------------------- FROM deps AS build ENV NEXT_TELEMETRY_DISABLED=1 # next build schreibt die Rewrite-Ziele aus next.config.mjs fest in # .next/routes-manifest.json, "next start" kann eine andere API-Adresse # spaeter nicht mehr uebernehmen. Der Wert muss hier bekannt sein, nicht erst # zur Laufzeit. Server-Komponenten lesen die Variable zur Laufzeit. ARG API_INTERNAL_URL=http://localhost:3000 ENV API_INTERNAL_URL=$API_INTERNAL_URL COPY . . RUN npm run build:api && npm run build:web RUN npm prune --omit=dev # --------------------------------------------------------------------------- # prod: Laufzeit-Image. node:24-slim teilt sich das Debian-Release mit der # build-Stufe, damit das kompilierte better-sqlite3-Binding ladbar bleibt. # Laeuft als "node" (UID 1000) statt als root. # --------------------------------------------------------------------------- FROM node:24-slim AS prod ENV NODE_ENV=production ENV NEXT_TELEMETRY_DISABLED=1 WORKDIR /app COPY --from=build --chown=node:node /app ./ RUN mkdir -p data && chown node:node data USER node EXPOSE 3000 3001 CMD ["node", "dist/server/index.js"]