Es gab bisher keinerlei Sicherung: Bestellungen, Rechnungen,
Kundenkonten und Chargendaten lagen in einem einzelnen
PersistentVolume ohne Netz. Ein Speicherfehler, ein versehentliches
"kubectl delete pvc" oder ein misslungenes Cluster-Update haetten alles
davon unwiederbringlich geloescht. Rechnungen unterliegen in
Deutschland zusaetzlich einer zehnjaehrigen Aufbewahrungspflicht
(§ 147 AO) — ein Datenverlust waere hier nicht nur aergerlich, sondern
ein Rechtsproblem.
Neu: 07-backup-cronjob.yaml — naechtlicher pg_dump auf ein eigenes
Volume, gzip-komprimiert, 30 Tage Aufbewahrung, concurrencyPolicy
Forbid. Fehlgeschlagene Laeufe werden laenger aufgehoben als
erfolgreiche: nur an ihnen laesst sich per "kubectl logs"
nachvollziehen, warum eine Sicherung ausblieb.
Zwei Details, an denen Sicherungsskripte typischerweise scheitern:
- "set -o pipefail". Ohne das liefert "pg_dump | gzip" den Exit-Code von
gzip, und gzip gelingt auch dann, wenn pg_dump vorher abgebrochen ist.
Der Job galte als erfolgreich, im Verzeichnis laege eine
abgeschnittene Datei, und das faellt erst im Ernstfall auf. Beide
Varianten mit einem absichtlich abbrechenden Dump geprueft: ohne
pipefail Exit 0 samt vollstaendig aussehender .sql.gz, mit pipefail
Exit 1 und keine .sql.gz.
- Schreiben unter ".partial" und erst danach umbenennen, damit ein
mitten im Lauf abgebrochener Job keine Datei hinterlaesst, die wie
eine vollstaendige Sicherung aussieht. Liegengebliebene .partial-Reste
raeumt derselbe Lauf mit auf.
k8s/README.md: neuer Abschnitt "Sicherung und Wiederherstellung" mit
Ansehen, manuellem Ausloesen, Herausziehen aus dem Cluster und dem
vollstaendigen Wiederherstellungsweg (App auf 0 skalieren, Dump
einspielen, wieder hochskalieren) — samt dem Hinweis, dass eine nie
getestete Sicherung keine Sicherung ist. Der Abschnitt "Bekannte
Grenzen" nannte "ohne Replikation/Backup-Automation"; das stimmt jetzt
nur noch zur Haelfte und ist entsprechend praezisiert: die Sicherung
liegt weiterhin im selben Cluster und ersetzt keine Replikation.
Alle Manifeste gegen einen YAML-Parser geprueft.
Co-Authored-By: Claude Opus 5 (1M context) <[email protected]>