Dienstag, 7. Oktober 2014

[linux] rsync Performance verbessern. Mehr CPU Kerne.

Ich stand vor dem Problem viele kleine (3 Millionen) Bilddateien von einem Server zum anderen kopieren zu müssen, da der Bildauslagerungsserver gewechselt werden sollte.

Das Packen und Archivieren mit tar und gzip war leider unbefriedigend langsam.

Auch die Alternative mit pigz (gzip mit Mehrkern-Unterstützung) brachte keine großartige Besserung.


Syntax für pigz:

 tar -cv –use-compress-program=pigz -f meinarchiv.tar /srv/www/img

Was ich noch nicht probiert habe, ist tar mit einer Erweiterung zu versehen, die mehrere Threads zum Schreiben verwenden kann.

Das gibts hier: http://www.maier-komor.de/mtwrite.html


Syntax für Nutzung mit mtwrite:

mttar xf mytarfile.tar


Ich habe mich dann aber erstmal für die Nutzung von rsync entschieden. Vorteile: Ich muss den laufenden Betrieb (Bildupload) nicht stoppen; Abgebrochene Aktionen können wieder aufgenommen werden; Ich habe nur eine Aktion auszuführen, denn die Daten werden direkt via ssh übertragen.

Leider dauert dieser Vorgang wegen der vielen kleinen Dateien auch ziemlich lange. Nach 24 Stunden waren knapp 70GB übertragen.

Nun gibt es noch einige Dinge die ich demnächst ausprobieren möchte. Und damit ich Sie nicht vergesse gibt es diesen Post :)

Zum Beispiel lässt sich der CPU - Kern den rsync verwendet auf den Maximalwert hochtakten.
Das kann man so machen:

for i in 0 ; do
echo performance > /sys/devices/system/cpu/cpu$i/cpufreq/scaling_governor
done

Mehr dazu auf http://lwn.net/Articles/400489/

Noch etwas mehr verspreche ich mir jedoch von mehreren parallel laufenden rsync- Prozessen.
Mit Hilfe eines Scripts werden die Dateien auf die Prozesse verteilt.

Das Script gibts dort: https://wiki.ncsa.illinois.edu/display/~wglick/Parallel+Rsync

Falls der Link irgendwann mal down sein sollte, hier zum Kopieren:

/bin/bash
# SETUP OPTIONS
export SRCDIR="/folder/path"
export DESTDIR="/folder2/path"
export THREADS="8"
# RSYNC TOP LEVEL FILES AND DIRECTORY STRUCTURE
rsync -lptgoDzd $SRCDIR/ /$DESTDIR/
# FIND ALL FILES AND PASS THEM TO MULTIPLE RSYNC PROCESSES
cd $SRCDIR; find . -type f | xargs -n1 -P$THREADS -I% rsync -az % /$DESTDIR/%
# IF YOU WANT TO LIMIT THE IO PRIORITY, 
# PREPEND THE FOLLOWING TO THE rsync & cd/find COMMANDS ABOVE:
#   ionice -c2

Nachteil hierbei: Bei diesem Script werden alle Dateien des Hauptverzeichnisses mit nur einem Prozess übertragen. In den Kommentaren gab es eine alternative Lösung:

#!/bin/bash
 
# SETUP OPTIONS
export SRCDIR="/Storage/data1"
export DESTDIR="/Storage/data2"
export THREADS="32"
 
# FIND ALL FILES AND PASS THEM TO MULTIPLE RSYNC PROCESSES
cd $SRCDIR
if [[ $? -eq 0 ]]; then
        find . -type d | xargs -I% mkdir -p /$DESTDIR/%
        find . -type f | xargs -n1 -P$THREADS -I% rsync -a % /$DESTDIR/%
fi

Für beide Fälle gilt: Soll per ssh übertragen werden - also von Server zu Server - müssen die rsync Befehle abgeändert werden:

rsync -lptgoDzd -e 'ssh -c arcfour' $SRCDIR/ remotehost:/$DESTDIR/
cd $SRCDIR; find . -type f | xargs -n1 -P$THREADS -I% rsync -az -e 'ssh -c arcfour' % remotehost:/$DESTDIR/%

Und noch ein wichtiger Parameter: Soll das Verzeichnis lediglich geupdated werden und nicht alle Dateien überschrieben werden, unbedingt die Option "-u"verwenden.

Quellen:

http://www.maier-komor.de/mtwrite.html
http://lwn.net/Articles/400489/
https://wiki.ncsa.illinois.edu/display/~wglick/Parallel+Rsync
http://wiki.ubuntuusers.de/rsync


Keine Kommentare: