91 lines
2.1 KiB
Bash
Executable File
91 lines
2.1 KiB
Bash
Executable File
#! /bin/sh
|
|
|
|
# change this to the name of your ZFS pool.
|
|
zpool="zroot"
|
|
|
|
# names of the DATASETs to exclude (datasets, not mountpoints!)
|
|
# can override this list at runtime with EXCLUDES envvar.
|
|
# can extend this list at runtime with EXTRA_EXCLUDES envvar.
|
|
excludes="/usr/ports /usr/src /backups"
|
|
|
|
|
|
# You do not want to edit anything below here
|
|
|
|
tstamp=`date +%Y%m%d-%H%M%S`
|
|
label_pfx="zbk-"
|
|
usrlabel=$1
|
|
maxnum=$2
|
|
|
|
usage () {
|
|
echo Usage:
|
|
echo "zfssnap [label [maxnum]]"
|
|
echo "default label: 'default'"
|
|
echo "default maxnum: infinite"
|
|
echo "Takes a ZFS snapshot with given custom label."
|
|
echo "If maxnum specified, keeps the so-many newest snaps only."
|
|
echo
|
|
echo "Optional envvars:"
|
|
echo "EXCLUDES list of dataset paths to exclude from snaps. Overrides default."
|
|
echo "EXTRA_EXCLUDES list of dataset paths to exclude from snaps. Extends default."
|
|
echo "default excluded DATASET paths:"
|
|
echo $excludes
|
|
}
|
|
|
|
# build list of dataset paths to exclude
|
|
if [ "x$EXCLUDES" != x ]
|
|
then
|
|
excludes=$EXCLUDES
|
|
elif [ "x$EXTRA_EXCLUDES" != x ]
|
|
then
|
|
excludes="$excludes $EXTRA_EXCLUDES"
|
|
fi
|
|
|
|
# label
|
|
if [ "x$usrlabel" != "x" ]
|
|
then
|
|
if echo "$usrlabel" | grep -qiE '^([a-z0-9]{1,10})$'
|
|
then
|
|
label_pfx="$label_pfx$usrlabel"
|
|
else
|
|
echo "Invalid label '$usrlabel'! Quitting."
|
|
usage
|
|
exit 1
|
|
fi
|
|
else
|
|
label_pfx="${label_pfx}default"
|
|
fi
|
|
|
|
# maxnum
|
|
if [ "x$maxnum" != "x" ]
|
|
then
|
|
if ! echo "$maxnum" | grep -qE '^[0-9]+$'
|
|
then
|
|
echo "Invalid maxnum '$maxnum'! Terminating."
|
|
usage
|
|
exit 1
|
|
fi
|
|
fi
|
|
|
|
|
|
# add timestamp to label
|
|
label="${label_pfx}-$tstamp"
|
|
|
|
# take recursive snap
|
|
zfs snapshot -r $zpool@$label || exit $?
|
|
# exclude folders
|
|
for xm in $excludes
|
|
do
|
|
# let this fail, the ds might not exist
|
|
zfs destroy -r $zpool$xm@$label
|
|
done
|
|
|
|
# prune dbs if requested
|
|
if [ "x$maxnum" != x ]
|
|
then
|
|
ls /.zfs/snapshot/ | sort -rt- -k 3,4 | awk -v maxnum=$maxnum -v matchlabel=$label_pfx 'BEGIN {x=0} $0 ~ "^"matchlabel { x++; if (x>maxnum) print}' | while read snapname
|
|
do
|
|
zfs destroy -r $zpool@$snapname || exit $?
|
|
done
|
|
fi
|
|
|