Draft ZFS snapshot utility
authorSergey Matveev <stargrave@stargrave.org>
Sat, 2 May 2020 14:08:24 +0000 (17:08 +0300)
committerSergey Matveev <stargrave@stargrave.org>
Mon, 4 May 2020 15:33:36 +0000 (18:33 +0300)
bin/bin/zsnap.zsh [new file with mode: 0755]

diff --git a/bin/bin/zsnap.zsh b/bin/bin/zsnap.zsh
new file mode 100755 (executable)
index 0000000..a14979b
--- /dev/null
@@ -0,0 +1,69 @@
+#!/bin/zsh -e
+
+usage() {
+cat <<EOF
+Usage: $0 DATASET@SNAPPREFIX snap-initial
+       $0 DATASET@SNAPPREFIX snap
+       $0 DATASET@SNAPPREFIX sync-initial DST
+       $0 DATASET@SNAPPREFIX sync DST
+       $0 DATASET@SNAPPREFIX clean COUNT
+EOF
+exit 1
+}
+
+enccmd="gpg --compress-level 0 --encrypt --recipient offline --cipher-algo AES-128"
+
+[ $# -ge 2 ] || usage
+
+what="$1"
+action="$2"
+
+now=$(date "+%Y%m%d%H%M")
+snaps=$(zfs list -t snap -d 1 -o name -H | grep $what | sort -nr)
+latest=$(echo $snaps | sed -n 1p)
+
+case "$action" in
+    snap-initial)
+        zfs snap -r $what-$now
+        echo $what-$now
+        ;;
+    snap)
+        [ -n "$latest" ]
+        [ "$what-$now" != "$latest" ]
+        zfs snap -r $what-$now
+        echo $what-$now
+        ;;
+    sync-initial)
+        dst="$3"
+        [ -d "$dst" ] || usage
+        set PIPE_FAIL
+        zfs send -Rv $latest | zstd | ${=enccmd} > $dst/$latest.zfs.zst.gpg
+        sync
+        touch $dst/$latest.from
+        ;;
+    sync)
+        dst="$3"
+        [ -d "$dst" ] || usage
+        latest_dst=$(find $dst -type f -name "*.from" | sort -rn | sed -n 1p)
+        [ -n "$latest_dst" ]
+        latest_dst=$(basename ${latest_dst%.from})
+        [ "$latest_dst" != "$latest" ]
+        set PIPE_FAIL
+        zfs send -Rv -i $latest_dst $latest | zstd | ${=enccmd} > $dst/$latest.zfs.zst.gpg
+        sync
+        echo "$latest_dst" > $dst/$latest.from
+        ;;
+    clean)
+        count="$3"
+        [ -n "$count" ] || usage
+        count=$(( $count + 1 ))
+        for snap in $(echo $snaps) ; do
+            count=$(( $count - 1 ))
+            [ $count -le 0 ] || continue
+            zfs destroy -Rv $snap
+        done
+        ;;
+    *)
+        usage
+        ;;
+esac