# Go-Live-Checkliste fuer Netcup Webspace Diese Checkliste ist fuer den ersten echten Betrieb auf Netcup Webspace gedacht. Sie baut auf [DEPLOY.md](/config/workspace/kaffeeliste-neustart/DEPLOY.md), [RUNBOOK.md](/config/workspace/kaffeeliste-neustart/RUNBOOK.md) und [docs/production-blueprint.md](/config/workspace/kaffeeliste-neustart/docs/production-blueprint.md) auf, ist aber absichtlich strenger und operativer. ## 1. Go-Live-Scope festziehen - [ ] Entscheiden, ob der erste Livegang ein geschlossener Pilot oder ein oeffentliches SaaS-Launch ist. - [ ] Fuer einen oeffentlichen Launch Registrierung absichern oder vorerst deaktivieren. Das Repo nennt Mail-Verifikation, Passwort-Reset und Rate-Limits selbst als offene Punkte vor echtem Go-Live. - [ ] Falls diese Punkte noch fehlen: nur mit eingeladenen Testkunden oder manuell freigeschalteten Mandanten live gehen. - [ ] Einen Release-Owner und einen Restore-Owner benennen. - [ ] Ein Wartungsfenster fuer den Erststart und fuer kuenftige Releases definieren. ## 2. Environment-Modell festlegen Empfehlung fuer Netcup Webspace: - [ ] `local`: Entwicklung lokal. - [ ] `staging`: echte Netcup-Subdomain wie `staging.example.tld`, eigene DB, eigene `.env`. - [ ] `production`: produktive Domain, eigene DB, eigene `.env`. Pragmatisches Verzeichnislayout ohne Root-Zwang: - [ ] `staging` unter `/apps/kaffeekasse-stage/current` - [ ] `production` unter `/apps/kaffeekasse/current` - [ ] Offsite- oder Backup-Artefakte nicht im Webroot ablegen. Wichtig fuer dieses Repo: - [ ] `public/` bleibt der einzige Webroot. - [ ] `.env` wird aus dem Projektwurzelverzeichnis geladen. - [ ] Der Browser-Installer schreibt `.env` in das Projektwurzelverzeichnis und `storage/installed.lock` in `storage/`. - [ ] `bin/cron.php` schreibt `storage/cron.lock`. - [ ] Deshalb muessen Projektwurzel und `storage/` mindestens fuer den Deployment-User, besser auch fuer den Webspace-User, sauber beschreibbar sein. ## 3. Netcup vorbereiten - [ ] Domain oder Subdomain im CCP/WCP anlegen. - [ ] DNS frueh setzen und Aufloesung pruefen. - [ ] In Plesk/WCP pro Environment eine eigene Site mit eigenem Document Root anlegen. - [ ] Document Root fuer jedes Environment auf `.../current/public` setzen. - [ ] Pro Environment eine eigene MySQL-Datenbank und einen eigenen DB-User anlegen. - [ ] PHP-Version im WCP fest auf 8.3 oder 8.4 pinnen und nicht auf "System Default" lassen. - [ ] Dieselbe PHP-Hauptversion fuer Web und CLI verwenden. ## 4. Secrets und Konfiguration vorbereiten Pflichtwerte laut App: - [ ] `APP_URL` - [ ] `APP_ENV` - [ ] `APP_DEBUG=0` - [ ] `APP_TIMEZONE` - [ ] `APP_KEY` - [ ] `DB_HOST` - [ ] `DB_PORT` - [ ] `DB_NAME` - [ ] `DB_USER` - [ ] `DB_PASS` - [ ] `RFID_SHARED_SECRET` Empfehlung: - [ ] `staging` und `production` nie dieselben Secrets oder dieselbe DB teilen. - [ ] Admin-Zugang fuer die Plattform separat dokumentieren und im Passwortsafe ablegen. - [ ] Wenn der Browser-Installer verwendet wird: danach `.env` sichern und offsite ablegen. - [ ] Wenn `.env` manuell gepflegt wird: `.env` vor dem ersten Deploy lokal erzeugen und erst dann hochladen. ## 5. Erstes Staging-Deployment - [ ] Lokal oder in CI `scripts/build-release.sh` ausfuehren. - [ ] Release-Artefakt sicher ablegen. Es ist Teil des Rollback-Pfads. - [ ] Artefakt per FTPES oder SFTP nach Netcup hochladen. - [ ] Paket in den festen Environment-Pfad entpacken. - [ ] Pruefen, dass `.env`, `storage/uploads`, `storage/logs` und `storage/cache` nicht versehentlich ueberschrieben oder geloescht wurden. Das Build-Skript schliesst diese Pfade aus dem Release aus. - [ ] Falls der Browser-Installer genutzt wird: `/install` nur auf `staging` einmal durchlaufen. - [ ] Falls manuell installiert wird: `.env` hochladen und danach `/usr/local/php83/bin/php /apps/kaffeekasse-stage/current/bin/migrate.php` oder die zu eurer PHP-Version passende Binary ausfuehren. - [ ] Pruefen, dass `storage/installed.lock` angelegt wurde. ## 6. Staging-Smoketest vor Production - [ ] Startseite laden. - [ ] `/admin/login` erfolgreich testen. - [ ] Einen Test-Mandanten anlegen. - [ ] Tenant-Login pruefen. - [ ] Eine Testbuchung und eine Test-Einzahlung anlegen. - [ ] `/usr/local/php83/bin/php /apps/kaffeekasse-stage/current/bin/healthcheck.php` ausfuehren und JSON pruefen. - [ ] `/usr/local/php83/bin/php /apps/kaffeekasse-stage/current/bin/cron.php` manuell ausfuehren. - [ ] Pruefen, dass `cron.lock` nach dem Lauf wieder verschwindet. ## 7. SSL und HTTPS - [ ] Erst SSL ausrollen, wenn DNS sauber auf Netcup zeigt. - [ ] Im WCP fuer jede produktive Domain ein Let's-Encrypt-Zertifikat ausstellen. - [ ] `www` nur dann mit absichern, wenn `www` auch wirklich genutzt werden soll. - [ ] Fuer den ersten Go-Live kein Wildcard-Zertifikat verwenden, wenn es nicht zwingend noetig ist. Bei Netcup werden Wildcard-Zertifikate nicht automatisch erneuert. - [ ] HTTPS fuer die produktive Domain erzwingen. - [ ] Nach Aktivierung pruefen, dass alle Logins und Formulare nur noch ueber HTTPS laufen. - [ ] Session-Cookies unter HTTPS pruefen, weil `secure` in der App vom HTTPS-Kontext abhaengt. ## 8. Backup-Strategie produktionsreif machen Minimum: - [ ] Taegliches DB-Backup einrichten. - [ ] Vor jedem Release ein frisches manuelles DB-Backup ziehen. - [ ] `.env` offsite sichern. - [ ] `storage/uploads` offsite sichern. - [ ] Letztes stabiles Release-Artefakt offsite sichern. Netcup-spezifisch: - [ ] Falls euer Tarif den Backup Manager anbietet: wiederkehrendes Backup in WCP aktivieren. - [ ] Backups regelmaessig herunterladen oder an einen zweiten Ort kopieren. - [ ] Backup Manager nicht als einzigen Disaster-Recovery-Pfad betrachten. Netcup dokumentiert, dass diese Backups nur auf demselben Hosting wiederhergestellt werden sollen. ## 9. Cron sauber einrichten - [ ] In WCP eine geplante Aufgabe fuer `bin/cron.php` alle 5 Minuten anlegen. - [ ] Dieselbe PHP-Version verwenden wie fuer die Website. - [ ] Den Task vor dem Speichern mit "Run Now" testen. - [ ] Wenn WCP auf eurem Tarif mit chroot oder relativen Pfaden zickt: den final funktionierenden Befehl direkt dokumentieren. - [ ] Eine zweite geplante Aufgabe fuer `bin/healthcheck.php` einrichten, mindestens stuendlich oder taeglich. - [ ] Task-Ausgaben in eine Mail oder Logdatei laufen lassen, statt sie still zu verwerfen. Wichtige Einschraenkung dieses Repos: - [ ] `bin/healthcheck.php` liefert JSON, setzt aber bei DB-Problemen derzeit keinen expliziten Exit-Code ungleich 0. - [ ] Fuer Alarmierung deshalb nicht nur auf "Errors only" bei Scheduled Tasks vertrauen. - [ ] Zusaetzlich einen externen HTTPS-Uptime-Check auf Startseite oder Login-Seite einrichten. ## 10. Monitoring-Minimum fuer den Start - [ ] Externes Uptime-Monitoring auf die produktive HTTPS-URL aktivieren. - [ ] Plesk-/PHP-Error-Logs in die Regelbetriebsroutine aufnehmen. - [ ] Nach dem Go-Live taeglich Audit-Ereignisse fuer fehlgeschlagene Logins und Access-Denied pruefen. - [ ] Wachstum der Tabellen `consumption_events`, `ledger_entries` und `audit_events` beobachten. - [ ] Offene RFID-Ereignisse aus dem Cron-Output beobachten, falls RFID pilotiert wird. - [ ] Einen klaren Empfaenger fuer Alarmmails hinterlegen. ## 11. Release-Prozess fuer echte Produktion festlegen Empfohlener erster Produktionsprozess auf Netcup Webspace: - [ ] Aenderungen auf `staging` komplett durchtesten. - [ ] Release-Artefakt mit Zeitstempel bauen. - [ ] Direkt vor dem Produktionsdeploy DB-Backup erstellen. - [ ] `.env` und persistente `storage/`-Inhalte zusatzlich sichern. - [ ] Release nach `production` hochladen. - [ ] `bin/migrate.php` ausfuehren. - [ ] `bin/healthcheck.php` ausfuehren. - [ ] Admin-Login, Tenant-Login und Testbuchung sofort pruefen. - [ ] Den naechsten automatischen Cron-Lauf beobachten. - [ ] Erst danach das Release als "stabil" markieren. Wichtige Einschraenkung dieses Repos: - [ ] `bin/migrate.php` spielt nur `database/schema.sql` erneut ein. - [ ] Das aktuelle `schema.sql` arbeitet mit `CREATE TABLE IF NOT EXISTS` und ist damit fuer Erstinstallation geeignet, aber kein vollwertiges inkrementelles Migrationssystem. - [ ] Vor dem ersten Release mit DB-Schema-Aenderungen eine klare Migrationskonvention festlegen, zum Beispiel versionierte SQL-Dateien plus Runbook-Schritt. ## 12. Fallback und Restore vorher ueben Rollback fuer einen fehlgeschlagenen Release: - [ ] Letztes stabiles Release-Artefakt erneut deployen. - [ ] Wenn noetig DB-Backup vom Start des Releases einspielen. - [ ] `.env` und `storage/uploads` wiederherstellen. - [ ] `bin/healthcheck.php` ausfuehren. - [ ] Admin-Login, Tenant-Login und Testbuchung pruefen. Restore fuer echten Ausfall: - [ ] Zielreihenfolge dokumentieren: Code, `.env`, Uploads, DB, Healthcheck, Smoke-Test. - [ ] Restore nicht nur theoretisch planen, sondern einmal auf `staging` ueben. - [ ] Ziel-RTO und Ziel-RPO festlegen, auch wenn sie anfangs noch pragmatisch sind. - [ ] Ansprechpartner und Zugangsdaten fuer Restore ausserhalb des Repos dokumentieren. ## 13. Finale Go-Live-Freigabe Nur live schalten, wenn alles abgehakt ist: - [ ] Production-Domain zeigt auf Netcup und loest korrekt auf. - [ ] SSL ist gueltig und HTTPS wird erzwungen. - [ ] `public/` ist einziger Webroot. - [ ] `.env`, Backups, Dumps und `.git` sind nicht oeffentlich erreichbar. - [ ] DB-Backup von heute existiert. - [ ] Cron laeuft erfolgreich. - [ ] Externes Monitoring prueft die Seite. - [ ] Admin-Login und ein Test-Tenant funktionieren. - [ ] Restore wurde mindestens einmal auf `staging` geprobt. - [ ] Es gibt eine bewusste Entscheidung, ob offene Registrierung bereits verantwortbar ist. ## Quellen - Repo-intern: [DEPLOY.md](/config/workspace/kaffeeliste-neustart/DEPLOY.md), [RUNBOOK.md](/config/workspace/kaffeeliste-neustart/RUNBOOK.md), [docs/production-blueprint.md](/config/workspace/kaffeeliste-neustart/docs/production-blueprint.md), [app/bootstrap.php](/config/workspace/kaffeeliste-neustart/app/bootstrap.php), [config/app.php](/config/workspace/kaffeeliste-neustart/config/app.php), [app/Services/SetupService.php](/config/workspace/kaffeeliste-neustart/app/Services/SetupService.php), [bin/migrate.php](/config/workspace/kaffeeliste-neustart/bin/migrate.php), [bin/cron.php](/config/workspace/kaffeeliste-neustart/bin/cron.php), [bin/healthcheck.php](/config/workspace/kaffeeliste-neustart/bin/healthcheck.php), [scripts/build-release.sh](/config/workspace/kaffeeliste-neustart/scripts/build-release.sh) - Offizielle Doku: https://www.netcup.com/en/helpcenter/documentation/web-hosting/php-shell https://www.netcup.com/en/helpcenter/documentation/web-hosting/scheduled-tasks https://www.netcup.com/en/helpcenter/documentation/web-hosting/enabling-ssl-tls https://www.netcup.com/en/helpcenter/documentation/web-hosting/backup-manager https://docs.plesk.com/en-US/obsidian/customer-guide/scheduling-tasks.65207/ https://www.plesk.com/kb/docs/managing-web-hosting-changing-the-document-root-directory/