Docker-Setup: App-Image (standalone), PostgreSQL-Dienst mit Auto-Import, Dev-Profil
This commit is contained in:
@@ -0,0 +1,11 @@
|
|||||||
|
node_modules
|
||||||
|
.next
|
||||||
|
.git
|
||||||
|
.claude
|
||||||
|
.env*
|
||||||
|
!.env.example
|
||||||
|
ZUGANGSDATEN.md
|
||||||
|
supabase/local
|
||||||
|
Dockerfile
|
||||||
|
docker-compose.yml
|
||||||
|
README.md
|
||||||
+41
@@ -0,0 +1,41 @@
|
|||||||
|
# =============================================================
|
||||||
|
# Next.js-App als eigenständiges Produktions-Image (Multi-Stage)
|
||||||
|
# Build: docker compose --env-file .env.local build
|
||||||
|
# =============================================================
|
||||||
|
|
||||||
|
# ---------- Abhängigkeiten ----------
|
||||||
|
FROM node:24-alpine AS deps
|
||||||
|
WORKDIR /app
|
||||||
|
COPY package.json package-lock.json ./
|
||||||
|
RUN npm ci
|
||||||
|
|
||||||
|
# ---------- Build ----------
|
||||||
|
FROM node:24-alpine AS builder
|
||||||
|
WORKDIR /app
|
||||||
|
COPY --from=deps /app/node_modules ./node_modules
|
||||||
|
COPY . .
|
||||||
|
|
||||||
|
# NEXT_PUBLIC_*-Variablen werden zur Build-Zeit ins Client-Bundle eingebacken
|
||||||
|
ARG NEXT_PUBLIC_SUPABASE_URL
|
||||||
|
ARG NEXT_PUBLIC_SUPABASE_ANON_KEY
|
||||||
|
ENV NEXT_PUBLIC_SUPABASE_URL=$NEXT_PUBLIC_SUPABASE_URL
|
||||||
|
ENV NEXT_PUBLIC_SUPABASE_ANON_KEY=$NEXT_PUBLIC_SUPABASE_ANON_KEY
|
||||||
|
|
||||||
|
RUN npm run build
|
||||||
|
|
||||||
|
# ---------- Runtime ----------
|
||||||
|
FROM node:24-alpine AS runner
|
||||||
|
WORKDIR /app
|
||||||
|
ENV NODE_ENV=production
|
||||||
|
ENV PORT=3000
|
||||||
|
ENV HOSTNAME=0.0.0.0
|
||||||
|
|
||||||
|
RUN addgroup -S nodejs && adduser -S nextjs -G nodejs
|
||||||
|
|
||||||
|
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
|
||||||
|
|
||||||
|
USER nextjs
|
||||||
|
EXPOSE 3000
|
||||||
|
CMD ["node", "server.js"]
|
||||||
@@ -38,14 +38,24 @@ scripts/ Hilfsskripte (DB-Migration, lokaler Sync)
|
|||||||
|
|
||||||
## Entwicklung
|
## Entwicklung
|
||||||
|
|
||||||
|
Voraussetzung in beiden Varianten: `.env.local` mit den Werten aus
|
||||||
|
`.env.example` (liegt lokal bereits vor und ist per `.gitignore` vom
|
||||||
|
Repo ausgeschlossen).
|
||||||
|
|
||||||
|
**Variante A – Docker (nichts vorinstallieren außer Docker):**
|
||||||
|
|
||||||
|
```bash
|
||||||
|
docker compose --env-file .env.local --profile dev up dev
|
||||||
|
# http://localhost:3000 (Hot-Reload, Quellcode wird gemountet)
|
||||||
|
```
|
||||||
|
|
||||||
|
**Variante B – lokal installiertes Node.js:**
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
npm install
|
npm install
|
||||||
npm run dev # http://localhost:3000
|
npm run dev # http://localhost:3000
|
||||||
```
|
```
|
||||||
|
|
||||||
Voraussetzung: `.env.local` mit den Werten aus `.env.example`
|
|
||||||
(liegt lokal bereits vor und ist per `.gitignore` vom Repo ausgeschlossen).
|
|
||||||
|
|
||||||
## Umgebungsvariablen (Live-Betrieb)
|
## Umgebungsvariablen (Live-Betrieb)
|
||||||
|
|
||||||
Beim Webserver/Hoster müssen genau diese drei Variablen hinterlegt werden
|
Beim Webserver/Hoster müssen genau diese drei Variablen hinterlegt werden
|
||||||
@@ -57,7 +67,16 @@ Beim Webserver/Hoster müssen genau diese drei Variablen hinterlegt werden
|
|||||||
| `NEXT_PUBLIC_SUPABASE_ANON_KEY` | Öffentlicher anon-Key (RLS schützt die Daten) | nein |
|
| `NEXT_PUBLIC_SUPABASE_ANON_KEY` | Öffentlicher anon-Key (RLS schützt die Daten) | nein |
|
||||||
| `SUPABASE_SERVICE_ROLE_KEY` | Service-Role-Key für die Benutzerverwaltung | **ja – niemals im Browser/Repo!** |
|
| `SUPABASE_SERVICE_ROLE_KEY` | Service-Role-Key für die Benutzerverwaltung | **ja – niemals im Browser/Repo!** |
|
||||||
|
|
||||||
Build & Start auf dem Server:
|
Build & Start auf dem Server – **mit Docker** (empfohlen, Node.js und
|
||||||
|
PostgreSQL müssen nicht installiert sein):
|
||||||
|
|
||||||
|
```bash
|
||||||
|
docker compose --env-file .env.local up -d --build
|
||||||
|
# App: Port 3000 (hinter Reverse-Proxy mit HTTPS betreiben)
|
||||||
|
# Lokale DB-Kopie: Port 5432 (Dienst "db", optional)
|
||||||
|
```
|
||||||
|
|
||||||
|
Oder klassisch ohne Docker:
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
npm ci
|
npm ci
|
||||||
@@ -97,9 +116,15 @@ Sicherheitsmodell (Row Level Security):
|
|||||||
|
|
||||||
### Lokale PostgreSQL-Kopie
|
### Lokale PostgreSQL-Kopie
|
||||||
|
|
||||||
Auf dem Entwicklungsrechner läuft PostgreSQL 17 mit der Datenbank
|
Die Datenbank `speisekarte` (Kopie von Schema + Daten aus Supabase, inkl.
|
||||||
`speisekarte` (Kopie von Schema + Daten aus Supabase, inkl. Minimal-Stubs
|
Minimal-Stubs für `auth`/`storage`) gibt es in zwei Varianten:
|
||||||
für `auth`/`storage`). Neu aufbauen bzw. aktualisieren:
|
|
||||||
|
**Per Docker:** Der Dienst `db` aus `docker-compose.yml` spielt die
|
||||||
|
Skripte aus `supabase/local/` beim ersten Start automatisch ein
|
||||||
|
(PostgreSQL 17, Port 5432, Passwort über `LOCAL_PG_PASSWORD`).
|
||||||
|
|
||||||
|
**Nativ:** Auf dem Entwicklungsrechner läuft PostgreSQL 17 mit derselben
|
||||||
|
Datenbank. Neu aufbauen bzw. aktualisieren:
|
||||||
|
|
||||||
```powershell
|
```powershell
|
||||||
$env:SUPABASE_DB_PASSWORD = "<Supabase-DB-Passwort>"
|
$env:SUPABASE_DB_PASSWORD = "<Supabase-DB-Passwort>"
|
||||||
|
|||||||
@@ -0,0 +1,63 @@
|
|||||||
|
# =============================================================
|
||||||
|
# Speisekarte – Docker-Setup
|
||||||
|
#
|
||||||
|
# Produktion (App + lokale PostgreSQL-Kopie):
|
||||||
|
# docker compose --env-file .env.local up -d --build
|
||||||
|
#
|
||||||
|
# Entwicklung (Dev-Server mit Hot-Reload, kein lokales Node nötig):
|
||||||
|
# docker compose --env-file .env.local --profile dev up dev
|
||||||
|
#
|
||||||
|
# Die --env-file-Angabe speist NEXT_PUBLIC_* in den Build und
|
||||||
|
# SUPABASE_SERVICE_ROLE_KEY in die Laufzeit-Umgebung.
|
||||||
|
# =============================================================
|
||||||
|
|
||||||
|
services:
|
||||||
|
# ---------- Next.js-App (Produktions-Build) ----------
|
||||||
|
app:
|
||||||
|
build:
|
||||||
|
context: .
|
||||||
|
args:
|
||||||
|
NEXT_PUBLIC_SUPABASE_URL: ${NEXT_PUBLIC_SUPABASE_URL}
|
||||||
|
NEXT_PUBLIC_SUPABASE_ANON_KEY: ${NEXT_PUBLIC_SUPABASE_ANON_KEY}
|
||||||
|
environment:
|
||||||
|
NEXT_PUBLIC_SUPABASE_URL: ${NEXT_PUBLIC_SUPABASE_URL}
|
||||||
|
NEXT_PUBLIC_SUPABASE_ANON_KEY: ${NEXT_PUBLIC_SUPABASE_ANON_KEY}
|
||||||
|
SUPABASE_SERVICE_ROLE_KEY: ${SUPABASE_SERVICE_ROLE_KEY}
|
||||||
|
ports:
|
||||||
|
- "3000:3000"
|
||||||
|
restart: unless-stopped
|
||||||
|
|
||||||
|
# ---------- Lokale PostgreSQL-Kopie (Ablage/Auswertungen) ----------
|
||||||
|
# Beim ersten Start werden die Skripte aus supabase/local
|
||||||
|
# automatisch in alphabetischer Reihenfolge eingespielt.
|
||||||
|
db:
|
||||||
|
image: postgres:17-alpine
|
||||||
|
environment:
|
||||||
|
POSTGRES_DB: speisekarte
|
||||||
|
POSTGRES_PASSWORD: ${LOCAL_PG_PASSWORD:-speisekarte}
|
||||||
|
ports:
|
||||||
|
- "5432:5432"
|
||||||
|
volumes:
|
||||||
|
- pgdata:/var/lib/postgresql/data
|
||||||
|
- ./supabase/local:/docker-entrypoint-initdb.d:ro
|
||||||
|
restart: unless-stopped
|
||||||
|
|
||||||
|
# ---------- Dev-Server (nur mit --profile dev) ----------
|
||||||
|
dev:
|
||||||
|
image: node:24-alpine
|
||||||
|
profiles: ["dev"]
|
||||||
|
working_dir: /app
|
||||||
|
command: sh -c "npm install && npm run dev"
|
||||||
|
environment:
|
||||||
|
NEXT_PUBLIC_SUPABASE_URL: ${NEXT_PUBLIC_SUPABASE_URL}
|
||||||
|
NEXT_PUBLIC_SUPABASE_ANON_KEY: ${NEXT_PUBLIC_SUPABASE_ANON_KEY}
|
||||||
|
SUPABASE_SERVICE_ROLE_KEY: ${SUPABASE_SERVICE_ROLE_KEY}
|
||||||
|
ports:
|
||||||
|
- "3000:3000"
|
||||||
|
volumes:
|
||||||
|
- .:/app
|
||||||
|
- dev_node_modules:/app/node_modules
|
||||||
|
|
||||||
|
volumes:
|
||||||
|
pgdata:
|
||||||
|
dev_node_modules:
|
||||||
@@ -15,6 +15,8 @@ const securityHeaders = [
|
|||||||
];
|
];
|
||||||
|
|
||||||
const nextConfig: NextConfig = {
|
const nextConfig: NextConfig = {
|
||||||
|
// Für den Docker-Betrieb: minimales, eigenständiges Server-Bundle
|
||||||
|
output: "standalone",
|
||||||
async headers() {
|
async headers() {
|
||||||
return [
|
return [
|
||||||
{
|
{
|
||||||
|
|||||||
Reference in New Issue
Block a user