Beide UIs haben effektiv Host-/Backup-Zugriff (Borg-Restore-Scope inkl.
/local/secrets, code-server mit Workspace-Mounts). Bisher liefen sie ueber
die catch-all-Regel mit nur one_factor. Files und Scrutiny waren bereits
two_factor; die Liste wird konsistent gezogen.
Wirkung erst nach manuellem Host-Merge (Ausnahme laut docs/WORKFLOW.md):
1. /mnt/user/appdata/authelia/config/configuration.yml mergen
2. docker restart authelia
3. Smoke-Test auf einer der vier 2FA-Domains
4. services/authelia-diff.sh muss exit 0 liefern
Audit-Restliste nachgezogen: Tier-1-Operator-2FA geschlossen, restliche
geparkte Auth-Themen (OIDC, CrowdSec, Nextcloud-2FA) bewusst weiter offen
mit aktualisierter Begruendung.
Traefik-Restore am 2026-06-03 erfolgreich: dynamic/ (2 Files) +
letsencrypt/acme.json (426K) aus Borg, File-Provider-Boot, /ping 200.
Erster Versuch, kein shfs-Problem.
11 von 12 Restore-Tests sind jetzt gruen. Einzig Nextcloud bleibt
blockiert durch Unraids shfs-chmod-Inkompatibilitaet.
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
Borg-Extract von dynamic/ und letsencrypt/, Traefik startet mit
File-Provider gegen restaurierte Config, /ping Health antwortet.
Bewusst kein docker.sock (wuerde produktive Container discovern),
kein CF-Token (keine DNS-Challenge), keine produktiven Ports.
acme.json-Existenz und -Groesse wird geprueft, TLS-Validitaet nicht.
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
Mail-Archiver-Restore am 2026-06-03 erfolgreich: Data-Protection-Keys
aus Borg + 645M pg_restore + HTTP 200. Erster Versuch, kein shfs-Problem.
10 von 12 Restore-Tests sind jetzt gruen. Verbleibend: Nextcloud
(blockiert/shfs-chmod) und Traefik (komplex, niedrigere Prio).
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
Borg-Extract der Data-Protection-Keys + pg_restore des 645M
mailarchiver-Dumps in isoliertes Test-Postgres + Container-Boot +
HTTP-Smoke. Wegwerf-DB-Connection und Auth-Password, kein produktiver
Stack-ENV, kein Authelia-ForwardAuth im Smoke.
Machbarkeit vorab verifiziert: Dump vorhanden, App-Image gepinnt,
Data-Protection-Keys im Borg, .NET-App hat kein shfs-chmod-Problem.
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
Mealie-Restore-Test am 2026-06-03 erfolgreich: Borg-Data + pg_restore
+ HTTP 200, 3 Rezepte im Test-DB-Check. Erster Versuch, kein
shfs-Problem (Mealie startet als root, kein chmod auf User Shares).
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
Negativ-Test 2026-06-03: korrupter mealie.dump wurde nicht erkannt,
weil der Docker-Fallback-Pfad nach gescheitertem pg_restore --list
zu return 2 (unchecked) durchfiel statt return 1 (invalid).
Fix: explizites if/else statt &&-Kette, damit fehlgeschlagene
Header-Validierung return 1 liefert und als DUMP_HEADER_INVALID
in den Critical-Zaehler geht.
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
Produktive Mongo ist 8.0.23, Test-Composes pinnten noch 7.0.32.
Eliminiert die Cross-Version-Warnung beim mongorestore.
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
Kompletter Restore-Drill fuer den Shared-PostgreSQL-18-Cluster:
globals (Rollen) + 5 per-DB Custom-Format-Dumps (paperless,
mailarchiver, authelia, nextcloud, mealie).
Bekannter mailarchiver-Bootstrap-Rollenkonflikt wird toleriert.
Authelia/Nextcloud/Mealie-Dumps als optional markiert.
Tabellen-Count pro DB als fachlicher Sanity-Check.
Machbarkeit vorab verifiziert: alle Dumps auf Host vorhanden,
pg_restore im postgres:18.4-Image verfuegbar, Postgres auf shfs
bewiesen durch bestehende Tests.
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
Komodo-Mongo-Daten-Restore am 2026-06-03 erfolgreich: mongorestore
von komodo-mongo.archive.gz in Wegwerf-Mongo, 86904 Dokumente
(inkl. 32 Stack-Definitionen). Damit ist die kanonische Quelle fuer
KOMODO_*-Stack-ENV-Werte im DR-Fall als wiederherstellbar belegt.
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
Zweiter Lauf scheiterte mit Auth-Failure weil der Container-Name
restoretest-komodo-mongo mit dem alten Bootstrap-Test kollidierte
(stale Datadir auf shfs mit anderen Credentials).
Fix: eigenes Compose mit eigenem Container-Namen
(restoretest-komodo-mongorestore) und eigenem Project-Name, damit
keine Namenskollision mit dem bestehenden Bootstrap-Test entsteht.
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
Erstlauf 2026-06-03: 86904 Dokumente (inkl. 32 Stack-Dokumente)
erfolgreich restored, aber Exit 1 weil der Index-Rebuild mit
"Command createIndexes requires authentication" scheitert (Test-User
hat keine dbAdmin-Rolle).
Fix: --noIndexRestore. Fuer den Smoke-Zweck (Stack-Definitionen lesbar,
KOMODO_*-ENV-Werte rekonstruierbar) reicht das. Indexe werden bei einem
echten Komodo-Restart ohnehin neu aufgebaut.
Nebenbefund: produktive Mongo ist 8.0.23, Test-Compose pinnt 7.0.32.
Cross-Version-Warning ist fuer den Lesetest harmlos, aber der
Bootstrap-Compose-Pin sollte separat auf 8.0 nachgezogen werden.
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
Neuer Test: mongorestore von komodo-mongo.archive.gz in eine frische
Wegwerf-Mongo. Beweist, dass die Stack-Definitionen und damit die
KOMODO_*-Stack-ENV-Werte aus dem Dump rekonstruiert werden koennen
(kanonische Quelle laut docs/DISASTER_RECOVERY.md 6.2.1).
Machbarkeit vorab verifiziert: Dump 6.0M auf Host vorhanden,
mongorestore im mongo:7.0.32-Image verfuegbar, shfs-Write funktioniert.
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
Nextcloud-Restore-Test Erstlauf 2026-06-03 nach 5 Iterationen als
strukturell blockiert durch Unraid shfs/FUSE eingestuft.
Ursache: Nextcloud 33 fuehrt zur Laufzeit chmod() auf Dateien unter
/var/www/html aus (OC_Util.php#486). Auf Unraids FUSE/shfs User Shares
ist chmod nicht moeglich - weder vom Host (chown ignoriert) noch aus dem
Container (Operation not permitted), auch nicht ohne no-new-privileges.
In Produktion funktioniert Nextcloud, weil die Daten dort auf einem
Cache-Drive (XFS/BTRFS direkt) statt ueber shfs liegen.
Scaffold (Skript + Compose) bleibt im Repo als Ausgangspunkt fuer die
Loesung. Drei Optionen dokumentiert:
a) Restore-Lab auf Cache-Drive
b) Docker-Volumes statt Bind-Mounts
c) tmpfs + rsync
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
Erstlauf 2026-06-03: borg_extract fuer den Nextcloud-Dump scheiterte
still (Pfad local/borg-dumps/latest/nextcloud.dump existiert im
Archiv moeglicherweise unter einem anderen Prefix). Der Dump liegt
taeglich frisch auf dem Host unter /mnt/user/backups/borg/dumps/latest/
und wird von dort in Borg gesichert - der Smoke-Wert ist identisch.
HTML (App-Code + config) kommt weiterhin aus dem Borg-Archiv.
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
Zweiter Erstlauf 2026-06-03 scheiterte weiterhin mit 503, obwohl
config.php korrekt gepatcht war.
Ursache: Unraid's FUSE/shfs-Dateisystem auf User-Shares ignoriert
chown -R 33:33 still — Dateien bleiben bei sshd:sshd. Der
Nextcloud-Entrypoint versucht intern chmod/chown auf /var/www/html und
/var/www/html/data, was mit no-new-privileges:true blockiert wird.
Fix:
- no-new-privileges vom restoretest-nextcloud Container entfernt,
damit der Entrypoint Rechte im Container selbst setzen kann
(Test-Postgres und Test-Redis behalten no-new-privileges)
- Host-seitiger chown durch chmod a+rwX ersetzt (funktioniert auf shfs)
- Vertretbar im isolierten Smoke-Kontext (127.0.0.1, Wegwerf-Daten,
kein Traefik)
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
Erstlauf 2026-06-03 scheiterte mit dauerhaft 503. config.php-Patching
(Redis-Host + trusted_domains) war korrekt, aber Nextcloud konnte die
restaurierten Dateien nicht lesen/schreiben: "chmod(): Operation not
permitted at OC_Util.php#486".
Ursache: Borg-Extract ueber den borg-ui Container legt Dateien mit dem
borg-ui-User (sshd o.ae.) an. Nextcloud im Container laeuft als
www-data (UID 33). Mit no-new-privileges:true scheitert jeder chmod/
chown-Versuch im Container.
Fix: chown -R 33:33 auf html/ und data/ nach dem Extract, bevor der
Nextcloud-Container startet.
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
Erstlauf 2026-06-03 scheiterte mit 503: Redis-Host war noch auf dem
produktiven 'nextcloud-redis' statt 'restoretest-nextcloud-redis', und
trusted_domains enthielt kein 127.0.0.1 (Nextcloud blockt mit
"Access through untrusted domain").
Ursache: das sed-Pattern fuer Redis versuchte den ganzen Array-Block
einzeilig zu ersetzen, traf aber das PHP-Mehrzeilenformat nicht. Und
das trusted_domains-sed fand das Schliessmuster nicht zuverlaessig.
Fix:
- Redis-Host separat per sed patchen (nur den 'host'-Wert im Block)
- trusted_domains per PHP-CLI rewrite (robuster als sed auf PHP-Arrays)
- Fallback auf sed fuer Hosts ohne php
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
Nextcloud-Restore-Test nach dem Muster der anderen Restore-Smokes:
- Borg-Extract von html (App-Code + config.php) und nextcloud.dump
- pg_restore in isoliertes Test-Postgres (mit Retry-Schleife)
- config.php wird im Restore-Lab auf Test-DB-Credentials gepatcht
(produktive Secrets werden nicht gemountet)
- Nextcloud startet gegen restaurierte Daten + Test-Redis
- Smoke prueft HTTP /status.php und occ status (maintenance mode)
- Produktive Nutzdaten unter /mnt/user/documents/nextcloud-data
werden bewusst NICHT gemountet (zu gross fuer regelmaessigen Smoke)
Erster Lauf steht aus und braucht Operator-Freigabe auf dem Host.
Dispatcher und ntfy-Wrapper um Nextcloud erweitert.
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
Erstlauf 2026-06-03 hat einen by-design-Konflikt offengelegt: pg_restore des
produktiven postgresql17-authelia.dump in eine Test-Instanz mit Wegwerf
AUTHELIA_STORAGE_ENCRYPTION_KEY scheitert im Authelia-Startup-Check mit
"the configured encryption key does not appear to be valid for this database".
Productive Storage-Werte werden mit dem produktiven Key verschluesselt; ein
Wegwerf-Key kann sie nicht entschluesseln. Smoke ist deshalb explizit auf
Config-Restore + Boot reduziert, nicht Daten-Decrypt.
Zwei Nebenbefunde aus demselben Lauf:
- AUTHELIA__SERVER__ADDRESS (Doppel-Underscore) wurde von Authelia 4.39
abgelehnt ("configuration environment variable not expected"). ENV
entfernt; server.address kommt eh aus der generierten configuration.yml.
- ntp-Startup-Check schlug fehl ("Could not determine the clock offset
... lookup time.cloudflare.com on 127.0.0.1:53: server misbehaving"),
weil das isolierte Test-Compose-Netz keinen DNS-Resolver fuer NTP hat.
Neuer Test-Config-Block setzt ntp.disable_startup_check: true.
Doku nachgezogen (Plan + Runbook): Encryption-Key-Konflikt ist explizit
als "nicht Teil dieses Smokes" dokumentiert; Fehler-Matrix hat Eintraege
fuer Doppel-Underscore-ENV und NTP-Lookup.
Frische des produktiven authelia-Dumps wird unveraendert ueber
check-restore-freshness.sh ueberwacht; Daten-Decrypt-Drill ist eine eigene
DR-Aufgabe mit kontrollierter Schluessel-Verwendung.
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
Authelia 4.39 verlangt: ohne access_control.rules muss default_policy
'two_factor' oder 'one_factor' sein. 'bypass' war nur historisch zulaessig,
mit 4.39 schlaegt config validate fehl mit "'default_policy' option
'bypass' is invalid: when no rules are specified it must be 'two_factor'
or 'one_factor'". /api/health ist public und laeuft nicht durch
access_control - die Smoke-Semantik bleibt unveraendert.
Beobachtet im Erstlauf 2026-06-03 nach Refactor auf Minimal-Testkonfig
(Commits 541c7be..440000c). Mit diesem Fix sollte 'authelia config
validate' durchlaufen; HTTP /api/health-Smoke ist der Folgeschritt.
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>