+#!/bin/bash
+set -x
+set -eE -o pipefail
+trap 'echo "$0:$LINENO:error: \"$BASH_COMMAND\" returned $?" >&2' ERR
+
+usage() {
+ cat <<EOF
+Usage: ${0##*/} OLD_HOST NEW_HOST
+
+Adjust home network dns so NEW_HOST resolves locally if it is on the
+local network. Turn off mail receiving on OLD_HOST, run btrbk to move
+mail to NEW_HOST, turn on mail receiving on NEW_HOST.
+
+
+-h|--help Print help and exit.
+
+Note: Uses GNU getopt options parsing style
+EOF
+ exit $1
+}
+
+##### begin command line parsing ########
+
+if (( $# != 2 )) || [[ $1 == -* || $2 == -* ]]; then
+ usage 1
+fi
+
+old_host=$1
+new_host=$2
+
+if [[ $old_host != $MAIL_HOST ]]; then
+ read -p "warning: \$old_host != \$MAIL_HOST: $old_host != $MAIL_HOST, proceed? y/N "
+ if [[ $REPLY != [yY] ]]; then
+ exit 1
+ fi
+fi
+
+if [[ $new_host == "$HOSTNAME" ]]; then
+ localhost_new=true
+ ssh_prefix=ssh
+else
+ localhost_new=false
+ ssh_prefix=
+fi
+if [[ ! $new_host || ! $old_host ]]; then
+ echo "$0: bad args. see script"
+ exit 1
+fi
+
+at_home=false
+if timeout -s 9 10 ssh root@wrt.lan :; then
+ at_home=true
+fi
+
+source /a/bin/bash_unpublished/source-semi-priv
+#### begin convert private hostnames to public hostnames ####
+if ! $at_home; then
+ for var in old_host new_host; do
+ case ${!var} in
+ treetowl)
+ eval $var=$HOME_DOMAIN
+ ;;
+ esac
+ done
+fi
+#### end convert private hostnames to public hostnames ####
+
+
+# because our port forward is not robust enough, we can't use proxy command,
+# todo: just open an ssh port to the world on wrt
+if ! $at_home; then
+ ssh_cmd="ssh $HOME_DOMAIN ssh wrt"
+else
+ ssh_cmd="ssh wrt"
+fi
+# if new_host is not on home network, make mail.iankelling.org not resolve
+# on the home network.
+if [[ $new_host == $HOSTNAME ]] && ! $at_home; then
+ echo | $ssh_cmd cedit mail_host /etc/hosts
+else
+ $ssh_cmd bash -s <<EOFOUTER
+ cedit mail_host /etc/hosts <<'EOF' || /etc/init.d/dnsmasq restart
+\$(grep "\b$new_host\b" /etc/hosts | awk '{print $1}') mail.iankelling.org
+EOF
+EOFOUTER
+fi
+
+mail-setup() {
+ shell="$1"
+ $shell sed -ri "s/MAIL_HOST=.*/MAIL_HOST=$new_host/" /a/bin/bash_unpublished/source-semi-priv
+ $shell /a/bin/distro-setup/mail-setup exim4
+}
+
+mail-setup "ssh $old_host"
+
+sudo dd of=/etc/btrbk.conf <<'EOF'
+ssh_identity /root/.ssh/id_rsa
+# Just a guess that local7 is a good facility to pick.
+# It's a bit odd that the transaction log has to be logged to
+# a file or syslog, while other output is sent to std out.
+# The man does not mention a way for them to be together, but
+# I dunno if setting a log level like warn might also output
+# transaction info.
+transaction_syslog local7
+
+# so we only run one at a time
+lockfile /var/lock/btrbk.lock
+
+# default format of short does not accomidate hourly preservation setting
+timestamp_format long-iso
+
+# only make a snapshot if things have changed
+snapshot_create onchange
+# I could make this different from target_preserve,
+# if one disk had less space.
+# for now, keeping them equal.
+snapshot_preserve 36h 14d 8w 24m
+snapshot_preserve_min 4h
+snapshot_dir btrbk
+
+# so, total backups = ~89
+target_preserve 36h 14d 8w 24m
+target_preserve_min 4h
+
+# if something fails and it's not obvious, try doing
+# btrbk -l debug -v dryrun
+
+
+EOF
+
+
+if $localhost_new; then
+ btrbk_src=ssh://$old_host/mnt/root
+ btrbk_dst=/mnt/root/btrbk
+else
+ btrbk_src=/mnt/root
+ btrbk_dst=ssh://$old_host/mnt/root/btrbk
+fi
+
+sudo tee -a /etc/btrbk.conf <<EOF
+volume $btrbk_src
+subvolume o
+target send-receive $btrbk_dst
+EOF
+
+
+sudo btrbk --progress run
+$ssh_prefix $new_host mount-latest-subvol
+
+mail-setup