|
| 1 | +#!/bin/bash -e |
| 2 | +# This is a hook to handle the changes to the mysql.user table in MariaDB 10.4+ |
| 3 | + |
| 4 | +# set DEBUG=y to enable verbose output |
| 5 | +[[ -z "$DEBUG" ]] || set -x |
| 6 | + |
| 7 | +# hooks are always called with two arguments |
| 8 | +op=$1 |
| 9 | +state=$2 |
| 10 | + |
| 11 | +echo "HOOK $0 :: op=$op state=$state pwd=$(pwd) :: " |
| 12 | +echo "TKLBAM_RESTORE_PROFILE_ID: $TKLBAM_RESTORE_PROFILE_ID" |
| 13 | + |
| 14 | +fatal() { echo "[$(basename $0)] FATAL: $*" >&2; exit 1; } |
| 15 | +warn() { echo "[$(basename $0)] WARN: $*" >&2; } |
| 16 | +info() { echo "[$(basename $0)] INFO: $*"; } |
| 17 | + |
| 18 | +migrate_db_not_set() { |
| 19 | + warn "MIGRATE_DB env var not set; DB restore of MySQL/MariaDB from TKL v16.x and earlier may fail" |
| 20 | + warn "If migration of old backup fails, please run 'tklbam-restore-rollback' and retry with 'MIGRATE_DB=y tklbam-restore ...'" |
| 21 | +} |
| 22 | + |
| 23 | +check_version() { |
| 24 | + local org_version=$(cat /etc/turnkey_version | sed -En "s|turnkey-[a-z0-9-]+-([0-9]+)\.[0-9]+[a-z0-9]*-.*|\1|p") |
| 25 | + local bak_version=$(echo $TKLBAM_RESTORE_PROFILE_ID | sed -En "s|turnkey-[a-z0-9-]+-([0-9]+)\.[0-9]+[a-z0-9]*-.*|\1|p") |
| 26 | + if [[ "$org_version" -ge 17 ]] && [[ "$bak_version" -le 16 ]]; then |
| 27 | + echo "run_migration" |
| 28 | + else |
| 29 | + echo "skip_migration" |
| 30 | + fi |
| 31 | +} |
| 32 | + |
| 33 | +if [[ "$state" == "pre" ]] && [[ "$op" == "restore" ]]; then |
| 34 | + info "hook invoked before Duplicity downloads backup archive. Extras path = $(pwd)" |
| 35 | + info "Nothing to do yet (DB migration may be required)" |
| 36 | + |
| 37 | +elif [[ "$state" == "inspect" ]] && [[ "$op" == "restore" ]]; then |
| 38 | + |
| 39 | + info "hook invoked after Duplicity downloads backup archive. Extras path = $(pwd)" |
| 40 | + |
| 41 | + if [[ "$(check_version)" == 'skip_migration' ]]; then |
| 42 | + info "DB migration not required, skipping" |
| 43 | + elif [[ -x "/usr/bin/mysql" ]]; then |
| 44 | + info "Migration of MySQL/MariaDB database detected, working around possible issue" |
| 45 | + mysqldump mysql > /tmp/mysql_db.sql |
| 46 | + info "'mysql' DB dumped to /tmp/mysql_db.sql (in case you need to restore) - or just run 'tklbam-restore-rollback'" |
| 47 | + mysql -e "DROP TABLE IF EXISTS mysql.global_priv; DROP VIEW IF EXISTS mysql.user;" |
| 48 | + info "Table mysql.global_priv & view mysql.user dropped, continuing restore" |
| 49 | + else |
| 50 | + warn "/usr/bin/mysql not found (or not executable) - assuming no MySQL/MariaDB database" |
| 51 | + fi |
| 52 | + |
| 53 | + |
| 54 | +elif [[ "$state" == "post" ]] && [[ "$op" == "restore" ]]; then |
| 55 | + |
| 56 | + info "hook invoked after backup restore. Extras path = $(pwd)" |
| 57 | + if [[ "$(check_version)" == 'skip_migration' ]]; then |
| 58 | + info "DB migration not required, skipping" |
| 59 | + elif [[ -x "/usr/bin/mysql" ]]; then |
| 60 | + if [[ -f "/tmp/mysql_db.sql" ]]; then |
| 61 | + info "Restore of MySQL/MariaDB database detected; ensuring that MySQL/MariaDB is running properly" |
| 62 | + else |
| 63 | + warn "no local MySQL/MariDB 'mysql' database backup located" |
| 64 | + fi |
| 65 | + # ensure no mariadb processes still running |
| 66 | + systemctl stop mariadb |
| 67 | + pkill mariadb || true |
| 68 | + |
| 69 | + # start mariadb with '--skip-grant-tables' - to fix permissions |
| 70 | + # pre/post exec commands taken from mariadb.service file, possibly not |
| 71 | + # all needed, but just in case... |
| 72 | + ## pre-exec |
| 73 | + /usr/bin/install -m 755 -o mysql -g root -d /var/run/mysqld |
| 74 | + systemctl unset-environment _WSREP_START_POSITION |
| 75 | + [ ! -e /usr/bin/galera_recovery ] && VAR= || \ |
| 76 | + VAR=`cd /usr/bin/..; /usr/bin/galera_recovery`; [ $? -eq 0 ] \ |
| 77 | + && systemctl set-environment _WSREP_START_POSITION=$VAR || exit 1 |
| 78 | + ## exec |
| 79 | + su mysql -s /bin/bash -c "/usr/sbin/mariadbd --skip-grant-tables" & |
| 80 | + ## post-exec |
| 81 | + systemctl unset-environment _WSREP_START_POSITION |
| 82 | + /etc/mysql/debian-start |
| 83 | + |
| 84 | + # wait until mariadb socket is available |
| 85 | + tries=0 |
| 86 | + sock="/var/run/mysqld/mysqld.sock" |
| 87 | + while [[ ! -S "$sock" ]]; do |
| 88 | + if [[ "$tries" -le 10 ]]; then |
| 89 | + sleep 1 |
| 90 | + else |
| 91 | + echo "FATAL: $sock not found after waiting $tries seconds" |
| 92 | + exit 1 |
| 93 | + fi |
| 94 | + tries=$((tries+1)) |
| 95 | + |
| 96 | + done |
| 97 | + |
| 98 | + # reset root@localhost and mysql@locahost users are authenticted by unix_socket |
| 99 | + mysql --wait --batch --execute \ |
| 100 | + "FLUSH PRIVILEGES; \ |
| 101 | + GRANT SELECT ON *.* TO root@localhost IDENTIFIED VIA unix_socket; \ |
| 102 | + GRANT SELECT ON *.* TO mysql@localhost IDENTIFIED VIA unix_socket;" |
| 103 | + if [[ -f '/etc/mysql/debian.cnf' ]]; then |
| 104 | + # adjust /etc/mysql/debian.cnf if it uses the debian-sys-maint user |
| 105 | + if grep -q debian-sys-maint /etc/mysql/debian.cnf; then |
| 106 | + sed -i "1a # This file has been automatically adjusted by TKLBAM" /etc/mysql/debian.cnf |
| 107 | + sed -i "\|debian-sys-maint|s|||g; \|^password|s|^|#|; \|^basedir|s|^|#|;" /etc/mysql/debian.cnf |
| 108 | + fi |
| 109 | + fi |
| 110 | + # force upgrade to recreate the mysql.global_priv table and convert mysql.user from table to view |
| 111 | + mariadb-upgrade --force |
| 112 | + |
| 113 | + # kill mariadb background process and start service |
| 114 | + pkill mariadb || true |
| 115 | + systemctl start mariadb |
| 116 | + info "MariaDB restarted" |
| 117 | + info "Everything should be good to go" |
| 118 | + else |
| 119 | + echo "/usr/bin/mysql not found (or not executable) - assuming no MySQL/MariaDB database" |
| 120 | + fi |
| 121 | + |
| 122 | +elif [[ "$op" == "backup" ]]; then |
| 123 | + |
| 124 | + info "nothing to do when backing up" |
| 125 | + |
| 126 | +else |
| 127 | + |
| 128 | + echo "bad hook invocation" |
| 129 | + exit 1 |
| 130 | + |
| 131 | +fi |
0 commit comments