我编写了一个在cron上启动的bash脚本,它每晚和每周备份一台特定计算机上的所有数据库。该脚本正确地删除了旧数据库,除了那些月份发生变化的情况。
举个例子,假设是11月2日。该脚本在晚上11点运行,并正确删除从11月1日开始的备份。但到了12月1日,脚本会变得混乱,并且无法正确删除11月30日制作的备份。
在这种情况下,如何修复此脚本以正确删除旧备份?
DATABASES=$(echo 'show databases;' | mysql -u backup --password='(password)' | grep -v ^Database$)
LIST=$(echo $DATABASES | sed -e "s/\s/\n/g")
DATE=$(date +%Y%m%d)
DAYOLD=$(($DATE-1))
SUNDAY=$(date +%a)
WEEKOLD=$(($DATE-7))
for i in $LIST; do
if [[ $i != "mysql" ]]; then
mysqldump --single-transaction $i > /mnt/backups/mariadb/daily/$i.$DATE.sql
if [ -f /mnt/backups/mariadb/daily/$i.$DAYOLD.sql ]; then
rm -f /mnt/backups/mariadb/daily/$i.$DAYOLD.sql
fi
if [[ $SUNDAY == "Sun" ]]; then
cp /mnt/backups/mariadb/daily/$i.$DATE.sql /mnt/backups/mariadb/weekly/$i.$DATE.sql
rm -f /mnt/backups/mariadb/weekly/$i.$WEEKOLD.sql
fi
fi
done
答案 0 :(得分:1)
如果您知道在特定时间范围内执行的备份数量,请假设您知道从11月2日到12月2日,您知道已经完成了30次备份,而您现在想要删除这些备份,只需使用备份,这很简单,你不必处理bash中非常复杂的日期:
$ (ls -t|head -n 30;ls)|grep -v ^Database|sort|uniq -u|xargs rm -rf
然后,您可以通过删除旧版本的每一天来轻松自动执行此脚本,这样您只能获得所需的修订备份数量:
#! /bin/bash
# Create new full backup
BACKUP_DIR="/path-to-backups/"
BACKUP_DAYS=1
# Prepare backup
cd ${BACKUP_DIR}
latest=`ls -rt | grep 201 | head -1`
# Change latest reference
ln -sf ${BACKUP_DIR}${latest} latest
# Cleanup older than one week (n days)
to_remove=`(ls -t | grep 201 | head -n 3;ls)|sort|uniq -u`
echo "Cleaning up... $to_remove"
(ls -t|head -n ${BACKUP_DAYS};ls)|sort|uniq -u|xargs rm -rf
echo "Backup Finished"
exit 0
然后你可以将它链接到每日cron。这篇博客文章对此进行了解释,如何以非常简单的方式完成这些工作(但是使用热备份,没有mysqldump):http://codeispoetry.me/index.php/mariadb-daily-hot-backups-with-xtrabackup/
答案 1 :(得分:0)
我让这太复杂了。我只是用以下方式搜索文件备份的年龄,而不是使用日期:
find /mnt/backups/mariadb/weekly/* -type f -mtime +8 -exec rm -f {} \;
所以整个脚本变成了:
DATABASES=$(echo 'show databases;' | mysql -u backup --password='foo' | grep -v ^Database$)
LIST=$(echo $DATABASES | sed -e "s/\s/\n/g")
DATE=$(date +%Y%m%d)
SUNDAY=$(date +%a)
for i in $LIST; do
if [[ $i != "mysql" ]]; then
/bin/nice mysqldump --single-transaction $i > /mnt/backups/mariadb/daily/$i.$DATE.sql
find /mnt/backups/mariadb/daily/* -type f -mtime +1 -exec rm -f {} \;
if [[ $SUNDAY == "Sun" ]]; then
cp /mnt/backups/mariadb/daily/$i.$DATE.sql /mnt/backups/mariadb/weekly/$i.$DATE.sql
find /mnt/backups/mariadb/weekly/* -type f -mtime +8 -exec rm -f {} \;
fi
fi
chown -R backup.backup /mnt/backups
done