mirror of
https://github.com/bashclub/bashclub-zfs-push-pull.git
synced 2024-12-23 21:20:13 +01:00
Implement catchup mode to fix interrupted transfer
When zfs send -R is interrupted, some child filesystems will be at a more recent snapshot than their parent. There's then no way to do a zfs send -R from the root/parent, as the children are inconsistent. Catchup mode handles recursion on its own, instead of relying on zfs to do it. Basically picking a single consistent snapshot across the board, then bringing all to that level.
This commit is contained in:
parent
6d906ad640
commit
fcd5fb0e08
28
backup-zfs
28
backup-zfs
@ -57,6 +57,22 @@ ZFS() {
|
||||
fi
|
||||
}
|
||||
|
||||
# If initial zfs send -R is interrupted, it can't be resumed.
|
||||
# Rolling back all filesystems to the last consistent snapshot ought
|
||||
# to do the trick, but that's annoying to throw that data away.
|
||||
catchup() {
|
||||
srcparent="${srcfs%/*}" # all but last child component of srcfs
|
||||
root="${srcfs#*/}" # last child component of srcfs
|
||||
target="$(ZFS "$srchost" list -d 1 -t snapshot -H -S creation -o name $srcfs | cut -f2 -d@ | grep "^$tag" | head -n1)"
|
||||
for fs in $(ZFS "$desthost" list -Ho name -r "$destfs/$root" | tac) ; do
|
||||
child="${fs#$destfs/}"
|
||||
destsnap=$(ZFS "$desthost" list -Ho name -S creation -d1 -t snapshot $destfs/$child | head -n1 | cut -f2 -d@)
|
||||
if [[ $destsnap != $target ]] ; then
|
||||
ZFS "$srchost" send $send_opts -R -I @$destsnap $srcparent/$child@$target | ZFS "$desthost" receive $recv_opts -Fue "$destfs/${child%/*}"
|
||||
fi
|
||||
done
|
||||
}
|
||||
|
||||
###
|
||||
### defaults
|
||||
###
|
||||
@ -65,12 +81,14 @@ dateopts="+%F_%T"
|
||||
keep=5
|
||||
verbose=false
|
||||
quiet=false
|
||||
catchup=false
|
||||
|
||||
###
|
||||
### parse options
|
||||
###
|
||||
while getopts "hvqk:t:d:" opt ; do
|
||||
while getopts "chvqk:t:d:" opt ; do
|
||||
case $opt in
|
||||
c) catchup=true ;;
|
||||
h) usage 0 ;;
|
||||
v)
|
||||
verbose=true
|
||||
@ -118,6 +136,14 @@ if [[ $(ZFS "$desthost" list -H -o name "$destfs" 2>/dev/null) != $destfs ]] ; t
|
||||
die 1 "destination fs '$destfs' doesn't exist"
|
||||
fi
|
||||
|
||||
###
|
||||
### fix interrupted transfer
|
||||
###
|
||||
if $catchup ; then
|
||||
catchup || die $? "catchup failed"
|
||||
exit 0
|
||||
fi
|
||||
|
||||
###
|
||||
### create new snapshot on src
|
||||
###
|
||||
|
Loading…
Reference in New Issue
Block a user