#!/usr/bin/env bash
set -euo pipefail

REPO_ROOT="$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)"
HOMELAB_STATE_DIR="${HOMELAB_STATE_DIR:-${XDG_DATA_HOME:-${HOME}/.local/share}/homelab}"
SNAPSHOT_DIR="${HOMELAB_RELEASE_SNAPSHOT_DIR:-${HOMELAB_STATE_DIR}/release-snapshots}"
TIMESTAMP="$(date -u +%Y%m%dT%H%M%SZ)"
REPORT="${SNAPSHOT_DIR}/release-snapshot-${TIMESTAMP}.txt"

mkdir -p "$SNAPSHOT_DIR"
exec > >(tee "$REPORT") 2>&1

section() {
    printf '\n== %s ==\n' "$1"
}

have() {
    command -v "$1" >/dev/null 2>&1
}

run_optional() {
    local description="$1"
    shift

    section "$description"
    if "$@"; then
        return 0
    fi

    printf 'warn: %s unavailable or failed\n' "$description"
}

latest_file() {
    local dir="$1"
    local pattern="$2"

    if [ -d "$dir" ]; then
        find "$dir" -maxdepth 1 -type f -name "$pattern" -print 2>/dev/null | sort | tail -1
    fi
}

section "Snapshot Metadata"
printf 'created_utc=%s\n' "$TIMESTAMP"
printf 'report=%s\n' "$REPORT"
printf 'repo=%s\n' "$REPO_ROOT"
printf 'host=%s\n' "$(hostname 2>/dev/null || echo unknown)"

section "Git State"
git -C "$REPO_ROOT" rev-parse --abbrev-ref HEAD
git -C "$REPO_ROOT" rev-parse HEAD
git -C "$REPO_ROOT" status --short
git -C "$REPO_ROOT" log --oneline -5

if have kubectl; then
    run_optional "Kubernetes Nodes" kubectl get nodes -o wide
    run_optional "Kubernetes Problem Pods" sh -c \
        'kubectl get pods -A --field-selector=status.phase!=Running,status.phase!=Succeeded -o wide'
    run_optional "Argo CD Applications" sh -c \
        'kubectl -n argocd get applications.argoproj.io -o custom-columns=NAME:.metadata.name,SYNC:.status.sync.status,HEALTH:.status.health.status,REVISION:.status.sync.revision,PATH:.spec.source.path --no-headers'
    run_optional "Workload Images" sh -c \
        'kubectl get deploy,statefulset,daemonset -A -o jsonpath="{range .items[*]}{.metadata.namespace}{\"/\"}{.metadata.name}{\"\\t\"}{range .spec.template.spec.containers[*]}{.image}{\" \"}{end}{\"\\n\"}{end}"'
else
    section "Kubernetes"
    echo "kubectl not installed; skipping Kubernetes snapshot."
fi

if have helm; then
    run_optional "Helm Releases" helm list -A
else
    section "Helm Releases"
    echo "helm not installed; skipping Helm release snapshot."
fi

section "Backup Pointers"
state_backup="$(latest_file "${HOMELAB_TOFU_STATE_BACKUP_DIR:-${HOMELAB_STATE_DIR}/tofu-state-backups}" 'tofu-state-*.tgz' || true)"
gitea_backup="$(latest_file "${LAB_GITEA_BACKUP_DIR:-/home/jv/backups/gitea}" 'gitea-*.zip' || true)"
printf 'latest_tofu_state_backup=%s\n' "${state_backup:-missing}"
printf 'latest_gitea_backup=%s\n' "${gitea_backup:-missing}"

section "Public URLs"
for url in "${LAB_PUBLIC_URL:-https://lab2025.duckdns.org/}" "${LAB_GITEA_URL:-https://lab2025.duckdns.org/git/jv/my-homelab-configs}"; do
    if have curl; then
        status="$(curl -k -sS -o /dev/null -w '%{http_code}' --max-time 10 "$url" 2>/dev/null || true)"
        printf '%-60s http=%s\n' "$url" "${status:-none}"
    else
        printf '%-60s curl not installed\n' "$url"
    fi
done

section "Next Actions"
cat <<EOF
Before applying risky changes:
1. Review this report for dirty Git state, unhealthy apps, or missing backups.
2. Run ./jeannie state-backup if latest_tofu_state_backup is missing or old.
3. Run ./jeannie backup-gitea if latest_gitea_backup is missing or old.
4. Keep this report path with the change notes: $REPORT
EOF
