chore(docker): .dockerignore angepasst; lokale Build-Schritte in Rebuild-Skripten; Doku/README zu production vs production-prebuilt aktualisiert
This commit is contained in:
181
docs/docker-build-stages.md
Normal file
181
docs/docker-build-stages.md
Normal file
@@ -0,0 +1,181 @@
|
||||
# Docker Build Stages
|
||||
|
||||
Das Dockerfile definiert drei Build-Stages für unterschiedliche Deployment-Szenarien.
|
||||
|
||||
## Stages Übersicht
|
||||
|
||||
### 1. `builder`
|
||||
**Zweck:** Baut sowohl Client als auch Server-Artefakte
|
||||
|
||||
**Verwendung:** Wird als Basis für `production` Stage verwendet
|
||||
|
||||
**Prozess:**
|
||||
- Installiert alle Dependencies (inkl. devDependencies)
|
||||
- Baut Client mit Vite (`dist/`)
|
||||
- Baut Server mit TypeScript (`server-dist/`)
|
||||
- Kompiliert native Module (bcrypt) für Alpine Linux
|
||||
|
||||
---
|
||||
|
||||
### 2. `production`
|
||||
**Zweck:** Vollständiger Build für Remote-Deployment (CI/CD, Production-Server)
|
||||
|
||||
**Verwendung:**
|
||||
```yaml
|
||||
# docker-compose-prod.yml
|
||||
build:
|
||||
context: .
|
||||
target: production
|
||||
```
|
||||
|
||||
**Prozess:**
|
||||
1. Kopiert Source-Code (Client + Server) in Container
|
||||
2. Baut Client mit Vite (`dist/`)
|
||||
3. Baut Server mit TypeScript (`server-dist/`)
|
||||
4. Installiert nur Production-Dependencies
|
||||
5. Kompiliert native Module (bcrypt) für Alpine Linux
|
||||
6. Verifiziert bcrypt Installation
|
||||
|
||||
**Vorteile:**
|
||||
- ✅ Vollständig autark (keine lokalen Builds nötig)
|
||||
- ✅ Reproduzierbare Builds
|
||||
- ✅ Ideal für CI/CD-Pipelines
|
||||
|
||||
**Nachteile:**
|
||||
- ⏱️ Längere Build-Zeit (Client + Server werden im Container gebaut)
|
||||
|
||||
---
|
||||
|
||||
### 3. `production-prebuilt`
|
||||
**Zweck:** Schnelles lokales Testing mit vorgebauten Artefakten
|
||||
|
||||
**Verwendung:**
|
||||
```yaml
|
||||
# docker-compose.yml (lokal)
|
||||
build:
|
||||
context: .
|
||||
target: production-prebuilt
|
||||
```
|
||||
|
||||
**Voraussetzungen:**
|
||||
- `dist/` und `server-dist/` müssen bereits existieren
|
||||
- `.dockerignore` darf diese Verzeichnisse NICHT ausschließen
|
||||
- Lokal ausführen: `pnpm run build` vor `docker compose build/up`
|
||||
|
||||
**Prozess:**
|
||||
1. Kopiert vorgebaute `dist/` und `server-dist/` aus Build-Context
|
||||
2. Installiert nur Production-Dependencies
|
||||
3. Kompiliert native Module (bcrypt) für Alpine Linux
|
||||
4. Verifiziert bcrypt Installation
|
||||
5. Bei Fehlern schlägt der Build fehl
|
||||
|
||||
**Vorteile:**
|
||||
- ⚡ Sehr schnelle Container-Builds (kein TypeScript/Vite-Build)
|
||||
- 🔄 Ideal für lokale Entwicklung und Testing
|
||||
|
||||
**Nachteile:**
|
||||
- ❌ Benötigt lokale Builds vor Docker-Build
|
||||
- ❌ Nicht geeignet für Remote-Deployment
|
||||
|
||||
---
|
||||
|
||||
## Verwendungsempfehlungen
|
||||
|
||||
### Lokale Entwicklung
|
||||
```bash
|
||||
# 1. Baue Artefakte lokal (Client + Server)
|
||||
pnpm install --frozen-lockfile
|
||||
pnpm run build # erzeugt dist/ und server-dist/
|
||||
|
||||
# 2. Baue & starte Container mit production-prebuilt
|
||||
docker compose build
|
||||
docker compose up -d
|
||||
```
|
||||
|
||||
### Production-Deployment
|
||||
```bash
|
||||
# Nutzt production Stage (baut alles im Container)
|
||||
docker-compose -f docker-compose-prod.yml up --build
|
||||
```
|
||||
|
||||
### CI/CD-Pipeline
|
||||
```bash
|
||||
# Explizit production Stage verwenden
|
||||
docker build --target production -t myapp:latest .
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
### Problem: "Cannot find module 'bcrypt'"
|
||||
**Ursache:** Native Module (bcrypt) nicht korrekt für Alpine Linux kompiliert.
|
||||
|
||||
**Lösung:** Der Build schlägt jetzt absichtlich fehl, wenn `bcrypt` nicht kompiliert werden kann. Prüfe die Build-Logs und stelle sicher, dass Build-Tools (python3, make, g++) installiert sind. Im `production-prebuilt`-Szenario erfolgt ein Rebuild beim Container-Start.
|
||||
|
||||
### Problem: "dist/ not found" im production-prebuilt Stage
|
||||
**Ursache:** Lokale Builds fehlen
|
||||
|
||||
**Lösung:** Führe `pnpm build` vor `docker-compose up` aus
|
||||
|
||||
### Problem: Container startet nicht in Production
|
||||
**Ursache:** docker-compose-prod.yml nutzt falschen Stage
|
||||
|
||||
**Lösung:** Setze explizit `target: production` in docker-compose-prod.yml
|
||||
|
||||
---
|
||||
|
||||
## Native Module (bcrypt)
|
||||
|
||||
bcrypt ist ein natives Node.js-Modul, das für die jeweilige Plattform kompiliert werden muss.
|
||||
|
||||
**Im Dockerfile (Build & Verifikation):**
|
||||
```dockerfile
|
||||
# Build-Dependencies für native Module
|
||||
RUN apk add --no-cache python3 make g++ libc6-compat
|
||||
|
||||
# Nach pnpm install: bcrypt neu kompilieren (Fehler NICHT unterdrücken) und verifizieren
|
||||
RUN echo "[production] Rebuilding bcrypt for Alpine Linux..." \
|
||||
&& pnpm rebuild bcrypt --build-from-source \
|
||||
&& echo "[production] Verifying bcrypt installation..." \
|
||||
&& node -e "require('bcrypt')"
|
||||
```
|
||||
|
||||
**Im Startup (production-prebuilt):**
|
||||
Der Container verifiziert vor dem Start, dass `bcrypt` verfügbar ist, und bricht mit klarer Fehlermeldung ab, falls nicht.
|
||||
|
||||
---
|
||||
|
||||
## Troubleshooting: Native Module (bcrypt)
|
||||
|
||||
### Problem: bcrypt_lib.node nicht gefunden
|
||||
|
||||
**Symptom**: Container startet mit Fehler:
|
||||
```
|
||||
Error: Cannot find module '/app/node_modules/.pnpm/bcrypt@5.1.1/node_modules/bcrypt/lib/binding/napi-v3/bcrypt_lib.node'
|
||||
```
|
||||
|
||||
**Ursache**: Native Module wie bcrypt müssen für die Zielplattform (Alpine Linux) kompiliert werden. Wenn lokal auf Windows/Mac gebaut wird, sind die Bindings inkompatibel.
|
||||
|
||||
**Lösung**:
|
||||
1. **Für lokale Entwicklung** (docker-compose.yml mit `production-prebuilt`):
|
||||
- Der Container rebuildet bcrypt automatisch beim Start
|
||||
- Prüfe Logs: `docker compose logs stargirlnails | grep bcrypt`
|
||||
- Bei Fehlern: `docker compose down && docker compose build --no-cache`
|
||||
|
||||
2. **Für Production** (docker-compose-prod.yml mit `production`):
|
||||
- bcrypt wird während des Docker-Builds kompiliert
|
||||
- Build-Tools (python3, make, g++) sind im Image vorhanden
|
||||
- Bei Fehlern: Prüfe Build-Logs auf Compiler-Fehler
|
||||
|
||||
3. **Manuelle Verifikation**:
|
||||
```bash
|
||||
docker compose exec stargirlnails node -e "require('bcrypt')"
|
||||
```
|
||||
Sollte ohne Fehler durchlaufen.
|
||||
|
||||
### Best Practices
|
||||
|
||||
- Niemals `|| true` bei native Module Rebuilds verwenden
|
||||
- Immer Build-Tools im Production-Image behalten (python3, make, g++)
|
||||
- Testen nach jedem Dependency-Update mit `--no-cache` Build
|
Reference in New Issue
Block a user