Neue Antwort schreiben 
 
Themabewertung:
  • 0 Bewertung(en) - 0 im Durchschnitt
  • 1
  • 2
  • 3
  • 4
  • 5
Linux Backup Script
chessboi Offline
Erfahrener Benutzer

Beiträge: 250
Registriert seit: Jul 2008
Beitrag #1
Linux Backup Script
Vor ungefähr einem Jahr, habe ich einen Backupscript gepostet. Den habe ich nun noch etwas erweitert. Die neue Funktion erlaubt es ein Verzeichniss zu überwachen und alle Änderungen sofort zu sichern (differentel Backup):

Code:
#!/bin/bash
#
# Version: 2.0
# Changelog:
# initial 24.02.2008
# last modify 16.02.2009 - add iwatch observation
#
# to do:
# better handling with logfiles
# set paths by parameter
# handling for old backupfiles

BACKUPPATH="/data/backup/configs/"        # backuppath for files
CONFIGFILE="$(dirname $0)/configfiles.conf"    # scriptconfig
DATAPATH="/data"                # datapath to backup
BACKUPDISK="/backup/backup"            # backupdisk
IWATCHPATH="/data/doku/ipa"            # observation dir for iwatch
IBACKUPPATH="/data/backup/iwatch"        # backuppath for iwatchfiles
LOGIWATCH="/var/log/backup/iwatch.log"        # logfile vor iwatch (if running in verbose mode)
LOGFILE="/var/log/backup/backup.log"        # logfile
DATE=`date +%d%m%Y%H%M`                # date like 240220081430 (day month year hour minute)
TIMESTAMP="date +%X"                # timestamps for logfile
ROOT_UID=0                    # root user-id

# usage: how to use this script
F_USAGE () {
cat << EOF

Backup Script
Usage:

-b    backup the files from ${CONFIGFILE}
-s    sync ${DATAPATH} to ${BACKUPPATH}
-B    first backup the files from ${CONFIGFILE}, then sync ${DATAPATH} to ${BACKUPPATH}
-r    restore all files from ${CONFIGFILE} (untestet)
-nt    also backup notext files with iwatch
-V    Verboselevel for iwatch function
-i    observate ${IWATCHPATH} and make backup by changing
    warning: you can run out of disk space or inodes with this function!

EOF
    exit 1
}

# backup: backup the defined configfiles
F_BACKUP () {
    echo "# `${TIMESTAMP}`: backup the files from ${CONFIGFILE}" >> ${LOGFILE}
    while read input  
    do
        rsync -avR --progress $input ${BACKUPPATH} | tee -a ${LOGFILE}
    done < ${CONFIGFILE}
}

# restore: copy back all data - untested, becauce this is a backup script, nobody needs restore
F_RESTORE () {
    while read input
    do
        if [ ! -e $(dirname $input) ];
        then
            mkdir -p $(dirname $input)
        fi
        cp -r ${BACKUPPATH}$input $(dirname $input)
    done < ${CONFIGFILE}
}

# resync: sync the datapath with the backupdisk
F_RSYNC ()
{
    echo "# `${TIMESTAMP}`: sync ${DATAPATH} to ${BACKUPPATH}" >> ${LOGFILE}
    rsync -av --progress ${DATAPATH} ${BACKUPDISK} | tee -a ${LOGFILE}
}

# iwatch function, copy data to IBACKUPPATH
iF_COPY ()
{    
    echo "copy $1 to ${IBACKUPPATH}" >> ${LOGFILE}
    cp $1 ${IBACKUPPATH}/`echo $1 | sed s@${IWATCHPATH}@@g`
}

# iwatch function, make a differential backup
iF_DIFFBACK ()
{
    if [ ! -e ${IBACKUPPATH}/`echo $1 | sed s@${IWATCHPATH}@@g` ];
    then
        iF_COPY "$1"
    elif [ `file -b $1 | grep " text" > /dev/null; echo $?` -eq 0 -o "${IWATCH_NOTXT}" == 0 ];
    then
        diff -U 0 -a $1 ${IBACKUPPATH}/`echo $1 | sed s@${IWATCHPATH}@@g` >> ${IBACKUPPATH}/`echo $1 | sed s@${IWATCHPATH}@@g`.${DATE}.diff
        # restore with `patch ${IBACKUPPATH}/file ${IBACKUPPATH}/file.diff`
        #cp $1 ${IBACKUPPATH}/`basename $1`.${DATE}.oldfile
    else
        echo "$1 seems not do be a textfile" >> ${LOGIWATCH}
    fi
}

