Backup mysql
| Ce wiki a été archivé en 2018.
Le nouveau wiki se trouve à: ressources.labomedia.org Les fonctionnalités sont désactivées: vous pouvez faire une recherche sur Google site:https://wiki.labomedia.org et découvrir La Labomedia. |
De Centre de Ressources Numériques - Labomedia
Petit Script perso de sauvegarde d'une base de données mysql en bash (par JO) :
Sommaire
Déroulement du script
- dump mysql qui génère 2 fichiers .sql par base de donnée (un pour la structure, et un pour les données)
- création d'une archivage .tar.gz
- enregistrement de l'archive dans un dossier prédéfini
- suppression des archives trop anciennes
- envois d'un email de listing des backups disponibles (ou d'un log d'erreur si il y en a une)
Configurations disponibles
- DB_LOGIN_PATH login path utilisé lors du mysql_config_editor pour vous connecter à mysql
- MAIL_REPORT email du rapport
- MAIL_SUBJECT sujet du mail
- FOLDER_BACKUP répertoire de stockage des sauvegardes
- FOLDER_WWW URL d'accès aux sauvegardes
- FILE_LOG fichier de log
- FILE_INFO fichier de listing des sauvegardes
- BACKUP_NAME nom de l'archive de chaque sauvegarde
- BACKUP_IGNORE_DATABASES base de données à ignorer lors de la sauvegarde
- BACKUP_IGNORE_TABLES_DATA contenu des tables à ignorer lors de la sauvegarde (ignore uniquement le contenu, la structure sera bien sauvegardée)
- BACKUP_RETENTION nombre de jours max de rétention des sauvegardes avant suppression
Installation du script
Le script necessite un utilisateur (ici backup) pour accéder à votre base de données.
mysql -u root -p -e "CREATE USER 'backup'@'localhost' IDENTIFIED BY '[VOTRE_MOT_DE_PASSE]';"
mysql -u root -p -e "GRANT SELECT , SHOW DATABASES , LOCK TABLES , SHOW VIEW ON * . * TO 'backup'@'localhost' IDENTIFIED BY '[VOTRE_MOT_DE_PASSE]' WITH MAX_QUERIES_PER_HOUR 0 MAX_CONNECTIONS_PER_HOUR 0 MAX_UPDATES_PER_HOUR 0 MAX_USER_CONNECTIONS 0 ;"
Pour ne pas avoir le mot de passe en clair dans le script:
mysql_config_editor set --login-path=backup --host=localhost --user=backup --passwordPensez à rendre executable le script de sauvegarde:
chmod +x backup.sh
Le Script en question pour backup vos bases de données MySQL
#!/bin/bash
########################################################################
#
# Génération d'une sauvegarde des base de données
# Il faudra éxecuter le script automatiquement grâce à un cron
#
# Le script necessite un utilisateur pour accéder à la base de données:
# mysql -u root -p -e "CREATE USER 'backup'@'localhost' IDENTIFIED BY 'VOTRE_MOT_DE_PASSE';"
# mysql -u root -p -e "GRANT SELECT , SHOW DATABASES , LOCK TABLES , SHOW VIEW ON * . * TO 'backup'@'localhost' IDENTIFIED BY 'VOTRE_MOT_DE_PASSE' WITH MAX_QUERIES_PER_HOUR 0 MAX_CONNECTIONS_PER_HOUR 0 MAX_UPDATES_PER_HOUR 0 MAX_USER_CONNECTIONS 0 ;"
#
# Pour ne pas avoir le mot de passe en clair dans le script:
# mysql_config_editor set --login-path=backup --host=localhost --user=backup --password
#
# Pensez à rendre executable le script de sauvegarde: chmod +x backup.sh
#
########################################################################
# login path utilisé lors du mysql_config_editor
DB_LOGIN_PATH="backup"
# email du rapport
MAIL_REPORT="email@domain.com"
#sujet du mail
MAIL_SUBJECT="Mon super Backup Backup $(date +%Y.%m.%d@%Hh%M)"
# Répertoire de stockage des sauvegardes
FOLDER_BACKUP="$HOME/Mes_Backups"
# URL d'accès aux sauvegardes
FOLDER_WWW="https://monsite.com/Mes_Backups/"
# Fichiers de log et infos
FILE_LOG="${FOLDER_BACKUP}/backup.log"
FILE_INFO="${FOLDER_BACKUP}/backup.txt"
# Nom de la sauvegarde
BACKUP_NAME="backup"
# Base de données à ignorer lors de la sauvegarde
BACKUP_IGNORE_DATABASES=(
"mysql"
"performance_schema"
"phpmyadmin"
"test"
"sys"
)
# Contenu des tables à ignorer lors de la sauvegarde (ignore uniquement le contenu, la structure sera bien sauvegardée)
# Ex. "DATABASE.TABLE1" "DATABASE.TABLE2" "DATABASE2.TABLE1"
BACKUP_IGNORE_TABLES_DATA=(
"database.table1"
)
# Nombre de jours max de rétention des sauvegardes
BACKUP_RETENTION=30
########################################################################
#
# NE PAS TOUCHER AU RESTE DU CODE SAUF SI VOUS SAVEZ CE QUE VOUS FAITE !
#
########################################################################
# Format de nommage du fichier de sauvegarde (ne pas changer au risque de casser les rotations)
BACKUP_DATE="$(date +%Y.%m.%d-%Hh%M)"
BACKUP_FILE="${BACKUP_NAME}-${BACKUP_DATE}"
BACKUP_PATH="${FOLDER_BACKUP}/${BACKUP_FILE}"
########################################################################
#
# Fonctions du script
#
########################################################################
tmp_folder_create() {
echo "- Création du répertoire de sauvegarde temporaire: ${BACKUP_PATH}"
mkdir "${BACKUP_PATH}" 2>> "$FILE_LOG"
}
tmp_folder_delete() {
echo "- Suppression du répertoire de sauvegarde temporaire: ${BACKUP_PATH}"
rm -rf "${BACKUP_PATH}" 2>> "$FILE_LOG"
}
mysql_connect() {
echo "- Connexion à mysql pour lister toutes les BDD du serveur."
DATABASES="$(mysql --login-path=$DB_LOGIN_PATH -Bse 'show databases' 2>> $FILE_LOG | grep -v information_schema)"
}
mysql_dump() {
echo "- Dump des bases de données"
BACKUP_IGNORE_TABLES_ARG=""
for TABLE in "${BACKUP_IGNORE_TABLES_DATA[@]}"
do
BACKUP_IGNORE_TABLES_ARG+=" --ignore-table=${TABLE}"
done
for DATABASE in ${DATABASES[@]}
do
if [[ ! " ${BACKUP_IGNORE_DATABASES[@]} " =~ " ${DATABASE} " ]]; then
echo " - Sauvegarde: $DATABASE.sql"
mysqldump --login-path=$DB_LOGIN_PATH --quick --add-locks --lock-tables --extended-insert --no-data $DATABASE > "${BACKUP_PATH}/${DATABASE}-structure.sql" 2>> $FILE_LOG
mysqldump --login-path=$DB_LOGIN_PATH --quick --add-locks --lock-tables --extended-insert --no-create-info $BACKUP_IGNORE_TABLES_ARG $DATABASE > "${BACKUP_PATH}/${DATABASE}-data.sql" 2>> $FILE_LOG
fi
done
}
compress_dump() {
echo "- Archivage de la sauvegarde: ${BACKUP_FILE}.tar.gz"
cd "${FOLDER_BACKUP}"
tar -czf "${BACKUP_FILE}.tar.gz" "${BACKUP_FILE}" 2>> "$FILE_LOG"
chmod 600 "${BACKUP_FILE}.tar.gz" 2>> "$FILE_LOG"
}
archive_link_latest() {
echo "- Création du lien symbolique vers la dernière version: ${BACKUP_NAME}-latest.tar.gz"
unlink "${BACKUP_NAME}-latest.tar.gz"
ln -s "${BACKUP_FILE}.tar.gz" "${BACKUP_NAME}-latest.tar.gz"
}
archive_remove_oldest() {
echo "- Suppression des anciennes sauvegardes obsolètes"
find "${FOLDER_BACKUP}" -name "*.tar.gz" -mtime +$BACKUP_RETENTION -print -exec rm {} \;
}
file_info() {
echo "- Génération du nouveau fichier d'informations sur les sauvegardes: ${FILE_INFO}"
rm "${FILE_INFO}"
find "${FOLDER_BACKUP}" -name "*.tar.gz" -exec basename {} \; | sort -r | while read file; do echo "${FOLDER_WWW}$file" >> "${FILE_INFO}"; done
}
mail_report_success() {
echo "- Email du rapport des sauvegardes"
cat $FILE_INFO | mail -s "$MAIL_SUBJECT" $MAIL_REPORT
}
mail_report_error() {
echo "- Email de log des erreurs"
cat $FILE_LOG | mail -s "[ERROR :(] $MAIL_SUBJECT" $MAIL_REPORT
}
########################################################################
#
# Déroulement du script
#
########################################################################
echo "############################################################################### BACKUP"
echo "########################################################################" > "${FILE_LOG}"
echo "# NEW BACKUP ${BACKUP_DATE}" >> "${FILE_LOG}"
echo "" >> "${FILE_LOG}"
tmp_folder_create
mysql_connect
mysql_dump
# le répertoire temporaire des dump est vide !
if [ -z "$(ls -A $BACKUP_PATH)" ]; then
echo "No mysql dump found" >> "${FILE_LOG}"
else
compress_dump
fi
tmp_folder_delete
# succès, une archive a été créé
if [ -f "${BACKUP_FILE}.tar.gz" ]; then
archive_link_latest
archive_remove_oldest
echo "" >> "${FILE_LOG}"
echo "# SUCCESS :)" >> "${FILE_LOG}"
echo "########################################################################" >> "${FILE_LOG}"
echo "" >> "${FILE_LOG}"
echo "" >> "${FILE_LOG}"
file_info
mail_report_success
echo "############################################################################### SUCCESS :)"
exit 0;
# erreur, aucune archive n'a été créé
else
echo "" >> "${FILE_LOG}"
echo "# ERROR :(" >> "${FILE_LOG}"
echo "########################################################################" >> "${FILE_LOG}"
echo "" >> "${FILE_LOG}"
echo "" >> "${FILE_LOG}"
file_info
mail_report_error
echo "############################################################################### ERROR :("
exit 1;
fi