#!/usr/bin/env bash set -euo pipefail PATH="/usr/local/bin:/usr/bin:/bin:/usr/sbin:/sbin:${PATH:-}" SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" ROOT_DIR="$(cd "${SCRIPT_DIR}/../.." && pwd)" ENV_FILE="${ROOT_DIR}/.env" BACKUP_DIR="${BACKUP_DIR:-/volume1/naurua_db_backups/dev}" FILE_PREFIX="${FILE_PREFIX:-erpnaurua_dev}" PG_DUMP_BIN="${PG_DUMP_BIN:-$(command -v pg_dump || true)}" PSQL_BIN="${PSQL_BIN:-$(command -v psql || true)}" DOCKER_BIN="${DOCKER_BIN:-$(command -v docker || true)}" COMPOSE_FILE="${COMPOSE_FILE:-${ROOT_DIR}/scripts/db/backup-client/docker-compose.yml}" if [[ ! -f "${ENV_FILE}" ]]; then echo "Missing environment file: ${ENV_FILE}" >&2 exit 1 fi set -a # shellcheck disable=SC1090 . "${ENV_FILE}" set +a for required_var in DB_HOST DB_PORT DB_NAME DB_USER DB_PASSWORD; do if [[ -z "${!required_var:-}" ]]; then echo "Missing required database setting: ${required_var}" >&2 exit 1 fi done if [[ -z "${DOCKER_BIN}" || ! -x "${DOCKER_BIN}" ]]; then echo "Docker is required for the PostgreSQL client container." >&2 exit 1 fi if [[ ! -f "${COMPOSE_FILE}" ]]; then echo "Missing backup compose file: ${COMPOSE_FILE}" >&2 exit 1 fi mkdir -p "${BACKUP_DIR}" timestamp="$(date +%Y%m%d_%H%M%S)" output_file="${BACKUP_DIR}/${FILE_PREFIX}_${DB_NAME}_${timestamp}.dump" temporary_file="${output_file}.tmp" cleanup() { rm -f "${temporary_file}"; } trap cleanup EXIT export BACKUP_DIR "${DOCKER_BIN}" compose --file "${COMPOSE_FILE}" run --rm --no-deps -T backup if [[ ! -s "${BACKUP_DIR}/current.dump" ]]; then echo "Backup failed: container dump file is empty." >&2 exit 1 fi mv -f "${BACKUP_DIR}/current.dump" "${temporary_file}" if [[ ! -s "${temporary_file}" ]]; then echo "Backup failed: dump file is empty." >&2 exit 1 fi mv -f "${temporary_file}" "${output_file}" trap - EXIT find "${BACKUP_DIR}" -maxdepth 1 -type f -name "${FILE_PREFIX}_${DB_NAME}_*.dump" \ -printf '%T@ %p\n' | sort -nr | tail -n +21 | cut -d' ' -f2- | xargs -r rm -f printf '%s\n' "Backup created: ${output_file}"