#!/usr/bin/env bash
# backup/restore-site -- restore both the files and the database of a site
#
# Restoring files overwrites the live document root, so the current state is
# snapshotted first and the operator must type the domain back.
set -o pipefail
SELF=$(readlink -f "${BASH_SOURCE[0]}")
NV_BASE=$(cd "$(dirname "$SELF")/../../.." && pwd)
export NV_BASE
# shellcheck source=/dev/null
. "$NV_BASE/lib/core/bootstrap.sh"

nv_require_root || exit 1
ui_header "$(t backup_m_restoresite)"

mapfile -t snapshots < <(find "$NV_BACKUP_ROOT" -mindepth 1 -maxdepth 1 -type d \
    \( -name '*.site-*' -o -name '*.pre-update-*' -o -name '*.pre-search-replace-*' -o -name '*.auto-*' \) \
    -printf '%f\n' 2>/dev/null | sort -r | head -n 20)

if [ ${#snapshots[@]} -eq 0 ]; then
    ui_info "$(t backup_restore_site_none)"
    exit 0
fi

i=0
for s in "${snapshots[@]}"; do
    i=$((i + 1))
    printf '  %2d) %-46s %s\n' "$i" "$s" "$(du -sh "$NV_BACKUP_ROOT/$s" 2>/dev/null | cut -f1)"
done
printf '  %2d) %s\n' 0 "$(t menu_back)"
ui_blank

printf '  %s: ' "$(t backup_pick_set)"
read -r pick || exit 130
case $pick in ''|*[!0-9]*) ui_err "$(t ui_invalid_number)"; exit 2 ;; esac
[ "$pick" -eq 0 ] && exit 0
[ "$pick" -lt 1 ] || [ "$pick" -gt ${#snapshots[@]} ] && { ui_err "$(t menu_invalid)"; exit 2; }

set_dir="$NV_BACKUP_ROOT/${snapshots[$((pick - 1))]}"
ui_section "$set_dir"
ls -1 "$set_dir" | sed 's/^/  /'
ui_blank

printf '  %s: ' "$(t site_prompt_domain)"
read -r domain || exit 130
domain=$(nv_lower "$(nv_trim "$domain")")
nv_valid_domain "$domain" || { ui_err "$(t site_bad_domain "$domain")"; exit 2; }

sql="$set_dir/$domain.sql.gz"
files="$set_dir/$domain.files.tar.gz"
[ -f "$sql" ] || [ -f "$files" ] || { ui_err "$(t backup_restore_no_match "$domain")"; exit 2; }

root=$(nv_site_get "$domain" root_path "/home/$domain/public_html")
db=$(nv_site_get "$domain" db_name "")
[ -n "$db" ] || db=$domain

ui_blank
ui_warn "$(t backup_restore_site_warn "$domain" "$root")"
ui_confirm_typed "$(t backup_restore_confirm)" "$domain" || { ui_info "$(t pf_cancelled)"; exit 3; }

nv_lock_acquire "site:$domain" 10 || { nv_fail 6199 "$(t lock_busy "$domain")"; exit 1; }

safety=$(site_snapshot "$domain" "pre-restore-$domain")
[ -n "$safety" ] && ui_ok "$(t backup_safety_at "$safety")"

if [ -f "$files" ]; then
    ui_step "$(t backup_restore_files)"
    install -d -m 0755 "/home/$domain"
    if tar xzf "$files" -C "/home/$domain" 2>/dev/null; then
        chown -R "$(site_web_user "$domain"):$(site_web_user "$domain")" "/home/$domain" 2>/dev/null || true
        ui_ok "$(t backup_restore_files_ok)"
    else
        ui_err "$(t backup_restore_files_failed)"
    fi
fi

if [ -f "$sql" ] && db_available; then
    ui_step "$(t backup_restore_db_running)"
    if gunzip -c "$sql" | mariadb --protocol=socket -u root "$db" 2>/dev/null; then
        ui_ok "$(t backup_restore_ok "$db")"
    else
        ui_err "$(t backup_restore_failed)"
    fi
fi

nv_trace backup-restore-site "$domain <- $set_dir"
nv_lock_release "site:$domain"
ui_blank
ui_ok "$(t backup_restore_site_done "$domain")"
ui_info "$(t backup_restore_safety "$safety")"
exit 0
