Backup unter Linux mit udev

Backup ist eine schwierige Sache und es gibt sicher viele Strategien.
Ich möchte im Folgenden meine bevorzugte Möglichkeit beschreiben:

  • Externe HD (nicht im Gehäuse sondern so: SATA QuickPort USB3.0
  • Daten wegen des einfacheren Zugriffs aufs Backup NICHT komprimieren sondern nur kopieren.
  • Backup wird durch das Anschließen der HD automatisch gestartet.

Udev bietet unter anderem, die Möglichkeit bash-scripte auszuführen, wenn Geräte angeschlossen werden. Dazu legt man unter /etc/udev/rules.d/ eine Datei an und schreibt seine Regeln rein. Zum Beispiel so:
/etc/udev/rules.d/10-local.rules:

SUBSYSTEM=="block", SUBSYSTEMS=="scsi", RUN+="/usr/script/backup/backup-hd-udev.sh"

Die udev-Attribute kann man sich auf einem halbwegs aktuellem System nicht mehr mittels udevinfo anzeigen lassen sonden eher so:

udevadm info --query=all --name=<DEVICENAME> --attribute-walk

Diese Regel ruft das Script „/usr/script/backup/backup-hd-udev.sh“ auf, wenn ein SCSI blockdevice angeschlossen wird. Das Script selber sieht so aus:

#!/bin/bash
BACKUPROOT="<DESTINATION>"
 
if [ $ACTION == "add" ] && [ $DEVTYPE == "partition" ]; then
  case $ID_SERIAL in 
    "ST2000VX_002-12345_0000000000000002-0:0" )
      mount $DEVNAME <DESTINATION> && 
      rsync -avz <SOURCE> --exclude *<NOT_WANT>*  $BACKUPROOT
      touch $BACKUPROOT/backup_vom_`date -I`.log
      umount $DEVNAME
      hdparm -S1 `echo $DEVNAME | rev | cut -b 2- | rev`
      ;; 
  esac
fi

wobei folgende Platzhalter noch zu ersetzen wären:

  • <DESTINATION>: Ort an dem die Partition des Backup-HD eingehängt wird und an dem per rsync die Daten kopiert werden.
  • <SOURCE>: Quellort der zu sichernden Daten.
  • <NOT_WANT>: Auszuschließendes Verzeichnis im Quellort. Es können auch mehrere angegeben werden, dazu muss eben „–exclude…“ mehrmals wiederholt werden.

Funktionsweise des Scripts

Was macht das Script?

  1. if [ $ACTION == "add" ] && [ $DEVTYPE == "partition" ]; then

    Nur für den Fall weitermachen, dass ein Gerät des Typs „partition“ hinzugefügt wird.

  2. case $ID_SERIAL in 

    Switch case über die Seriennummer, falls es mal mehr als eine Platte gibt, auf die wir sichern wollen.

  3. "ST2000VX_002-12345_0000000000000002-0:0" )

    Führe für genau diese Seriennummer aus.

  4. mount $DEVNAME <DESTINATION> && 

    Gerät einhängen UND nächste Zeile nur ausführen, wenn der Befehl erfolgreich war. Wir wollen nicht, dass irgendeine Partition vollgeschrieben wird, wenn das Einhängen fehlschlägt.

  5. rsync -avz <SOURCE> --exclude *<NOT_WANT>*  $BACKUPROOT 

    Kopiere die Daten mittels rsync.

  6. touch $BACKUPROOT/backup_vom_`date -I`.log

    Lege eine Datei an, die Auskunft über das Datum des Backups gibt.

  7. umount $DEVNAME

    Hänge das Gerät wieder aus.

  8. hdparm -S1 `echo $DEVNAME | rev | cut -b 2- | rev`

    Bringe die Backup-HD dazu in den standby-Modus zu gehen. Der Teil

    echo $DEVNAME | rev | cut -b 2- | rev

    macht hierbei aus „/dev/sdb1“ → „/dev/sdb“ indem der letzte Buchstabe abgeschnitten wird.

udev Umgebungsvariablen

Udev setzt Umgebungsvariablen, die vom aufgerufenen Script benutzt werden. Unter anderen sind das:

  • ACTION: hat den Wert „add“, wenn das Gerät angeschlossen wird und „remove“, wenn das Gerät entfernt wird.
  • DEVTYPE: hat den Wert „disk“, wenn das „disk“-Gerät von udev angelegt wird (z.b. /dev/sdb) oder „partition“, wenn von udev das Gerät für die Partition angelegt wird (z.b. /dev/sdb1)
  • DEVNAME: der Name des eben angelegten Geräts: im Falle von DEVTYPE=„disk“ ist DEVNAME=/dev/sdb

Alle Umgebungsvariablen mit Wert in meinem Fall:

ID_USB_DRIVER=usb-storage 
ID_MODEL=002-12345 
ID_MODEL_ENC=002-1AH166\x20\x20\x20\x20\x20\x20 
ID_REVISION=CV01 
DEVTYPE=partition 
ID_BUS=usb 
SUBSYSTEM=block 
ID_SERIAL=ST2000VX_002-12345_0000000000000002-0:0 
ID_FS_UUID=eb354dc1-e6b1-48b1-8c69-c30671c58034 
DEVPATH=/devices/pci0000:00/0000:00:1d.7/usb1/1-2/1-2:1.0/host18/target18:0:0/18:0:0:0/block/sde/sde1 
ID_MODEL_ID=55aa 
ID_VENDOR_ENC=ST2000VX 
ID_FS_VERSION=1.0 MINOR=65 
ACTION=add PWD=/ 
UDEV_LOG=3 ID_
FS_TYPE=ext3 
MAJOR=8 
DEVLINKS=/dev/block/8:65 /dev/disk/by-id/usb-ST2000VX_002-12345_0000000000000002-0:0-part1 /dev/disk/by-path/pci-0000:00:1d.7-usb-0:2:1.0-scsi-0:0:0:0-part1 /dev/disk/by-uuid/eb354dc1-e6b1-48b1-8c69-c30671c58034 
ID_VENDOR_ID=174c 
DEVNAME=/dev/sde1 
SHLVL=1 
ID_FS_USAGE=filesystem 
ID_TYPE=disk 
ID_PART_TABLE_TYPE=dos 
ID_FS_SEC_TYPE=ext2 
ID_FS_UUID_ENC=eb354dc1-e6b1-48b1-8c69-c30671c58034 
ID_INSTANCE=0:0 
ID_VENDOR=ST2000VX 
ID_USB_INTERFACE_NUM=00 
ID_SERIAL_SHORT=0000000000000002 
ID_PATH=pci-0000:00:1d.7-usb-0:2:1.0-scsi-0:0:0:0 
ID_USB_INTERFACES=:080650: 
SEQNUM=1866

Links