Sauvegarde chiffrée d’un serveur dédié vers FTP

Je sais pas chez vous mais ici aujourd’hui c’est après-midi pluvieux. Et qui dit après-midi pluvieux dit maintenance sur mon petit serveur !
Je me suis attelé à la réécriture du script de sauvegarde du serveur, car mon vieux truc moisi avec rsync commençait à me faire un peu honte…

Dernière mise à jour le 17/07/2014 (mise à jour mineure)

J’ai donc commencé par poser la question à mon canard préféré et je suis tombé sur un site que je connais bien puisqu’il s’agit du blog de Nono, qui nous propose depuis février 2012 un script assez complet :

  • Archivage / Compression des dossiers choisis dans un dossier local daté.
  • Archivage / Compression des bases de données MySQL.
  • Envoi du contenu du dossier de sauvegarde vers un FTP.
  • Suppression du contenu du dossier local (ben oui pas la peine de garder une copie locale…).
  • Génération de rapport et envoi par email.

Comme il ne convenait pas exactement à mon cas, j’y ai apporté quelques modifications :

  • Les archives sont toutes chiffrées avec OpenSSL grâce à l’algorithme de chiffrement AES-256.
  • Les bases de données MySQL sont archivées par base (une archive = une base) et non pas de manière globale.
  • La liste des dossier à sauvegarder est placée dans un tableau, que le script va parcourir.

Sans compter une petite erreur par-ci / par-là 😀

Dépendances et fonctionnement du script

Ce script repose donc sur l’utilisation des outils OpenSSL, lftp, tar et gzip (et la commande mail au cas où). Le voici :

 
 
#!/bin/bash
# Script de sauvegarde du serveur par Guillaume
# Librement inspiré de http://blog.m0le.net/2012/02/17/le-petit-script-de-backup-de-nono/
 
date_start=`date +'%d/%m/%Y @ %H:%M:%S'`;
format_date='%d%m%Y';
date=`date +${format_date}`;
keepday="7";
keepdate=`date --date "-${keepday} days" +${format_date}`;
backup_dir='/home/backup/'${date};
rapport='/home/backup/backup.log';
sql_pass='SQLPASSWORD';
archives_pass='PASSWORD';
ftp_host='ftp.mon-domaine.de';
ftp_user='FTPUSER';
ftp_pass='FTPPASSWORD';
mail='mail@mon-domaine.fr';
 
# Création du répertoire de backup et initialisation du rapport
mkdir -p ${backup_dir}
echo -e "Rapport du ${date_start}.\n\n" > ${rapport};
 
# Tableau des répertoires à sauvegarder
backup=( '/etc/dossier1' '/home/dossier2' '/var/lib/dossier3' )
 
# Initialisation de la boucle et parcours du tableau
index=0
length=${#backup[*]}
 
while  [ "$index" -lt "$length" ]
do
        tar -jc ${backup[$index]} | openssl enc -e -aes256 -k ${archives_pass} -out ${backup_dir}/91-121-166-59.kimsufi.com${backup[$index]//\//_}.bz2.enc 2> /dev/null
        let "index = $index+1"
done
 
# Dump de MySQL
for db in `mysql -uroot -h localhost -p${sql_pass} -Bse 'show databases'`; do
  if [ "$db" != "information_schema" ]; then
        mysqldump -uroot -p${sql_pass} -h localhost --events $db | gzip -9 | openssl enc -e -aes256 -k ${archives_pass} -out ${backup_dir}/91-121-166-59.kimsufi.com_sqldump_"$db"_${date}.sql.bz2.enc
  fi
done
 
# Mise à jour du rapport
echo "Etat du dossier local :" >> ${rapport};
ls -lh ${backup_dir} -I rapport* >> ${rapport};
echo " " >> ${rapport};
 
# Envoi du dossier vers le FTP
echo "Etat du dossier distant :" >> ${rapport};
lftp ftp://${ftp_user}:${ftp_pass}@${ftp_host} -e "mirror -R ${backup_dir} /${date} ; quit" >> ${rapport};
echo " " >> ${rapport};
 
# Suppression du dossier local
echo "Suppression du dossier local : ${backup_dir}" >> ${rapport};
rm -rf ${backup_dir};
echo " " >> ${backup_dir};
 
# Suppression du dossier distant de plus de "$keepday" jour(s)
echo -e "Suppression du dossier distant de plus de ${keepday} jours : ${keepdate}.\n" >> ${rapport};
echo "Etat du FTP :" >> ${rapport};
lftp ftp://${ftp_user}:${ftp_pass}@${ftp_host} -e "rm -rf ${keepdate} ;ls ; quit" >> ${rapport};
 
# Finalisation du rapport et envoi par email
date_end=`date +'%d/%m/%Y @ %H:%M:%S'`;
echo -e "\nSauvegarde terminee le ${date_end}." >> ${rapport};
mail -s "Rapport de sauvegarde du `date +%d\/%m\/%Y`" ${mail} < ${rapport};

Explications

Vous l’aurez compris, c’est la commande openssl enc -e -aes256 -k pass_de_larchive -out nom_sortie qui chiffre tout cela. Pour déchiffrer une archive chiffrée de cette manière, utilisez simplement la commande suivante :

openssl enc -d -aes256 -k pass_de_larchive -in fichier_a_dechiffrer -out fichier_de_sortie

Vous trouverez quelques autres moyens de chiffrer une archive sur k0n1k.com qui m’a beaucoup aidé.

Le résultat

Ce petit script vous génère donc un email journalier ressemblant à cela :

 
 
Rapport du 04/03/2014 @ 02:10:01.
 
 
Etat du dossier local :
total 911M
-rw-r--r-- 1 root root 7,2M mars   4 02:24 91-121-166-59.kimsufi.com_etc.tar.bz2.enc
-rw-r--r-- 1 root root 2,8M mars   4 02:24 91-121-166-59.kimsufi.com_home_guillaume.tar.bz2.enc
[...]
-rw-r--r-- 1 root root 2,3K mars   4 02:32 91-121-166-59.kimsufi.com_sqldump_phpmyadmin_04032014.sql.gz.enc
-rw-r--r-- 1 root root  22K mars   4 02:32 91-121-166-59.kimsufi.com_sqldump_prod_pydio_04032014.sql.gz.enc
-rw-r--r-- 1 root root  496 mars   4 02:32 91-121-166-59.kimsufi.com_sqldump_test_04032014.sql.gz.enc
-rw-r--r-- 1 root root  22K mars   4 02:32 91-121-166-59.kimsufi.com_usr_ssl.tar.bz2.enc
-rw-r--r-- 1 root root 547K mars   4 02:24 91-121-166-59.kimsufi.com_var_awstats.tar.bz2.enc
-rw-r--r-- 1 root root 392M mars   4 02:32 91-121-166-59.kimsufi.com_webroot.tar.bz2.enc
 
Etat du dossier distant :
 
Suppression du dossier local : /home/backup/04032014
Suppression du dossier distant de plus de 7 jours : 25022014.
 
Etat du FTP :
drwx---r-x    4 96475      users               4 Mar  4 02:39 .
drwx---r-x    4 96475      users               4 Mar  4 02:39 ..
drwx---r-x    2 96475      users              24 Mar  3 17:52 03032014
drwx---r-x    2 96475      users              24 Mar  4 02:42 04032014
 
Sauvegarde terminee le 04/03/2014 @ 02:34:58.

Si vous avez des idées ou des suggestions à apporter n’hésitez pas ! )

Cet article vous a plu ? Partagez-le sur les réseaux sociaux !

Twitter Facebook Google Plus email