1 备份服务器
在日常运行中,正式环境、测试环境经常有一些文件、数据、配置等重要内容需要备份。但是手动备份的话将会花费很长时间,因此建议一个备份脚本对服务器稳定、恢复有重要意义。
#!/bin/bash
echo "started"
BACK_PATH=/backup/
TIME=$(date +%F)
PGSQL_BACK_DATA=${BACK_PATH}pgsql-${TIME}.bak
CANDAO_PATH=${BACK_PATH}candao-${TIME}/
CANDAO_BACK_NAME=${BACK_PATH}/candao-${TIME}.tar.gz
GITLAB_CONFIG1_BACK=${BACK_PATH}/gitlab.rb-${TIME}.bak
GITLAB_CONFIG2_BACK=${BACK_PATH}/gitlab-secrets.json-${TIME}.bak
SHOWDOC_BACK=${BACK_PATH}/showdoc-${TIME}.zip
MYSQL_BACK=${BACK_PATH}/mysql-${TIME}.zip
#删除大于30天的备份
echo "开始删除30天前的备份文件.........."
find /backup -mtime +30 -name "*.*" -exec rm -rf {} \;
echo "删除30天前的备份文件完成.........."
#执行PGSQL备份
echo "PGSQL数据库备份开始"
echo "PGSQL数据库备份中......"
export PGPASSWORD="123456"
pg_dumpall -h 127.0.0.1 -p 11000 -U postgres -c -f ${PGSQL_BACK_DATA}
echo "PGSQL数据库备份完成......"
#执行禅道备份
echo "禅道数据备份开始"
echo "禅道数据备份中......"
echo "停止apache和mysql服务中......"
/opt/zbox/zbox stop
echo "压缩文件中......"
zip -r ${CANDAO_BACK_NAME} /opt/zbox
echo "启动apache和mysql服务中......"
/opt/zbox/zbox start
echo "禅道数据备份完成......"
#执行gitlab备份
echo "gitlab数据备份开始"
echo "gitlab数据备份中......"
gitlab-rake gitlab:backup:create
mv /var/opt/gitlab/backups/*.tar /backup/
echo "gitlab-配置文件备份中......"
cp /etc/gitlab/gitlab.rb ${GITLAB_CONFIG1_BACK}
cp /etc/gitlab/gitlab-secrets.json ${GITLAB_CONFIG2_BACK}
echo "gitlab数据备份完成......"
#执行showdoc备份
echo "showdoc数据备份开始"
echo "showdoc数据备份中......"
zip -r ${SHOWDOC_BACK} /var/www/html/showdoc-master
echo "showdoc数据备份完成......"
#执行mysql备份
mysqldump -h 192.168.1.100 -p 3306 -uroot -ppassword --database cmdb > MYSQL_BACK
#移动文件至windows
echo "开始复制文件到备份机"
sshpass -p '123456' scp -r /backup/*$(date +%F)* admin@192.168.12.108:/d:/backup/
echo "开始传送gitlab备份文件"
sshpass -p '123456' scp -r /backup/*$(date +%Y_%m_%d)* admin@192.168.12.108:/d:/backup/
echo "复制文件到windows完成......."
echo "${TIME}-今日数据备份完成......"
以上配置数据均为虚拟的地址,需要根据实际情况做对应更改后生效
2 备份数据库
在内网服务器上往往有一些重要数据库需要备份,如何实现呢。
(1)编写mysql及pgsql备份语句
- mysql内容如下:
#!/bin/bash
BACK_PATH=/backup/
TIME=$(date +%F)
PGSQL_BACK_DATA=${BACK_PATH}mysql-${TIME}.bak
#删除大于15天的备份
echo "开始删除15天前的备份文件.........."
find /backup -mtime +15 -name "*.*" -exec rm -rf {} \;
echo "删除15天前的备份文件完成.........."
#执行MLSQL备份
echo "MLSQL数据库备份开始"
echo "MLSQL数据库备份中......"
mysqldump -h 127.0.0.1 -u root -p'123456' --all-databases > /backup/$(date +%Y_%m_%d)_mysql_backup.sql
echo "MLSQL数据库备份完成......"
- pgsql备份脚本
#!/bin/bash
BACK_PATH=/backup/
TIME=$(date +%F)
PGSQL_BACK_DATA=${BACK_PATH}pgsql-${TIME}.bak
#删除大于15天的备份
echo "开始删除15天前的备份文件.........."
find /backup -mtime +15 -name "*.*" -exec rm -rf {} \;
echo "删除15天前的备份文件完成.........."
#执行PGSQL备份
echo "PGSQL数据库备份开始"
echo "PGSQL数据库备份中......"
export PGPASSWORD="123123"
pg_dumpall -h 127.0.0.1 -p 5432 -U postgres -c -f ${PGSQL_BACK_DATA}
echo "PGSQL数据库备份完成......"
(2)拷贝至服务器执行,启动定时任务
1、拷贝shell脚本内容
2、根目录下创建backup目录
3、修改脚本文件中的数据库端口、账号、密码
4、更改shell脚本权限 chmod 755 XX.sh
5、更改shell脚本格式 sed -i -e 's/\r$//' fwqbackpgsql.sh
6、设置定时任务,执行crontab -e
文本中编辑输入00 00 * * * /backup/fwqbackpgsql.sh
7、重启定时任务sudo service crond restart或者sudo service cron restart
3 问题跟踪与解决
3.1 pgsql系统内置的备份命令出现offline乱码问题
(1)问题场景:
某次测试环境数据库被新来的实习生操作给误删除了,导致测试环境数据库没有了准备恢复。但是问题来了,登录服务器看了下竟然备份文件有8个g,打开特别慢,而且无法恢复单个数据库。因此我这边执行了全库恢复命令,后面发现一些库丢失了。
(2)问题分析:
pg_dumpall -h 127.0.0.1 -p 11000 -U postgres -c -f ${PGSQL_BACK_DATA}
命令导出的备份不能百分百正确,大家在备份过程中一定要注意。
在文件中有90%以上的数据都是offline行,导致文件异常大。
那么问题来了为什么会出现那么多offline呢?
(1)我们线上部署了一个实时连接特别大的服务,把服务器连接数打满了。
(2)服务数据库,每秒会产生大量数据,大致每秒以兆的速度增加数据。
这样会产生的结果,导致备份特别慢,单独他的数据库就有2个g,另外就会导致此方式根本连接不上无法进行数据备份。
但是问题已经发生了,如何处理呢。
(3)补救措施
首先将8个g的备份文件利用分割文件命令,进行拆分。命令如下。
split -b 500M filename
接着,分析拆分后的文件,头尾文件,将头尾文件有数据的留下来继续拆分:
split -b 50M filename
然后,拆分下来8个g的文件,最后成了3个50m的文件。对通过完整脚本没有恢复的数据库进行寻找。
alldump备份的数据库以dump开头,因此通过特有的标识可切分数据库然后恢复对应数据库。
最后,基本把所有数据库恢复了,但是那个实时数据特别多的数据库恢复失败了,因为数据太大经常离线导致无法恢复。
(4)预防措施
经过这次血的教训,以后一定要做好预防措施:
(1)以后开发一定要在开发数据库、测试数据库仅用于测试使用,这样至少有两个数据库不会导致误操作后,服务启动不了。
(2)创建数据库脚本及配置数据一定要保存完好。
(3)配置数据的表名一定要独立命名,方便后续使用。
(4)备份的脚本一定要定期跑一遍,恢复的时候一定要慎重,一个库一个库的恢复。