Wartbarkeit, Stabilität und Effektivität

MySQL Backup per Mercurial!

2009-11 16
Mo, 2009-11-16 15:37 -- mig

Backups sind wichtig! Unbestritten! Bisher wurde die komplette DB in eine Datei gedumpt bzipt und per ssh archiviert. Damit das Archiv nicht zu groß wird, wurden alle unwichtigen Zwischen-Stände gelöscht, mehr oder weniger intelligent und automatisch per Script. Schlecht wenn etwas schief geht.

Inzwischen habe ich eine bessere Lösung gefunden… Alle Tabellen einer DB werden in ein Verzeichnis gedumpt, dann per hg versioniert, das Repo wird dann regelmäßig gespiegelt.

Die Vorteile:

  • Statt täglich 3 Sicherungspunkten wird jetzt stündlich gesichert,
  • Das Repository ist mit einer Historie von 10 Tagen genauso groß wie vorher 3 komplett-Dumps (⇒ 1 Tag).
  • Der Traffik verursacht durch das Archivieren hat sich um 90% reduziert.
  • Nach einer verübergehenden Unerreichbarkeit werden alle verpassten Sicherungspunkte nachgesichert.
#!/bin/bash
based=/var/backup_dir
pass=secret
 
function usage() {
    echo "Usage: `basename $0` [-db <database>|-list|-pull <host>|-commit]*"
    if [[ -n "$1" ]]; then
        echo "Unknown parameter $1 "
    fi
    exit $E_BADARGS
}
 
function listdbs() {
    echo "SHOW DATABASES;" | mysql -uroot -p$pass
}
 
 
function dumpDaten() {
    install -g mysql -o mysql -d $based/$db
    mysqldump -uroot -p$pass -f --skip-comments --single-transaction -T $based/$db $db
 
    cd $based/$db
    hg addremove -s 70
}
 
function commit() {
    cd $based
    hg commit -m "backup $(date '+%Y%m%d %H:%M')" 2> /dev/null
}
 
function pull() {
    cd $based
    hg pull https://$host/$based
}
 
# --- main
VERBOSE=1
if [[ "$1" == "-q" ]]; then
    VERBOSE=0
    shift
fi
if [[ ! -n "$1" ]]; then
    usage
fi
 
while [ "x$1" != "x" ]
do
    case $1 in
        "-list")   listdbs ;;
        "-db")     db=$2;    shift ;  dumpDaten ;;
        "-pull")   host=$2;  shift ;  pull ;;
        "-commit") commit ;;
        *)         usage $1 ;;
    esac
    shift
done
 
#vim:set ts=4

Je nach Datenmodell ist es evtl. sinnvoll temporäre Tabellen nicht mitzusichern. Tabellen ausschließen kann man idealerweise beim dump (mysql_dump --ignore-table=db_name.tbl_name), durch Löschen der gedumpten Dateien oder durch ignorieren in mercurial (hg -X cache).