- Add comprehensive health check system with multiple endpoints - Add Prometheus metrics endpoint - Add production logging configurations (5 strategies) - Add complete deployment documentation suite: * QUICKSTART.md - 30-minute deployment guide * DEPLOYMENT_CHECKLIST.md - Printable verification checklist * DEPLOYMENT_WORKFLOW.md - Complete deployment lifecycle * PRODUCTION_DEPLOYMENT.md - Comprehensive technical reference * production-logging.md - Logging configuration guide * ANSIBLE_DEPLOYMENT.md - Infrastructure as Code automation * README.md - Navigation hub * DEPLOYMENT_SUMMARY.md - Executive summary - Add deployment scripts and automation - Add DEPLOYMENT_PLAN.md - Concrete plan for immediate deployment - Update README with production-ready features All production infrastructure is now complete and ready for deployment.
372 lines
8.9 KiB
Markdown
372 lines
8.9 KiB
Markdown
# SSL/TLS Deployment Guide
|
|
|
|
Vollständige Anleitung für Let's Encrypt SSL/TLS Setup im Custom PHP Framework.
|
|
|
|
## Übersicht
|
|
|
|
Das Framework nutzt **Let's Encrypt** mit einem **Certbot Sidecar Container** für automatische SSL-Zertifikatsverwaltung.
|
|
|
|
**Architektur**:
|
|
```
|
|
┌─────────────────────────────────────────────────────────┐
|
|
│ Nginx Container (macbre/nginx-http3) │
|
|
│ • HTTP/3 & QUIC Support │
|
|
│ • TLS 1.3 & TLS 1.2 │
|
|
│ • Security Headers │
|
|
│ • Shared Volume: /etc/letsencrypt (read-only) │
|
|
└──────────────────┬──────────────────────────────────────┘
|
|
│
|
|
│ Shared Volumes
|
|
↓
|
|
┌─────────────────────────────────────────────────────────┐
|
|
│ Certbot Sidecar Container (certbot/certbot) │
|
|
│ • Auto-renewal every 12h │
|
|
│ • HTTP-01 Challenge via webroot │
|
|
│ • Shared Volume: /etc/letsencrypt (read-write) │
|
|
└─────────────────────────────────────────────────────────┘
|
|
```
|
|
|
|
## Voraussetzungen
|
|
|
|
1. **Domain konfiguriert**: DNS A-Record zeigt auf Server-IP
|
|
2. **Firewall**: Port 80 und 443 offen
|
|
3. **Docker & Docker Compose** installiert
|
|
4. **Production Environment** konfiguriert
|
|
|
|
## Initial Setup
|
|
|
|
### 1. Environment Configuration
|
|
|
|
```bash
|
|
# Kopiere Production Template
|
|
cp .env.production.example .env.production
|
|
|
|
# Bearbeite .env.production
|
|
nano .env.production
|
|
```
|
|
|
|
**Wichtige Variablen**:
|
|
```bash
|
|
DOMAIN_NAME=michaelschiemer.de
|
|
SSL_EMAIL=mail@michaelschiemer.de
|
|
LETSENCRYPT_ENABLED=true
|
|
APP_ENV=production
|
|
APP_DEBUG=false
|
|
```
|
|
|
|
### 2. SSL Zertifikat Initial Holen
|
|
|
|
```bash
|
|
# Führe SSL Initialization Script aus
|
|
./scripts/ssl-init.sh
|
|
|
|
# Mit Custom Domain und Email
|
|
./scripts/ssl-init.sh yourdomain.com admin@yourdomain.com
|
|
|
|
# Testing Mode (Staging Certificates - empfohlen für ersten Test)
|
|
LETSENCRYPT_STAGING=1 ./scripts/ssl-init.sh
|
|
```
|
|
|
|
**Das Script macht**:
|
|
1. Startet Nginx Container
|
|
2. Erstellt ACME Challenge Verzeichnis
|
|
3. Holt Let's Encrypt Zertifikat via HTTP-01
|
|
4. Speichert Zertifikate in Docker Volume
|
|
5. Startet Nginx mit SSL neu
|
|
|
|
### 3. Production Stack Starten
|
|
|
|
```bash
|
|
# Starte kompletten Production Stack
|
|
docker-compose -f docker-compose.yml -f docker-compose.production.yml up -d
|
|
|
|
# Check Logs
|
|
docker-compose -f docker-compose.yml -f docker-compose.production.yml logs -f web certbot
|
|
```
|
|
|
|
## SSL Testing & Validation
|
|
|
|
### Lokaler Test
|
|
|
|
```bash
|
|
# Führe SSL Test Script aus
|
|
./scripts/ssl-test.sh
|
|
|
|
# Mit Custom Domain
|
|
./scripts/ssl-test.sh yourdomain.com
|
|
```
|
|
|
|
**Test Prüft**:
|
|
- ✅ Port 443 Erreichbarkeit
|
|
- ✅ Zertifikatsgültigkeit
|
|
- ✅ Let's Encrypt Issuer
|
|
- ✅ TLS 1.3 & TLS 1.2 Support
|
|
- ✅ HTTP → HTTPS Redirect
|
|
- ✅ HSTS Header
|
|
- ✅ Security Headers
|
|
|
|
### Online SSL Tests
|
|
|
|
**SSL Labs** (A+ Rating anstreben):
|
|
```
|
|
https://www.ssllabs.com/ssltest/analyze.html?d=michaelschiemer.de
|
|
```
|
|
|
|
**Mozilla Observatory**:
|
|
```
|
|
https://observatory.mozilla.org/analyze/michaelschiemer.de
|
|
```
|
|
|
|
**Security Headers**:
|
|
```
|
|
https://securityheaders.com/?q=michaelschiemer.de
|
|
```
|
|
|
|
## Auto-Renewal
|
|
|
|
### Certbot Sidecar Container
|
|
|
|
Der Certbot Container läuft permanent und prüft alle **12 Stunden** ob Zertifikate erneuert werden müssen.
|
|
|
|
```bash
|
|
# Check Certbot Logs
|
|
docker logs certbot
|
|
|
|
# Manuelles Renewal testen (Dry-Run)
|
|
docker exec certbot certbot renew --dry-run
|
|
|
|
# Manuelles Renewal (falls nötig)
|
|
docker exec certbot certbot renew
|
|
|
|
# Nginx nach Manual Renewal neu laden
|
|
docker-compose restart web
|
|
```
|
|
|
|
### Renewal Monitoring
|
|
|
|
**Zertifikats-Ablaufdatum prüfen**:
|
|
```bash
|
|
# Via Script
|
|
./scripts/ssl-test.sh
|
|
|
|
# Manuell
|
|
docker exec certbot certbot certificates
|
|
```
|
|
|
|
**Empfohlene Monitoring-Strategie**:
|
|
- Certbot Logs täglich checken
|
|
- Alert wenn Zertifikat < 30 Tage gültig
|
|
- Automatisches Monitoring via Cron/SystemD Timer
|
|
|
|
## Troubleshooting
|
|
|
|
### Problem: Zertifikat kann nicht geholt werden
|
|
|
|
**Symptom**: `ssl-init.sh` schlägt fehl
|
|
|
|
**Ursachen & Lösungen**:
|
|
|
|
1. **DNS nicht korrekt**:
|
|
```bash
|
|
# DNS prüfen
|
|
dig michaelschiemer.de
|
|
nslookup michaelschiemer.de
|
|
|
|
# Warte bis DNS propagiert ist (kann 1-48h dauern)
|
|
```
|
|
|
|
2. **Port 80 nicht erreichbar**:
|
|
```bash
|
|
# Firewall prüfen
|
|
sudo ufw status
|
|
sudo ufw allow 80
|
|
sudo ufw allow 443
|
|
|
|
# Nginx Test
|
|
curl -I http://michaelschiemer.de/.well-known/acme-challenge/test
|
|
```
|
|
|
|
3. **ACME Challenge Location fehlt**:
|
|
```bash
|
|
# Nginx Config prüfen
|
|
docker exec web nginx -t
|
|
|
|
# Log prüfen
|
|
docker logs web
|
|
```
|
|
|
|
### Problem: Zertifikat wird nicht erneuert
|
|
|
|
**Symptom**: Certbot Renewal schlägt fehl
|
|
|
|
**Lösungen**:
|
|
|
|
1. **Certbot Logs prüfen**:
|
|
```bash
|
|
docker logs certbot
|
|
docker exec certbot certbot renew --dry-run --verbose
|
|
```
|
|
|
|
2. **Webroot Permissions**:
|
|
```bash
|
|
# Permissions prüfen
|
|
docker exec web ls -la /var/www/certbot/.well-known/acme-challenge/
|
|
```
|
|
|
|
3. **Nginx Config Syntax**:
|
|
```bash
|
|
docker exec web nginx -t
|
|
```
|
|
|
|
### Problem: HTTPS funktioniert nicht nach Renewal
|
|
|
|
**Symptom**: Alte Zertifikate werden verwendet
|
|
|
|
**Lösung**:
|
|
```bash
|
|
# Nginx neu laden
|
|
docker-compose restart web
|
|
|
|
# Oder ohne Downtime
|
|
docker exec web nginx -s reload
|
|
```
|
|
|
|
## Zero-Downtime Renewal
|
|
|
|
Nginx unterstützt **graceful reload** ohne Connection-Drops:
|
|
|
|
```bash
|
|
# Reload ohne Downtime
|
|
docker exec web nginx -s reload
|
|
|
|
# In Auto-Renewal integrieren
|
|
docker exec certbot certbot renew --post-hook "nginx -s reload"
|
|
```
|
|
|
|
## Production Best Practices
|
|
|
|
### 1. Monitoring Setup
|
|
|
|
**Cron Job für tägliche Checks**:
|
|
```bash
|
|
# /etc/cron.daily/ssl-check
|
|
#!/bin/bash
|
|
/path/to/scripts/ssl-test.sh michaelschiemer.de > /var/log/ssl-check.log 2>&1
|
|
|
|
# Alert wenn weniger als 30 Tage
|
|
DAYS_LEFT=$(docker exec certbot certbot certificates | grep "VALID:" | awk '{print $6}' | head -1)
|
|
if [ "$DAYS_LEFT" -lt "30" ]; then
|
|
echo "WARNING: SSL certificate expires in $DAYS_LEFT days" | mail -s "SSL Alert" admin@michaelschiemer.de
|
|
fi
|
|
```
|
|
|
|
### 2. Backup Strategy
|
|
|
|
**Zertifikate Backup**:
|
|
```bash
|
|
# Backup Let's Encrypt Config
|
|
docker run --rm \
|
|
-v certbot-conf:/etc/letsencrypt \
|
|
-v $(pwd)/backups:/backup \
|
|
alpine tar czf /backup/letsencrypt-$(date +%Y%m%d).tar.gz /etc/letsencrypt
|
|
|
|
# Restore
|
|
docker run --rm \
|
|
-v certbot-conf:/etc/letsencrypt \
|
|
-v $(pwd)/backups:/backup \
|
|
alpine tar xzf /backup/letsencrypt-20241220.tar.gz -C /
|
|
```
|
|
|
|
### 3. Security Hardening
|
|
|
|
**HTTP/3 aktivieren** (bereits konfiguriert):
|
|
```nginx
|
|
listen 443 quic reuseport;
|
|
http3 on;
|
|
add_header Alt-Svc 'h3=":443"; ma=86400';
|
|
```
|
|
|
|
**HSTS Preload** (nach 6 Monaten stabiler Betrieb):
|
|
```nginx
|
|
add_header Strict-Transport-Security "max-age=31536000; includeSubDomains; preload" always;
|
|
```
|
|
|
|
Dann einreichen bei: https://hstspreload.org/
|
|
|
|
## Makefile Integration
|
|
|
|
Füge zu `Makefile` hinzu:
|
|
|
|
```makefile
|
|
# SSL Certificate Management
|
|
ssl-init: ## Initialize Let's Encrypt certificates
|
|
./scripts/ssl-init.sh
|
|
|
|
ssl-test: ## Test SSL configuration
|
|
./scripts/ssl-test.sh
|
|
|
|
ssl-renew: ## Manually renew certificates
|
|
docker exec certbot certbot renew
|
|
docker-compose restart web
|
|
|
|
ssl-status: ## Check certificate status
|
|
docker exec certbot certbot certificates
|
|
```
|
|
|
|
**Verwendung**:
|
|
```bash
|
|
make ssl-init # Initial Setup
|
|
make ssl-test # Test SSL
|
|
make ssl-renew # Manual Renewal
|
|
make ssl-status # Check Expiry
|
|
```
|
|
|
|
## Migration von Self-Signed zu Let's Encrypt
|
|
|
|
Wenn du von Self-Signed Zertifikaten migrierst:
|
|
|
|
```bash
|
|
# 1. Backup alte Zertifikate
|
|
cp -r docker/nginx/ssl docker/nginx/ssl.backup
|
|
|
|
# 2. SSL Init ausführen
|
|
./scripts/ssl-init.sh
|
|
|
|
# 3. Nginx Config Update (automatisch via docker-compose.production.yml)
|
|
# 4. Stack neu starten
|
|
docker-compose -f docker-compose.yml -f docker-compose.production.yml restart
|
|
```
|
|
|
|
## Kosten
|
|
|
|
**Let's Encrypt**: ✅ **Kostenlos**
|
|
- Unlimitierte Zertifikate
|
|
- Automatische Renewal
|
|
- Wildcard-Zertifikate möglich (DNS-01 Challenge)
|
|
|
|
**Rate Limits**:
|
|
- 50 Zertifikate pro Domain pro Woche
|
|
- 5 Duplicate Certificates pro Woche
|
|
- Kein Problem für normale Production-Nutzung
|
|
|
|
## Support & Dokumentation
|
|
|
|
**Let's Encrypt Dokumentation**: https://letsencrypt.org/docs/
|
|
**Certbot Dokumentation**: https://eff-certbot.readthedocs.io/
|
|
**Framework SSL Issues**: https://github.com/yourusername/framework/issues
|
|
|
|
## Zusammenfassung
|
|
|
|
**Setup-Schritte**:
|
|
1. ✅ `.env.production` konfigurieren
|
|
2. ✅ `./scripts/ssl-init.sh` ausführen
|
|
3. ✅ Production Stack starten
|
|
4. ✅ `./scripts/ssl-test.sh` validieren
|
|
5. ✅ SSL Labs Test (A+ Rating)
|
|
|
|
**Auto-Renewal**: ✅ Certbot Container erneuert automatisch
|
|
|
|
**Zero-Downtime**: ✅ Nginx reload ohne Connection-Drops
|
|
|
|
**Production-Ready**: ✅ HTTP/3, TLS 1.3, Security Headers
|