116 lines
2.7 KiB
Bash
Executable File
116 lines
2.7 KiB
Bash
Executable File
#!/bin/bash -eu
|
|
### Copyright 1999-2025. WebPros International GmbH. All rights reserved.
|
|
# Removes temporary backups older than MAX_AGE days made by deployer_lib
|
|
|
|
MAX_AGE=90 # days
|
|
FAIL2BAN_DIR='/etc/fail2ban'
|
|
MODSEC_DIR_APACHE='/etc/apache2/modsecurity.d/rules'
|
|
MODSEC_DIR_NGINX='/etc/nginx/modsecurity.d/rules'
|
|
REMOVAL_PATTERN='*.saved-*-*'
|
|
TIMESTAMP_PATTERN_SED='s/.\+\.saved-\([0-9]\{4\}\)\([0-9]\{2\}\)\([0-9]\{2\}\)T\([0-9]\{2\}\)\([0-9]\{2\}\)\([0-9]\{2\}\)-.\+$/\1-\2-\3T\4:\5:\6/'
|
|
|
|
logerror() {
|
|
IFS=' ' echo "ERROR: $*" >&2
|
|
}
|
|
|
|
logdebug() {
|
|
if [ -n "$DEBUG_MODE" ]; then
|
|
IFS=' ' echo "DEBUG: $*" >&2
|
|
fi
|
|
}
|
|
|
|
die() {
|
|
logerror "$@"
|
|
exit 1
|
|
}
|
|
|
|
# path_in <path> <directory>...
|
|
# Returns true if the path is in one of the directories.
|
|
function path_in() {
|
|
local path=$1
|
|
shift
|
|
|
|
local dir
|
|
for dir in "$@"; do
|
|
if [ "${path#$dir}" != "$path" ]; then
|
|
return 0
|
|
fi
|
|
done
|
|
return 1
|
|
}
|
|
|
|
function rm_path() {
|
|
local path=$1
|
|
|
|
if ! path_in "$path" "${DIRS[@]}"; then
|
|
die "Path '$path' is out of a permitted directory"
|
|
fi
|
|
|
|
if [ "${path%$REMOVAL_PATTERN}" = "$path" ]; then
|
|
die "Path '$path' doesn't match the removal pattern"
|
|
fi
|
|
|
|
logdebug "Removing '$path'"
|
|
$DRY_RUN rm -rf "$path"
|
|
}
|
|
|
|
function main() {
|
|
local now=$(date +%s)
|
|
local min_timestamp=$((now - MAX_AGE * 24 * 60 * 60))
|
|
logdebug "Removing temporary backups older than $(date --date="@$min_timestamp" --iso-8601=seconds) ($min_timestamp)"
|
|
while IFS= read -r -d $'\0' path; do
|
|
local timestamp_iso=$(sed "$TIMESTAMP_PATTERN_SED" <<<"$path")
|
|
local timestamp_unix
|
|
timestamp_unix=$(date --date="$timestamp_iso" +%s) || { logerror "The path '$path' doesn't have a valid timestamp, skipping" && continue; }
|
|
logdebug "Examining '$path' with timestamp $timestamp_iso ($timestamp_unix)"
|
|
if [ "$timestamp_unix" -lt "$min_timestamp" ]; then
|
|
rm_path "$path"
|
|
fi
|
|
done < <(find "${DIRS[@]}" -name "$REMOVAL_PATTERN" -print0)
|
|
}
|
|
|
|
DEBUG_MODE=""
|
|
DRY_RUN=""
|
|
|
|
while [ $# -gt 0 ]; do
|
|
case "$1" in
|
|
-h|--help)
|
|
cat <<-EOT
|
|
Usage: $0 [<options>]
|
|
Removes old temporary backups made by deployer_lib.
|
|
|
|
Options:
|
|
--debug Turn on debug mode.
|
|
--dry-run Don't actually remove anything, just show commands to be performed.
|
|
--max-age MAX_AGE Remove temporary backups older than MAX_AGE days (default: $MAX_AGE).
|
|
EOT
|
|
exit 0
|
|
;;
|
|
--debug)
|
|
DEBUG_MODE=1
|
|
shift 1
|
|
;;
|
|
--dry-run)
|
|
DRY_RUN="echo"
|
|
shift 1
|
|
;;
|
|
--max-age)
|
|
MAX_AGE=$2
|
|
shift 2
|
|
;;
|
|
*)
|
|
die "Unrecognized argument: $1"
|
|
;;
|
|
esac
|
|
done
|
|
|
|
DIRS=()
|
|
dir=""
|
|
for dir in "$FAIL2BAN_DIR" "$MODSEC_DIR_APACHE" "$MODSEC_DIR_NGINX"; do
|
|
if [ -n "$dir" -a -d "$dir" ]; then
|
|
DIRS+=("$dir")
|
|
fi
|
|
done
|
|
|
|
main
|