• # Rsync toujours...

    Posté par . En réponse au message [Résolu] Backup (oui, c'est une vielle problématique). Évalué à 1. Dernière modification le 10 mars 2014 à 21:34.

    Salut à tous,

    Dans le même esprit qu'Axone, j'ai écrit un script rsync dont le principe est le suivant :

    • Un ou plusieurs répertoires sources, et du coup, un ou plusieurs répertoires de destination possibles.
    • La sauvegarde est incrémentale, chaque fichier modifié depuis la dernière sauvegarde est suffixé par la date de la sauvegarde (monfichier.txt et monfichier.txt_201404_03_09 sont dans le même répertoire)
    • Possibilité de faire un "rsync --delete" ponctuel du répertoire de destination, par exemple tous les lundis après externalisation, ou pas.
    • Possibilité d'avoir une source et/ou une destination SSH, l'échange des clés doit être fait au préalable bien sur.
    • Écriture dans un fichier de log et rotation du fichier de log
    • Utilisation du fichier de filtre rsync

    La contrainte est d'avoir un répertoire de destination non vide la première backup. j'ai du faire cette vérification pour éviter qu'un éventuel répertoire CIFS mal monté déclenche une sauvegarde en local, ce qui pourrait rapidement saturé un disque local s'il n'est pas prévu pour. Créer un fichier bidon lors de la première sauvegarde suffit.

    En le relisant je vois pas mal d'améliorations possible, mais jusqu'à présent ça m'a déjà pas mal rendu service.

    Enjoy !

     #!/bin/bash
     #jour de la semaine ou est remise a zero la sauvegarde (1-7 - 0 pour ne jamais executer de rsync --delete)
     day_to_delete=0
     # Nombre de jours avant nettoyage par le find
     day_to_conserve=60
     #le chemin de source et de destination doivent exister et etre non vide - (sauf si ssh)
     srcpath=( "/first/source/path" "/second/source/path" )
     destpath=( "/first/dest/path" "/second/dest/path" )
     #Fichier de filtre (unique pour X synchros)
     filter_file="/rsync/filter/file/path.txt"
     #SSH SOURCE PARAM
     sshsourcebackup=0
     sshsourcelogin=user
     sshsourcehost=host
     #SSH DEST PARAM
     sshdestbackup=0
     sshdestlogin=user
     sshdesthost=host
     #Log file
     log_file="/path/to/log/file.txt"
     maxlines=1000
     #
     # Script
     #
     todayinweek=`date +%u`
     today=`date +%F`
     ######
     #FONCTION ecriture dans fichier de log et rotation des logs (update du 26/10/2011)
     function writelogandrotate
     {
     #refresh date of log writing
     date_log=$( date +%d-%m-%Y )' '$( date +%H:%M:%S )
     #write log in the log file (given in parameter)
     echo $date_log' '1ドル >> $log_file
     #show whats written to the stdout
     echo $date_log' '1ドル
     #purge log file
     nblines=`cat $log_file | wc -l`
     #while the logline var is less than the number of line in the log file
     while [ "$maxlines" -lt "$nblines" ]
     do
    sed -i '1d' $log_file
     nblines=`cat $log_file | wc -l`
     done
     }
     ####################SCRIPT
     if [ "$sshsourcebackup" = "1" ] ; then
    sshcmd="-e ssh"
     sshsourcecred="${sshsourcelogin}@${sshsourcehost}:"
     fi
     if [ "$sshdestbackup" = "1" ] ; then
    sshcmd="-e ssh"
     sshdestcred="${sshdestlogin}@${sshdesthost}:"
     fi
     #test de l existance des repertoires sources et destination (sauf si ssh activé)
     for (( i = 0 ; i < ${#srcpath[@]} ; i++ ))
     do
     if [ ! "$(ls -1A ${srcpath[$i]})" ] && [ "$sshsourcebackup" = "0" ] ; then
     ( writelogandrotate "Source ${srcpath[$i]} vide et ssh non activé. Abort." )
     exit 1
     fi
     if [ ! "$(ls -1A ${destpath[$i]})" ] && [ "$sshdestbackup" = "0" ] ; then
     ( writelogandrotate "Destination ${destpath[$i]} vide et ssh non activé. Abort." )
     exit 1
     fi
     done
     #
     if [ $day_to_delete -eq $todayinweek ] ; then
     ( writelogandrotate "Nous sommes le jour $day_to_delete de la semaine, execution de rsync --delete : " )
     for (( i = 0 ; i < ${#srcpath[@]} ; i++ ))
     do
     ( writelogandrotate "Démarrage du script de sauvegarde incrémentielle de ${srcpath[$i]} vers ${destpath[$i]}" )
     rsyncexec=`rsync $sshcmd -a --stats --filter="merge $filter_file" --delete-after --force "$sshsourcecred""${srcpath[$i]}" "${sshdestcred[$i]}""${destpath[$i]}"`
     nbfiles_synced=`echo $rsyncexec | grep transferred | cut -d " " -f9`
     total_files_synced=$(( nbfiles_synced + total_files_synced ))
     done
     ( writelogandrotate $total_files_synced" fichiers transférés" )
     msg=$total_files_synced
     else
     ( writelogandrotate "Execution de la sauvegarde incrementielle" )
     for (( i = 0 ; i < ${#srcpath[@]} ; i++ ))
     do
     ( writelogandrotate "Démarrage du script de sauvegarde incrémentielle de ${srcpath[$i]} vers ${destpath[$i]}" )
     rsyncexec=`rsync $sshcmd -a --stats --filter="merge $filter_file" --backup --suffix=_"$today" "$sshsourcecred""${srcpath[$i]}" "$sshdestcred""${destpath[$i]}"`
     nbfiles_synced=`echo $rsyncexec | grep transferred | cut -d " " -f9`
     total_files_synced=$(( nbfiles_synced + total_files_synced ))
     done
     ( writelogandrotate $total_files_synced" fichiers transférés" )
     msg=$total_files_synced
     #clean day_to_conserve+1 days backup - if backup destination is not SSH
     if [ "$sshdestbackup" = "0" ] ; then
     ( writelogandrotate "Nettoyage des fichiers datés de $day_to_conserve +1 jours - Uniquement si destination non SSH !" )
     find $destpath -name *_`date --date=$day_to_conserve' days ago' +%F` -exec rm -rf {} \;
     fi
     fi
     ( writelogandrotate "Fin du script" )
     #end