This is an old revision of the document!
Einige Zeit hat das Backup mit “rsync” gut funktioniert, aber ich habe mitr überlegt, dass ein einzelnes Backup bzw. das Backup auf eine einzelne Platte eventuell doch nicht so optimal ist. Daher habe ich mich ein wenig umgesehen wie man das besser machen kann ohne gleich das Backup-Script mehrmals mit verschiedenen Zielen aufzurufen.
Die Lösung war dann die Umstellung meiner derzeitigen gluster Konfiguration hin zu einer gespiegelten Konfiguration.
Damit hatte ich auch die Möglichkeit beim Backup gleichzeitig auf zwei (oder mehr) verschiedenen Server meine Backups zu schreiben.
Da ich das neue Script so flexibel wie möglich machen wollte habe ich mir überlegt, alle Parameter in ein extra File auszulagern. Ich habe wegen der einfachen Lesbarkeit -json als Format gewählt.
Es sind noch viele “echo” drinn damit man beim manuellen starten des Scriptes sehenkann was gerade passiert und wie die folgenden Kommandos dann zusammengesetzt werden.
#!/bin/bash ############################################################################# # # # backup script # # Author : theta-my -> thomas@tuhol.de # # # # can run with different backup methods, # # please take a look in backup_<host>.jason file for further informations # # # # to make my work easier, i have all my urgent data located in one folder # # and mount this folder or sub folders to the right location in file system # # # ############################################################################# setup() { tstemp=`date +%Y%m%d%H%M` host=`hostname` # define definition file and check availability DATA_FILE=/opt/backup/backup_$host.json if [ ! -f $DATA_FILE ] then logger " <error> : definition file /opt/backup/backup_$host.json not reachable, check file location" exit fi WORK_DIR=`jq .work_dir $DATA_FILE|sed 's/\"//g'`/ cd $WORK_DIR echo "working and running in : "$WORK_DIR MOUNT_FS="" message="" ERR_STOP=0 ERR_COUNT=0 ERR_HIGH_COUNT=0 ERR_MEDIUM_COUNT=0 ERR_LOW_COUNT=0 LOG_DIR=`jq .log_dir $DATA_FILE|sed 's/\"//g'` LOG_FILE=$LOG_DIR/$tstemp.backup.log LOG_CHECK_FILE=$LOG_DIR/$tstemp.backup.check.log } error_check() { IGNOR=`jq .error_hand.err_ignore $DATA_FILE|sed 's/\"//g'` echo "error to ignor : "$IGNOR HIGH=`jq .error_hand.err_high $DATA_FILE|sed 's/\"//g'` MEDIUM=`jq .error_hand.err_medium $DATA_FILE|sed 's/\"//g'` LOW=`jq .error_hand.err_low $DATA_FILE|sed 's/\"//g'` for FILE in `cat $LOG_CHECK_FILE | grep '<f'|cut -d\/ -f2-` do echo "check line "$FILE if [[ $IGNOR = "" ]] then error_check_sub else for TYPE in ${IGNOR[@]} do if ( ! $FILE| grep $TYPE ) then error_check_sub fi done fi done messaging } error_check_sub() { if ( cat $LOG_FILE | grep $FILE ) then echo "check line "$FILE for i in ${HIGH[@]} do if ( $FILE|grep $i ) then (($ERR_HIGH_COUNT++)) fi done for i in ${MEDIUM[@]} do if ( $FILE|grep $i ) then (($ERR_MEDIUM_COUNT++)) fi done for i in ${LOW[@]} do if ( $FILE|grep $i ) then (($ERR_LOW_COUNT++)) fi done (($ERR_COUNT++)) echo $ERR_COUNT fi } messaging() { echo "generate message for syslog" if [ $ERR_COUNT -gt 0 ] then if [ $ERR_HIGH_COUNT -eq 0 ] then pre_massage=' <error>' else pre_message=' <warning>' fi message=$pre_message' : backup has '$ERR_COUNT' failures: '$ERR_HIGH_COUNT' high, '$ERR_MEDIUM_COUNT' medium and '$ERR_LOW_COUNT' low; check errorlog in '$LOG_DIR echo "backup has "$ERR_COUNT else message=' <info> : backup successfully completed' if [[ `jq .log_remove $DATA_FILE|sed 's/\"//g'` = "yes" ]] then rm $LOG_DIR/* fi fi } replicate() { echo "job 'replicate' is running" TARGET_DIR=`jq .jobs.replicate.remote_folder $DATA_FILE|sed 's/\"//g'` REPL_OPT=`jq .jobs.replicate.repli_opt $DATA_FILE|sed 's/\"//g'` METHOD=`jq .jobs.replicate.method $DATA_FILE|sed 's/\"//g'` if [[ ! $REPL_OPT = "" ]] then if [[ $REPL_OPT = "local" ]] then DESTIN=$MOUNT_P/$TARGET_DIR PASSFILE="" if [ ! -d $DESTIN ] then echo $DESTIN" not exist, will create" mkdir $DESTIN fi DESTIN=$DESTIN/ echo "local sync target "$DESTIN else SERVER=`jq .jobs.replicate.sync_server $DATA_FILE` if( ! ping -c 3 $SERVER > /dev/null ) then (($ERR_STOP++)) message="<info> : server "$SERVER" not reachable" break fi USER=`jq .jobs.replicate.sync_user $DATA_FILE|sed 's/\"//g'` PASS_OPT=`jq .jobs.replicate.pass_option $DATA_FILE` DESTIN=$USER@$SERVER::/$MOUNT_P/$TARGET_DIR/ echo "remote sync with "$DESTIN fi FOLDERS=`jq .jobs.replicate.sync_folders $DATA_FILE|sed 's/\"//g'` echo $FOLDERS date >> $LOG_FILE date >> $LOG_CHECK_FILE for DIR in ${FOLDERS[@]} do echo $DIR echo "run : "$METHOD `jq .jobs.replicate.run_options $DATA_FILE|sed 's/\"//g'` $DIR $DESTIN $PASS_OPT echo " " >> $LOG_FILE echo "{"$DIR"()" >> $LOG_FILE $METHOD `jq .jobs.replicate.run_options $DATA_FILE|sed 's/\"//g'` $DIR $DESTIN $PASS_OPT >> $LOG_FILE echo " " >> $LOG_CHECK_FILE echo "{"$DIR"()" >> $LOG_CHECK_FILE $METHOD `jq .jobs.replicate.log_options $DATA_FILE|sed 's/\"//g'` $DIR $DESTIN $PASS_OPT >> $LOG_CHECK_FILE echo "}" >> $LOG_FILE echo "}" >> $LOG_CHECK_FILE done date >> $LOG_FILE date >> $LOG_CHECK_FILE error_check else (($ERR_STOP++)) message=" <warning> : no method defined" fi } mount_fs() { echo "job 'mount_fs' is running" # check if target host available TARGET_SRV=`jq .jobs.mount_fs.ping_target $DATA_FILE|sed 's/\"//g'` echo "check, if you'r in right location, try to ping "$TARGET_SRV MOUNT_P=`jq .jobs.mount_fs.mount_point $DATA_FILE|sed 's/\"//g'` if( ping -c 3 $TARGET_SRV > /dev/null ) then echo $TARGET_SRV" reachable, you'r in right location to backup" if [[ `jq .jobs.mount_fs.mount_def $DATA_FILE|sed 's/\"//g'` = "file" ]] then echo "mount "`jq .jobs.mount_fs.mount_opt $DATA_FILE|sed 's/\"//g'` `jq .jobs.mount_fs.mount_file $DATA_FILE|sed 's/\"//g'` $MOUNT_P mount `jq .jobs.mount_fs.mount_opt $DATA_FILE|sed 's/\"//g'` `jq .jobs.mount_fs.mount_file $DATA_FILE|sed 's/\"//g'` $MOUNT_P else CONNECT=`jq .jobs.mount_fs.mount_srv $DATA_FILE|sed 's/\"//g'`:`jq .jobs.mount_fs.mount_share $DATA_FILE|sed 's/\"//g'` echo "mount "`jq .jobs.mount_fs.mount_opt $DATA_FILE|sed 's/\"//g'` $CONNECT $MOUNT_P mount `jq .jobs.mount_fs.mount_opt $DATA_FILE|sed 's/\"//g'` $CONNECT $MOUNT_P fi sleep 10 # be sure mount is completed or timed out if ( mount | grep $MOUNT_P > /dev/null ) then MOUNT_FS=`jq .jobs.mount_fs.mount_point $DATA_FILE|sed 's/\"//g'` echo "umount "$MOUNT_FS" needed" else (($ERR_STOP++)) message=" <warning> : Can not mount backup target volume" fi else (($ERR_STOP++)) message=" <info> : "$TARGET_SRV" not reachable, server down or you are not at right location" fi } # master function main() { # select job sequence SEQUENCE=`jq .job_seq $DATA_FILE|sed 's/\"//g'` echo "job sequence are : "$SEQUENCE if [[ $SEQUENCE = "" ]] then message=" <info> no jobs defined" else for JOB in ${SEQUENCE[@]} do if ( echo $JOB | grep add_tasks ) then SUB_TASK=${JOB##*.} TARGET=$WORK_DIR`jq .jobs.add_tasks.$SUB_TASK.folder $DATA_FILE|sed 's/\"//g'`/ echo "sub task target "$TARGET echo "run sub task : "`jq .jobs.$JOB.task $DATA_FILE|sed 's/\"//g'` $TARGET `jq .jobs.$JOB.task $DATA_FILE|sed 's/\"//g'` $TARGET else echo "run main job : "$JOB $JOB fi if [[ $ERR_STOP -gt 0 ]] then logger $message exit fi done fi echo "clean up" if [[ ! $MOUNT_FS = "" ]] then echo "umount "$MOUNT_FS umount $MOUNT_FS fi logger $message } setup main exit