Fix backups Audit/Details for k8s-format archives + broken local access
Two separate bugs found while testing the Audit/Details UI against a real k8s-format backup (myapps-k8s-backup-*): 1. Format-hardcoded checks. audit_backup()'s Internal Structure and Volume Count checks assumed the legacy Docker-era archive layout (volumes/*.tar.gz, compose-files/) and would fail every k8s-format backup (per-app dirs with manifests.yaml/db-dump.sql.gz/pvc-data.tar.gz) even when it's perfectly healthy - same root cause as the myapps-backup-*/myapps-k8s-backup-* prefix bug fixed earlier, just in the audit checks instead of the listing/delete glob. cloud_backup.py's r2_audit_backup() had the identical unpatched filename regex, and app.py's /api/backups/details route had its own, which outright 400'd any k8s-format filename before even looking at it. 2. A bigger, separate bug this surfaced: get_local_backups(), get_vm_backups(), and _resolve_archive_path() all branch on RUNNING_ON_MAIN_SERVER to decide between direct filesystem access and SSH-to-self - and from inside the management-platform pod that flag's hostname check can be wrong for the pod's own ephemeral hostname depending on how it's evaluated, sending these down the SSH branch using a topology (separate warm-standby-on-the-VM SSH path) that doesn't apply to a pod that already has /root hostPath-mounted in. Fixed by trying direct filesystem access first wherever the archive would already be locally reachable, falling back to the existing SSH paths otherwise - this preserves the original warm-standby-on-VM failover design (a real second deployment of this platform on the VM host, kept reachable via SSH when the main server is down) completely unchanged; it only adds the fast local path for the case where the caller already has direct filesystem access. Verified against both a real k8s-format backup (odoo, single-app) and a real legacy-format backup on disk - both audit correctly now, with format-appropriate checks and labels. Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_017avLHFqkiti3g62Anq9sVA
This commit is contained in:
@@ -345,10 +345,12 @@ def r2_audit_backup(key: str) -> dict:
|
||||
else:
|
||||
report["checks"].append(f"✅ File size looks healthy ({_human_size(size)})")
|
||||
|
||||
# Check 5: Filename format
|
||||
# Check 5: Filename format — accepts both the legacy Docker-era
|
||||
# lineage (myapps-backup-*) and the k8s-native one
|
||||
# (myapps-k8s-backup-*, from backup-k8s-apps.sh).
|
||||
import re
|
||||
filename = key.replace("backups/", "")
|
||||
if re.match(r"myapps-backup-\d{8}_\d{6}\.tar\.gz", filename):
|
||||
if re.match(r"myapps-(k8s-)?backup-\d{8}_\d{6}\.tar\.gz", filename):
|
||||
report["checks"].append("✅ Filename format is valid")
|
||||
else:
|
||||
report["warnings"].append(f"⚠️ Unexpected filename format: {filename}")
|
||||
|
||||
Reference in New Issue
Block a user