mariadb/mysql-systemd-helper
Mikhail Novosyolov 0132e7e3ec No-change import from openSUSE mariadb 10.5.8-3.1
This package in ROSA was maintained quite poorly, had only a few users
and lacked such important features as running multiple instances
of MySQL server (mysqld@.service) and scripts for automatic upgrade
to newer versions.
Also upstream has renamed libraries, now there is mysql-connector-c with
devel parts.
/srv/mysql is also rather strange, /var/lib/mysql is more common.
Let's rebase to a well-maintained package from openSUSE.
It is being done in a not released platform without any compatibility
for smooth upgrades fromt he old package. The new one has a lower epoch,
automatic upgrades won't be done.
High epoch is not needed anymore: mysql-community has not been merged from
abf.io/rosaserver to abf.io/import, and now the library in mariadb is
called libmariadbclient, not libmysqlclient (but compatibility symlinks do exist),
so there are no duplicated provides and so there is no need in a high epoch.

This commits just imports from openSUSE's SRPM without any changes,
the following one will adapt it for ROSA. It will allow to easily see
the diff against the openSUSE's package to easify further syncs
and contibuting back to SUSE (https://bugzilla.opensuse.org/show_bug.cgi?id=1182218)
2021-02-13 14:21:52 +03:00

201 lines
6.4 KiB
Bash

#!/bin/bash
die() {
echo "$1"
exit 1
}
# Read options from config file
read_config() {
# Initial settings
MYSQLVER="$(echo @MYSQLVER@ | sed 's|\.[0-9]\+$||')"
mysql_daemon_user=mysql
mysql_daemon_group=mysql
# status information directory (e.g. info about a necessity of upgrade, current version etc)
mariadb_status_dir="/var/lib/misc"
if [[ -z "$INSTANCE" ]]; then
datadir=/var/lib/mysql
socket="/run/mysql/mysql.sock"
else
datadir="/var/lib/mysql-$INSTANCE"
socket="/run/mysql/mysql.${INSTANCE}.sock"
fi
# Read options - important for multi setup
if [[ -n "$INSTANCE" ]]; then
opts="$(/usr/bin/my_print_defaults mysqld mysqld_multi "$INSTANCE" --defaults-extra-file=/etc/my${INSTANCE}.cnf)"
tmp_opts="$opts"
config="/etc/my${INSTANCE}.cnf"
else
opts="$(/usr/bin/my_print_defaults mysqld)"
tmp_opts="$opts"
config="/etc/my.cnf"
fi
# Update local variables according to the settings from config
for arg in $tmp_opts; do
case "$arg" in
--basedir=*) basedir="$(echo "$arg" | sed -e 's/^[^=]*=//')" ;;
--socket=*) socket="$(echo "$arg" | sed -e 's/^[^=]*=//')" ;;
--datadir=*) datadir="$(echo "$arg" | sed -e 's/^[^=]*=//')" ;;
--user=*) mysql_daemon_user="$(echo "$arg" | sed -e 's/^[^=]*=//')" ;;
esac
done
# work-around for lost+found directory in $datadir (bug #986251)
if [ -d "$datadir/lost+found" ]
then
ignore_db_dir="--ignore-db-dir=lost+found"
else
ignore_db_dir=""
fi
}
# Create new empty database if needed
mysql_install() {
if [[ ! -d "$datadir/mysql" ]]; then
echo "Creating MySQL privilege database... "
mysql_install_db --rpm --user="$mysql_daemon_user" --datadir="$datadir" || \
die "Creation of MySQL database in $datadir failed"
echo -n "$MYSQLVER" > "$mariadb_status_dir"/mariadb_upgrade_info
fi
}
# Upgrade database if needed
mysql_upgrade() {
# Run mysql_upgrade on every package install/upgrade. Not always
# necessary, but doesn't do any harm.
if [[ -f "$mariadb_status_dir/.mariadb_run_upgrade" ]]; then
echo "Checking MySQL configuration for obsolete options..."
sed -i -e 's|^\([[:blank:]]*\)skip-locking|\1skip-external-locking|' \
-e 's|^\([[:blank:]]*skip-federated\)|#\1|' /etc/my.cnf
# instead of running mysqld --bootstrap, which wouldn't allow
# us to run mysql_upgrade, we start a full-featured server with
# --skip-grant-tables and restict access to it by unix
# permissions of the named socket
echo "Trying to run upgrade of MySQL databases..."
# Check whether upgrade process is not already running
protected="$(cat "/run/mysql/protecteddir.$INSTANCE" 2> /dev/null)"
if [[ -n "$protected" && -d "$protected" ]]; then
pid="$(cat "$protected/mysqld.pid" 2> /dev/null)"
if [[ "$pid" && -d "/proc/$pid" ]] &&
[[ $(readlink "/proc/$pid/exe" | grep -q "mysql") ]]; then
die "Another upgrade in already in progress!"
else
echo "Stale files from previous upgrade detected, cleaned them up"
rm -rf "$protected"
rm -f "/run/mysql/protecteddir.$INSTANCE"
fi
fi
protected="$(mktemp -d -p /var/tmp mysql-protected.XXXXXX | tee "/run/mysql/protecteddir.$INSTANCE")"
[ -n "$protected" ] || die "Can't create a tmp dir '$protected'"
# Create a secure tmp dir
chown --no-dereference "$mysql_daemon_user:$mysql_daemon_group" "$protected" || die "Failed to set group/user to '$protected'"
chmod 0700 "$protected" || die "Failed to set permissions to '$protected'"
# Run protected MySQL accessible only though socket in our directory
echo "Running protected MySQL... "
/usr/sbin/mysqld \
--defaults-file="$config" \
--user="$mysql_daemon_user" \
--skip-networking \
--skip-grant-tables \
$ignore_db_dir \
--log-error="$protected/log_upgrade_run" \
--socket="$protected/mysql.sock" \
--pid-file="$protected/mysqld.pid" &
mysql_wait "$protected/mysql.sock" || die "MySQL didn't start, can't continue"
# Run upgrade itself
echo "Running upgrade itself..."
echo "It will do some chek first and report all errors and tries to correct them"
echo
if /usr/bin/mysql_upgrade --no-defaults --force --socket="$protected/mysql.sock"; then
echo "Everything upgraded successfully"
up_ok=""
rm -f "$mariadb_status_dir/.mariadb_run_upgrade"
[[ $(grep -q "^$MYSQLVER" "$mariadb_status_dir/mariadb_upgrade_info" 2> /dev/null) ]] || \
echo -n "$MYSQLVER" > "$mariadb_status_dir/mariadb_upgrade_info"
else
echo "Upgrade failed"
up_ok="false"
fi
# Shut down MySQL
echo "Shutting down protected MySQL"
protected_pid=$(cat "$protected/mysqld.pid")
kill $protected_pid
for i in {1..30}; do
/usr/bin/mysqladmin --socket="$protected/mysql.sock" ping > /dev/null 2>&1
# Check both ping response and the pid in a process list as it can take some time till the process is terminated.
# Otherwise it can lead to "found left-over process" situation when regular mariadb is started.
if [[ $? -eq 1 ]] && ! ps -p $protected_pid > /dev/null 2>&1; then
break
fi
sleep 1
done
/usr/bin/mysqladmin --socket="$protected/mysql.sock" ping > /dev/null 2>&1 && kill -9 $protected_pid
# Cleanup
echo "Final cleanup"
if [[ -z "$up_ok" ]]; then
rm -rf "$protected" "/run/mysql/protecteddir.$INSTANCE"
else
die "Something failed during upgrade, please check logs"
fi
fi
}
mysql_wait() {
[[ -z "$1" ]] || socket="$1"
echo "Waiting for MySQL to start"
for i in {1..60}; do
/usr/bin/mysqladmin --socket="$socket" ping > /dev/null 2>&1 && break
sleep 1
done
if /usr/bin/mysqladmin --socket="$socket" ping > /dev/null 2>&1; then
echo "MySQL is alive"
return 0
else
echo "MySQL is still dead"
return 1
fi
}
mysql_start() {
exec /usr/sbin/mysqld \
--defaults-file="$config" \
$ignore_db_dir \
--user="$mysql_daemon_user"
}
# We rely on output in english at some points
LC_ALL=C
INSTANCE="$2"
read_config
# Make sure that /run/mysql is created and has correct permissions (bsc#1038740)
systemd-tmpfiles --create /usr/lib/tmpfiles.d/mariadb.conf
case "$1" in
install)
mysql_install ;;
upgrade)
mysql_upgrade ;;
start)
mysql_start ;;
wait)
mysql_wait ;;
*)
echo "Supported commands are:"
echo " install - creates empty database if needed"
echo " upgrade - tries to migrate data to newer version if needed"
echo " start - tries to start instance"
echo " wait - waits till instance is pingable"
echo "All commands can take extra argument which is group from 'mysqld_multi' you want to work with"
;;
esac