Deterministischer Abgleich zwischen DMS file_revisions und Objekt-Storage-Verzeichnis, existenz-only (keine Inhaltspruefung, saubere Abgrenzung zu BAK-08). Report sortiert nach storage_key fuer stabile Weiterverarbeitung durch BAK-08. Systemd-Timer taeglich, real auf 192.168.1.131 verdrahtet und ausgeloest.
5.4 KiB
BAK-05 – Prüfprotokoll: Reconciliation / Konsistenzprüfung Storage vs. DB
Voraussetzung BAK-01, BAK-02 (Welle 1) – erledigt, siehe eigene Protokolle.
Grundsatzentscheidung: reine Funktion + zwei Quell-Adapter
internal/reconcile.Reconcile ist eine reine Funktion ohne DB-/Storage-
Zugriff (leicht ohne echte Infrastruktur testbar), die Ein- und
Auslesen echter Systeme ist strikt in sources.go getrennt
(ListDBStorageKeys gegen echtes Postgres, ListStorageObjects gegen
echtes Dateisystem). Beide Seiten liefern nur SCHLÜSSEL – niemals Inhalt
– dadurch bleibt BAK-05 sauber getrennt von BAK-08 (Inhalts-/Prüfsummen-
verifikation, eigene Fehlerklasse, eigenes Ticket).
Report-Format bewusst deterministisch: beide Ergebnislisten
(missing_in_storage, orphaned_in_storage) nach storage_key
aufsteigend sortiert, damit BAK-08 später dieselbe Objektliste als
stabile Stichprobenquelle weiterverarbeiten kann, ohne selbst neu zu
sortieren/filtern (Nutzervorgabe).
Meldeweg über OPS-05 (wie später BAK-08) wurde als offene Design-Frage
aufgeworfen, aber nicht zur Vorbedingung gemacht – hier bewusst noch
nicht umgesetzt (kein OPS-05-Abhängigkeitseintrag im Board für BAK-05);
Report wird aktuell nur als JSON auf stdout ausgegeben und per
Exit-Code (1 bei Abweichungen) für systemd/Monitoring sichtbar gemacht.
Anbindung an OPS-05 kann bei Bedarf nachgezogen werden, ohne
Reconcile selbst zu ändern.
Umsetzung
internal/reconcile.Reconcile(dbEntries, storageKeys) Report– reine Vergleichsfunktion, liefertMissingInStorage/OrphanedInStorage,Report.IsClean()als eindeutiges Sauber-Merkmal.internal/reconcile.ListDBStorageKeys– liestfile_revisions(DMS FDN-02) per direktem SQL aus derselben physischen Tenant-DB (Modell C, Core TEN-01) – kein Import von DMS-Go-Paketen möglich (eigenes Go-Modul), daher reiner SQL-Zugriff gegen das dokumentierte Schema.internal/reconcile.ListStorageObjects– durchläuft den lokalen FDN-03-LocalDriver-Basisordner (filepath.WalkDir), liefertnil, nilbei fehlendem Verzeichnis statt Fehler (noch keine Objekte ist kein Fehlerzustand).cmd/reconcile-cli– liestNEXARCH_RECONCILE_TENANT_DSNundNEXARCH_RECONCILE_STORAGE_DIR, gibt Report als JSON auf stdout aus, Exit-Code 1 bei Abweichungen.
Prüfungen
| # | Prüfung | Ergebnis |
|---|---|---|
| 1 | Datenbankeintrag ohne Storage-Objekt wird erkannt | bestanden — TestReconcile_DetectsMissingInStorage |
| 2 | Storage-Objekt ohne Datenbankeintrag wird erkannt | bestanden — TestReconcile_DetectsOrphanedInStorage |
| 3 | Lauf ohne Abweichungen liefert leeren, eindeutig sauberen Bericht | bestanden — TestReconcile_CleanRunProducesEmptyReport (zusätzlich IsClean()-Konsistenzprüfung) |
Zusätzlich (Nutzervorgaben, nicht explizit im Ticket als Pflichtprüfung benannt, aber zentral für die Abgrenzung/Weiterverwendbarkeit):
TestReconcile_ExistingButCorruptedObjectProducesNoFinding– Nachweis, dass Reconcile AUSSCHLIESSLICH Existenz prüft, niemals Inhalt (Trennung von BAK-08).TestReconcile_DeterministicOrdering– zwei Läufe mit identischer Eingabe liefern identische Reihenfolge, aufsteigend nachstorage_key.TestListDBStorageKeys_ReadsRealFileRevisions– liest echt gegen die gemeinsame Tenant-Testdatenbankdms_tenant_test(reales DMS-FDN-02- Schema, kein Mock).TestListStorageObjects_WalksRealDirectory/_MissingDirectoryReturnsEmpty– echtes Dateisystem, kein Mock.
Echte Verdrahtung auf 192.168.1.131
reconcile-cligebaut nach/opt/nexarch-archive/bin//etc/nexarch/archive-reconcile.env(0600):NEXARCH_RECONCILE_TENANT_DSNzeigt auf die gemeinsame Tenant-Testdatenbankdms_tenant_test(DMS selbst läuft auf 192.168.1.131 noch nicht als eigener systemd- Dienst mit persistenter Konfiguration – dies ist die real verfügbare Tenant-DB mit echtem FDN-02-Schema, dokumentierter bekannter Stand, kein stiller Mock);NEXARCH_RECONCILE_STORAGE_DIRzeigt auf/var/nexarch-archiv/dms-objects(persistentes ZFS-Dataset, NICHT/var/nexarch-test/).- Timer
nexarch-archive-reconcile.timerinstalliert und aktiviert (täglich 05:00 UTC),systemctl list-timersbestätigt scharf. systemctl start nexarch-archive-reconcile.servicereal ausgelöst:status=0/SUCCESS, Journal zeigt echten JSON-Report (missing_in_storage: null, orphaned_in_storage: null– Tenant-DB aktuell leer, daher sauberer Bericht, keine synthetische Ausgabe).
Build/Test-Ergebnis (192.168.1.131, make check)
go build ./... -> clean
go vet ./... -> clean
golangci-lint run ./... -> 0 issues
go test ./... -p 1 -count=1 -> 3/3 Pakete mit Tests ok (internal/backup, internal/objectbackup, internal/reconcile), 0 Fehlschläge
internal/reconcile-Tests separat mit gesetzter TEST_TENANT_DSN gegen
dms_tenant_test verifiziert: 8/8 Tests bestanden (5 reine
Reconcile-Tests + 3 sources.go-Integrationstests).
Gesamtergebnis
Bestanden. Alle drei Akzeptanzkriterien und alle Pflicht- sowie
Nutzervorgaben-Prüfungen real erfüllt (echte Postgres-Instanz, echtes
Dateisystem, echter systemd-Lauf). Zwei Testfehler während der
Entwicklung (Schema-Abweichung revision_number NOT NULL in der realen
dms_tenant_test-Tabelle; inkonsistente Fixture-Daten in
TestReconcile_DeterministicOrdering) gefunden und korrigiert – beide
waren Testautorenfehler, keine Fehler in Reconcile selbst.