#!/usr/bin/env bash # PgBackrest backup wrapper script ## FUNCTIONS # METHOD: convert_time # PARAMS: timestamp in seconds or with milliseconds (nnnn.nnnn) # RETURN: formated string with human readable time (d/h/m/s) # CALL : var=$(convert_time $timestamp); # DESC : converts a timestamp or a timestamp with float milliseconds # to a human readable format # output is in days/hours/minutes/seconds function convert_time { timestamp=${1}; # round to four digits for ms timestamp=$(printf "%1.4f" "$timestamp"); # get the ms part and remove any leading 0 ms=$(echo "${timestamp}" | cut -d "." -f 2 | sed -e 's/^0*//'); timestamp=$(echo "${timestamp}" | cut -d "." -f 1); timegroups=(86400 3600 60 1); # day, hour, min, sec timenames=("d" "h" "m" "s"); # day, hour, min, sec output=( ); time_string=""; for timeslice in "${timegroups[@]}"; do # floor for the division, push to output output[${#output[*]}]=$(awk "BEGIN {printf \"%d\", ${timestamp}/${timeslice}}"); timestamp=$(awk "BEGIN {printf \"%d\", ${timestamp}%${timeslice}}"); done; for ((i=0; i<${#output[@]}; i++)); do if [ "${output[$i]}" -gt 0 ] || [ -n "$time_string" ]; then if [ -n "${time_string}" ]; then time_string=${time_string}" "; fi; time_string=${time_string}${output[$i]}${timenames[$i]}; fi; done; if [ -n "${ms}" ] && [ "${ms}" != "nan" ] && [ "${ms}" -gt 0 ]; then time_string=${time_string}" ${ms}ms"; fi; # just in case the time is 0 if [ -z "${time_string}" ]; then time_string="0s"; fi; echo -n "${time_string}"; } ## VARIABLES BACKUP_TYPE=""; OVERRIDE_STANZA=""; LIST_STANZA=0; TEST=0; sudo_user="pgbackrest"; # testweb (replaces kome) (aws2/ohio) # zac fte (aws2/tokyo) # sushi database # udon core # mailing-service-a (aws2/oregon) # url-redirect-logging (aws9/tokyo) # mrktsec (aws3/tokyo) # instawin (aws8/tokyo) stanza_list="testwebegplusww zacfte sushidatabase udoncore mailingservicea urlredirectlogging mrktsec instawin"; PRINTF_BLOCK="=== [%-8s: %19s] ==[%s]===============>\n"; ## OPT PARSEIN while getopts ":b:s:lt" opt; do case "${opt}" in b) # backuptype BACKUP_TYPE="${OPTARG}"; ;; s) # stanza OVERRIDE_STANZA="${OPTARG}"; ;; l) # list LIST_STANZA=1; ;; t) # test TEST=1; ;; :) echo "Option -$OPTARG requires an argument." ;; \?) echo -e "\n Option does not exist: ${OPTARG}\n"; echo "-b (backuptype): full/diff"; echo "-s (stanza): override stanza name, must be in list" echo "-l list available stanza" echo "-t test run" exit 1; ;; esac; done; ## SCRIPT if [ $TEST -eq 1 ]; then echo "[..........] TEST RUN ONLY"; fi; if [ $LIST_STANZA -eq 1 ]; then echo "+ Stanza List:"; for stanza in ${stanza_list}; do echo "${stanza}"; done; exit; fi; if [ -z "${BACKUP_TYPE}" ]; then echo "[!] Backup type must be set as -b full or -b diff"; exit; fi; if [ "${BACKUP_TYPE}" != "full" ] && [ "${BACKUP_TYPE}" != "diff" ]; then echo "[!] Backup type can only be 'full' or 'diff'"; exit; fi; echo "* PgBackrest Backup run type '${BACKUP_TYPE}' on $(date +'%F')"; SET_OVERRIDE_STANZA=0; # if we have override single host if [ -n "${OVERRIDE_STANZA}" ]; then echo "+ Set override stanza too: ${OVERRIDE_STANZA}"; for stanza in ${stanza_list}; do if [ "${stanza}" = "${OVERRIDE_STANZA}" ]; then stanza_list="${OVERRIDE_STANZA}"; SET_OVERRIDE_STANZA=1; break; fi; done; if [ $SET_OVERRIDE_STANZA = 0 ]; then echo "[!!!] Failed to set override stanza: ${OVERRIDE_STANZA}"; exit; fi; fi; # run backup for stanza in ${stanza_list}; do START=$(date +'%s'); # shellcheck disable=SC2059 printf "${PRINTF_BLOCK}" "START" "$(date +'%F %T')" "${stanza}"; # --log-level-console=info if [ $TEST -eq 1 ]; then echo "sudo -u ${sudo_user} pgbackrest --type=${BACKUP_TYPE} --stanza=${stanza} backup;"; else sudo -u ${sudo_user} pgbackrest --type="${BACKUP_TYPE}" --stanza="${stanza}" backup; fi; DURATION=$(( $(date +'%s')-START )); # shellcheck disable=SC2059 printf "${PRINTF_BLOCK}" "END" "$(convert_time ${DURATION})" "${stanza}"; done; echo "* PgBackrest Backup end"; if [ $TEST -eq 1 ]; then echo "[..........] TEST RUN ONLY"; fi; ## __END__