#!/usr/bin/env bash
#
# PLOCAL Phase 5I-B5 — safe, repeatable MySQL backup wrapper.
#
# Refuses to run unless every required variable is explicitly set — it
# never silently defaults to plocal_local, root, or localhost. No
# password is ever accepted on the command line or embedded in this
# script; credentials come only from a --defaults-extra-file the caller
# already prepared with mode 0600.
#
# Required environment variables:
#   PLOCAL_MYSQL_OPTION_FILE  path to a 0600 MySQL client option file
#                             (see tools/README or the deployment
#                             runbook for the [client] section shape)
#   PLOCAL_BACKUP_DB          exact source database name — no default
#   PLOCAL_BACKUP_DEST_DIR    directory the dump/checksum are written to
#
# Explicitly refused database names (never a valid PLOCAL_BACKUP_DB):
#   plocal_local, plocal_local_test
#
# Usage:
#   PLOCAL_MYSQL_OPTION_FILE=/path/to/opts.cnf \
#   PLOCAL_BACKUP_DB=plocal_a4_cleanroom_20260818 \
#   PLOCAL_BACKUP_DEST_DIR=/path/to/backups \
#   tools/plocal-db-backup.sh

set -euo pipefail

if [[ -z "${PLOCAL_MYSQL_OPTION_FILE:-}" ]]; then
    echo "Refusing: PLOCAL_MYSQL_OPTION_FILE is not set." >&2
    exit 2
fi
if [[ ! -f "${PLOCAL_MYSQL_OPTION_FILE}" ]]; then
    echo "Refusing: PLOCAL_MYSQL_OPTION_FILE does not exist: ${PLOCAL_MYSQL_OPTION_FILE}" >&2
    exit 2
fi
option_file_mode="$(stat -c '%a' "${PLOCAL_MYSQL_OPTION_FILE}")"
if [[ "${option_file_mode}" != "600" ]]; then
    echo "Refusing: PLOCAL_MYSQL_OPTION_FILE must be mode 0600, found ${option_file_mode}." >&2
    exit 2
fi

if [[ -z "${PLOCAL_BACKUP_DB:-}" ]]; then
    echo "Refusing: PLOCAL_BACKUP_DB is not set (no default is ever assumed)." >&2
    exit 2
fi
case "${PLOCAL_BACKUP_DB}" in
    plocal_local|plocal_local_test)
        echo "Refusing: '${PLOCAL_BACKUP_DB}' is a protected database and may never be a backup source target for this tool." >&2
        exit 2
        ;;
esac

if [[ -z "${PLOCAL_BACKUP_DEST_DIR:-}" ]]; then
    echo "Refusing: PLOCAL_BACKUP_DEST_DIR is not set." >&2
    exit 2
fi
mkdir -p "${PLOCAL_BACKUP_DEST_DIR}"
chmod 0700 "${PLOCAL_BACKUP_DEST_DIR}"

timestamp="$(date -u +%Y%m%dT%H%M%SZ)"
dump_file="${PLOCAL_BACKUP_DEST_DIR}/${PLOCAL_BACKUP_DB}_${timestamp}.sql.gz"
checksum_file="${dump_file}.sha256"

echo "Backing up '${PLOCAL_BACKUP_DB}' -> ${dump_file}"

mysqldump \
    --defaults-extra-file="${PLOCAL_MYSQL_OPTION_FILE}" \
    --single-transaction --quick --routines --triggers --no-tablespaces \
    "${PLOCAL_BACKUP_DB}" | gzip -c > "${dump_file}"

chmod 0600 "${dump_file}"

size_bytes="$(stat -c '%s' "${dump_file}")"
if [[ "${size_bytes}" -eq 0 ]]; then
    echo "FAIL: dump file is zero bytes — treating as a failed backup." >&2
    rm -f "${dump_file}"
    exit 1
fi

sha256sum "${dump_file}" > "${checksum_file}"
chmod 0600 "${checksum_file}"

echo "PASS: backup written (${size_bytes} bytes)."
echo "PASS: checksum written: $(cat "${checksum_file}")"
echo "${dump_file}"
