File: //bigscoots/wpo/backups/hourly-backup-cleanup.sh
#!/bin/bash
# hourly-backup-cleanup.sh
# Retains last N backups (default: 24), then 1 per day after that
# Usage:
# ./hourly-backup-cleanup.sh # local, keep 24
# ./hourly-backup-cleanup.sh --remote # remote, keep 24
# ./hourly-backup-cleanup.sh --keep 36 # local, keep 36
# ./hourly-backup-cleanup.sh --remote --keep 48
# Default values
IS_REMOTE="no"
KEEP_HOURS=24
# Parse arguments
while [[ $# -gt 0 ]]; do
case "$1" in
--remote)
IS_REMOTE="yes"
shift
;;
--keep)
KEEP_HOURS="$2"
shift 2
;;
*)
echo "Unknown option: $1"
echo "Usage: $0 [--remote] [--keep <hours>]"
exit 1
;;
esac
done
cleanup_backups() {
local PATH_TYPE="$1" # "local" or "remote"
local BACKUP_PATH="$2"
declare -A seen_dates
local count=0
if [[ "$PATH_TYPE" == "remote" ]]; then
if [[ -z "$BKUSER" || -z "$BKSVR" || -z "$RSYNCLOCATION" ]]; then
echo "Missing required remote variables: BKUSER, BKSVR, RSYNCLOCATION"
exit 1
fi
SSH_CMD="ssh -oStrictHostKeyChecking=no -i ${HOME}/.ssh/wpo_backups ${BKUSER}@${BKSVR}"
backups=$($SSH_CMD "ls -1 ${BACKUP_PATH} | grep '^back-' | sort")
else
backups=$(ls -1 "$BACKUP_PATH" | grep '^back-' | sort)
fi
total_backups=$(echo "$backups" | wc -l)
while read -r backup; do
backup_date=$(echo "$backup" | grep -oP '\d{4}-\d{2}-\d{2}')
[ -z "$backup_date" ] && continue
if [ $((total_backups - count)) -le "$KEEP_HOURS" ]; then
seen_dates["$backup_date"]=1
((count++))
continue
fi
if [[ -z ${seen_dates["$backup_date"]} ]]; then
seen_dates["$backup_date"]=1
((count++))
continue
fi
echo "Removing $PATH_TYPE backup: $backup"
if [[ "$PATH_TYPE" == "remote" ]]; then
$SSH_CMD "rm -rf ${BACKUP_PATH}/$backup"
else
rsync -a --delete /backup/empty/ "$BACKUP_PATH/$backup/"
rm -rf "$BACKUP_PATH/$backup"
fi
((count++))
done <<< "$backups"
}
if [[ "$IS_REMOTE" == "yes" ]]; then
cleanup_backups "remote" "$RSYNCLOCATION"
else
cleanup_backups "local" "/backup"
fi