# iwatch function, make a list with deletet files
iF_LIST ()
{
    # echo "$1" >> ${IBACKUPPATH}/delfiles.txt
    mv  ${IBACKUPPATH}/`echo $1 | sed s@${IWATCHPATH}@@g` ${IBACKUPPATH}/`echo $1 | sed s@${IWATCHPATH}@@g`.${DATE}.deleted
}

F_IWATCH ()
{
  ####
  #################################################################
  #    observate a path and make a backup by changing files
  #    needs the tool iwatch installed on the system
  #    use the above definded iF_* functions
  #################################################################

    #loglevel (more definitions are expectet) # debug
    case  ${IWATCH_V} in
    "0")
        iwatch -e all_events ${IWATCHPATH} >> ${LOGIWATCH} &
        ;;
    "1")
        iwatch -e default ${IWATCHPATH} >> ${LOGIWATCH} &    
        ;;
    esac    
    
    #create logfile
    if [ ! -e ${LOGIWATCH} ] ;
    then
        if [ ! -d $(dirname ${LOGIWATCH}) ];
        then
            mkdir -p $(dirname ${LOGIWATCH})
        fi
    else
        mv ${LOGIWATCH} ${LOGIWATCH}_${DATE}
    fi
    touch ${LOGIWATCH}
    
    #sync data with existing backup
    #rsync -av ${IWATCHPATH}/ ${IBACKUPPATH}/
    for file in $( find ${IWATCHPATH} -type f )
    do
        diff -q $file ${IBACKUPPATH}/`echo $file | sed s@${IWATCHPATH}@@g` > /dev/null 2>&1
        local ANSWER="$?"
        if [ $ANSWER -eq 1 ];
        then
            iF_DIFFBACK "$file" &
        elif [ $ANSWER -eq 2 ];
        then
            iF_COPY "$file" &
        fi
    done

    #begin observation
    iwatch -r -e create -c "$0 'iF_COPY' '%f'" ${IWATCHPATH} &
    iwatch -r -e modify,close_write -c "$0 'iF_DIFFBACK' '%f'" ${IWATCHPATH} &
    iwatch -r -e move,delete,delete_self -c "$0 'iF_LIST' '%f'" ${IWATCHPATH} &
}

################################################################################​##########
################################################################################​##########
# RUN
################################################################################​##########
################################################################################​##########

# some tests:
if [ "$#" -eq "0" ] ;
then
    F_USAGE
fi

if [ "$UID" -ne "$ROOT_UID" ]
then
        echo "You must be root to run this script."
        exit 1
fi

if [ ! -e ${LOGFILE} ] ;
then
    if [ ! -d $(dirname ${LOGFILE}) ];
    then
        mkdir -p $(dirname ${LOGFILE})
    fi
else
    mv ${LOGFILE} ${LOGFILE}_${DATE}
fi
touch ${LOGFILE}
echo "# backup from ${DATE} start" >> ${LOGFILE}

# read the parameters:
while [ "$#" -gt "0" ] ;
do
    case $1 in
        -B) # backup and sync: F_BACKUP + F_RSYNC
            F_BACKUP
            F_RSYNC
            shift
            ;;
        -b) # backup configs: F_BACKUP
            F_BACKUP
            shift
            ;;
        -s) # syncinc data: F_RSYNC
            F_RSYNC
            shift
            ;;
        -r) # restore configs: F_RESTORE
            F_RESTORE
            shift
            ;;
        -V) # verboselevel    
            IWATCH_V=$2
            shift
            shift    
            ;;
        -nt) # also backup notext files with iwatch
            IWATCH_NOTXT=$2
            shift
            shift
            ;;
        -i) # iwatch observation    
            F_IWATCH &
            shift
            ;;
        iF_COPY) # iwatch function
            iF_COPY $2 &
            exit 0
            ;;
        iF_DIFFBACK) # iwatch function
            iF_DIFFBACK $2 &
            exit 0
            ;;
        iF_LIST) # iwatch function
            iF_LIST $2 &
            exit 0
            ;;
        *) # default    
            F_USAGE
            break
            ;;
    esac
done
echo "# `${TIMESTAMP}` end" >> ${LOGFILE}
exit 0
################################################################################​##########
# EOF
16.02.2009 19:03
Alle Beiträge dieses Benutzers finden Diese Nachricht in einer Antwort zitieren
gandro Offline
Quälgeist

Beiträge: 8.950
Registriert seit: Jul 2008
Beitrag #2
Linux Backup Script
Sieht nett aus.. ausser dass die root UID als Variable gespeichert wird. Ist die nicht immer 0?

Die Diff-Funktion scheint im Code ganz nett, ist mir allerdings etwas zu unübersichtlich. Muss schauen, evtl. überleg ich mir nen Backupscript auf Basis von git zu bauen.
16.02.2009 20:54
Alle Beiträge dieses Benutzers finden Diese Nachricht in einer Antwort zitieren
chessboi Offline
Erfahrener Benutzer

