First Commit with complete Setup coded by Claude 4.7 Opus
This commit is contained in:
commit
bf1d37de77
19 changed files with 4544 additions and 0 deletions
50
nginx/certs/README.md
Normal file
50
nginx/certs/README.md
Normal file
|
|
@ -0,0 +1,50 @@
|
|||
# TLS-Zertifikate
|
||||
|
||||
Dieses Verzeichnis ist für deine eigenen TLS-Zertifikate gedacht.
|
||||
|
||||
## Selbstsigniertes Zertifikat (Standard)
|
||||
|
||||
Wenn dieses Verzeichnis **leer** ist, generiert CardSync beim ersten Start
|
||||
automatisch ein selbstsigniertes Zertifikat (10 Jahre gültig) für die Hostnamen:
|
||||
- `cardsync.local`
|
||||
- `localhost`
|
||||
- `127.0.0.1`
|
||||
|
||||
Browser zeigen dabei eine Sicherheitswarnung, die du einmalig akzeptieren musst.
|
||||
|
||||
## Eigenes Zertifikat verwenden (Wildcard, Let's Encrypt, etc.)
|
||||
|
||||
Lege deine Dateien hier ab — **exakt mit diesen Namen**:
|
||||
|
||||
```
|
||||
nginx/certs/cert.pem ← Public Cert (inkl. Intermediate-Chain bei CA-Certs)
|
||||
nginx/certs/key.pem ← Private Key (unverschlüsselt)
|
||||
```
|
||||
|
||||
Falls dein Provider die Datei anders nennt:
|
||||
| Datei vom Provider | → umbenennen zu |
|
||||
|-------------------------------------|-----------------|
|
||||
| `fullchain.pem` (Let's Encrypt) | `cert.pem` |
|
||||
| `privkey.pem` (Let's Encrypt) | `key.pem` |
|
||||
| `cert.crt` + `bundle.crt` | zusammenfügen zu `cert.pem` (cert zuerst, dann bundle) |
|
||||
| `*.pfx` (Windows) | siehe Konvertierung unten |
|
||||
|
||||
## PFX/P12 nach PEM konvertieren
|
||||
|
||||
Falls du nur eine `.pfx`-Datei hast (typisch bei Windows-Wildcard-Certs):
|
||||
|
||||
```bash
|
||||
# Cert extrahieren
|
||||
openssl pkcs12 -in dein-zertifikat.pfx -clcerts -nokeys -out cert.pem
|
||||
|
||||
# Key extrahieren (entschlüsselt)
|
||||
openssl pkcs12 -in dein-zertifikat.pfx -nocerts -nodes -out key.pem
|
||||
```
|
||||
|
||||
## Nach Cert-Tausch
|
||||
|
||||
```bash
|
||||
docker compose restart frontend
|
||||
```
|
||||
|
||||
Das ist alles — CardSync übernimmt das neue Zertifikat automatisch.
|
||||
44
nginx/entrypoint.sh
Executable file
44
nginx/entrypoint.sh
Executable file
|
|
@ -0,0 +1,44 @@
|
|||
#!/bin/sh
|
||||
# CardSync Nginx Entrypoint
|
||||
# Generiert ein selbstsigniertes Zertifikat falls noch keins vorhanden ist.
|
||||
# Eigene Zertifikate können einfach in ./nginx/certs/ als cert.pem + key.pem
|
||||
# abgelegt werden — diese werden dann verwendet.
|
||||
|
||||
set -e
|
||||
|
||||
CERT_DIR="/etc/nginx/certs"
|
||||
CERT_FILE="$CERT_DIR/cert.pem"
|
||||
KEY_FILE="$CERT_DIR/key.pem"
|
||||
|
||||
mkdir -p "$CERT_DIR"
|
||||
|
||||
if [ ! -f "$CERT_FILE" ] || [ ! -f "$KEY_FILE" ]; then
|
||||
echo "==> Kein TLS-Zertifikat gefunden — generiere selbstsigniertes Cert..."
|
||||
|
||||
# OpenSSL ist im nginx:alpine Image bereits vorhanden
|
||||
openssl req -x509 -nodes -newkey rsa:2048 \
|
||||
-keyout "$KEY_FILE" \
|
||||
-out "$CERT_FILE" \
|
||||
-days 3650 \
|
||||
-subj "/CN=cardsync.local/O=CardSync/C=DE" \
|
||||
-addext "subjectAltName=DNS:cardsync.local,DNS:localhost,IP:127.0.0.1" \
|
||||
2>/dev/null
|
||||
|
||||
chmod 644 "$CERT_FILE"
|
||||
chmod 600 "$KEY_FILE"
|
||||
|
||||
echo "==> Selbstsigniertes Zertifikat erstellt (gültig 10 Jahre)"
|
||||
echo " Cert: $CERT_FILE"
|
||||
echo " Key: $KEY_FILE"
|
||||
echo ""
|
||||
echo " Um ein eigenes Zertifikat zu verwenden:"
|
||||
echo " - Lege cert.pem + key.pem in ./nginx/certs/ ab"
|
||||
echo " - docker compose restart frontend"
|
||||
else
|
||||
echo "==> Verwende vorhandenes TLS-Zertifikat aus $CERT_DIR"
|
||||
# Kurze Cert-Info ausgeben
|
||||
openssl x509 -in "$CERT_FILE" -noout -subject -issuer -dates 2>/dev/null || true
|
||||
fi
|
||||
|
||||
# Nginx im Vordergrund starten (Standard-Behavior fortsetzen)
|
||||
exec nginx -g "daemon off;"
|
||||
58
nginx/nginx.conf
Normal file
58
nginx/nginx.conf
Normal file
|
|
@ -0,0 +1,58 @@
|
|||
# Redirect HTTP → HTTPS
|
||||
server {
|
||||
listen 80;
|
||||
server_name _;
|
||||
return 301 https://$host$request_uri;
|
||||
}
|
||||
|
||||
# HTTPS
|
||||
server {
|
||||
listen 443 ssl;
|
||||
http2 on;
|
||||
server_name _;
|
||||
|
||||
ssl_certificate /etc/nginx/certs/cert.pem;
|
||||
ssl_certificate_key /etc/nginx/certs/key.pem;
|
||||
|
||||
# Moderne TLS-Konfiguration (Mozilla "intermediate")
|
||||
ssl_protocols TLSv1.2 TLSv1.3;
|
||||
ssl_prefer_server_ciphers off;
|
||||
ssl_ciphers ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-CHACHA20-POLY1305:ECDHE-RSA-CHACHA20-POLY1305;
|
||||
ssl_session_timeout 1d;
|
||||
ssl_session_cache shared:SSL:10m;
|
||||
ssl_session_tickets off;
|
||||
|
||||
# HSTS (1 Jahr)
|
||||
add_header Strict-Transport-Security "max-age=31536000; includeSubDomains" always;
|
||||
|
||||
# Frontend (statische Dateien)
|
||||
root /usr/share/nginx/html;
|
||||
index index.html;
|
||||
|
||||
# API zum Backend
|
||||
location /api/ {
|
||||
proxy_pass http://backend:8000;
|
||||
proxy_set_header Host $host;
|
||||
proxy_set_header X-Real-IP $remote_addr;
|
||||
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
|
||||
proxy_set_header X-Forwarded-Proto $scheme;
|
||||
proxy_read_timeout 120s;
|
||||
}
|
||||
|
||||
location /auth/ {
|
||||
proxy_pass http://backend:8000;
|
||||
proxy_set_header Host $host;
|
||||
proxy_set_header X-Real-IP $remote_addr;
|
||||
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
|
||||
proxy_set_header X-Forwarded-Proto $scheme;
|
||||
}
|
||||
|
||||
location /health {
|
||||
proxy_pass http://backend:8000;
|
||||
}
|
||||
|
||||
# Frontend-Dateien
|
||||
location / {
|
||||
try_files $uri $uri/ /index.html;
|
||||
}
|
||||
}
|
||||
Loading…
Add table
Add a link
Reference in a new issue