Beiträge: 250
Registriert seit: Jul 2008
Beitrag #3
Linux Backup Script
gandro schrieb:  Sieht nett aus.. ausser dass die root UID als Variable gespeichert wird. Ist die nicht immer 0?

Muss erstens nicht sein, zweitens könntest du ja nen anderen priviligierten User haben, der alles darf was man tun muss, aber doch etwas eingeschränkt ist, und das ROOT_UID=0 durch etwas anderes ersetzten. Diese Überprüfung habe ich vom Advanced Bash Scripting Guide abgekuckt.

Zitat:Die Diff-Funktion scheint im Code ganz nett, ist mir allerdings etwas zu unübersichtlich.
Naja, ist relativ simpel, wenn ein File vorhanden ist und geändert wurde, wird geprüft ob es ein Textfile ist. Wenn ja wird Zeilenweise verglichen, und die Unterschiede, welche mir diff als Output zurück gibt, wird in ein File geschrieben, womit später mit patch ein restore gemacht werden kann. Wenn nicht muss der Script mit dem Parameter -nt gestartet worden sein, damit auch z.B. PDF-Files gebackupt werden.

Zitat:Muss schauen, evtl. überleg ich mir nen Backupscript auf Basis von git zu bauen.

Bin gespannt auf deinen Ansatz.
16.02.2009 21:34
Alle Beiträge dieses Benutzers finden Diese Nachricht in einer Antwort zitieren
gandro Offline
Quälgeist

Beiträge: 8.950
Registriert seit: Jul 2008
Beitrag #4
Linux Backup Script
chessboi schrieb:  
Zitat:Muss schauen, evtl. überleg ich mir nen Backupscript auf Basis von git zu bauen.
Bin gespannt auf deinen Ansatz.
Naja, falls ich was mache.

Der Ansatz wäre im Grunde ganz einfach:
Ich lass ein leeres git Repository auf dem Backupmedium anlegen. Dann werden da regelmässig Backups reingemacht (d.h. die Dateien überschrieben). Jedes mal wenn die frischen Backups reinkopiert mache, lasse ich einen git commit machen, der sieht was verändert wurde, und speichert die diffs inkl. Kommentar und z.B. Zeitstempel ab.

Danach kann ich von allen oder bestimmten Datien dann ohne Problem frühere Versionen betrachten, habe einen Log was wann geändert wurde und kann gegebenenfalls natürlich auch neue Dateien durch alte Versionen ersetzen.

Allerdings taugt da eher nicht für grosse Binärdateien, sondern eher für Konfigurationsdateien und Dokumente.
Nicht weil git dafür zu langsam wäre, sondern zuviel Speicherplatz verbrauchen würde.
16.02.2009 21:43
Alle Beiträge dieses Benutzers finden Diese Nachricht in einer Antwort zitieren
chessboi Offline
Erfahrener Benutzer

Beiträge: 250
Registriert seit: Jul 2008
Beitrag #5
Linux Backup Script
gandro schrieb:  Allerdings taugt da eher nicht für grosse Binärdateien, sondern eher für Konfigurationsdateien und Dokumente.
Nicht weil git dafür zu langsam wäre, sondern zuviel Speicherplatz verbrauchen würde.

Jup, und ansonsten kannst du auch gleich eine Snapshotfunkton von einem Filesystem (es gibt ja genügend) gebrauchen ...

git hat doch aber sicher die Möglichkeit wie bei SVN Filenamen welche auf bestimmte Patterns matchen auszuschliessen? Ist dann halt Namen basiert, sowas wollte ich zuerst auch machen, doch weil mir die Definierung was jetzt kopiert werden soll und was nicht, bin ich halt einfach auf den Mime-Type gegangen.
16.02.2009 22:36
Alle Beiträge dieses Benutzers finden Diese Nachricht in einer Antwort zitieren
gandro Offline
Quälgeist

Beiträge: 8.950
Registriert seit: Jul 2008
Beitrag #6
Linux Backup Script
Grundsätzlich gibst du bei git am Anfang an, welche Dateien er überwachen soll. Danach kannst du Dateien bzw. Änderungen hinzufügen oder löschen. Und es gibt selbstverändlich Exclude-Listen mit Patterns (damit die auch nicht in der Liste der "untracked files" erscheinen).
16.02.2009 22:39
Alle Beiträge dieses Benutzers finden Diese Nachricht in einer Antwort zitieren
Neue Antwort schreiben 


Gehe zu:


Benutzer, die gerade dieses Thema anschauen: 2 Gast/Gäste