浅析mysql 定时备份任务
简介
在生产环境上,为了避免数据的丢失,通常情况下都会定时的对数据库进行备份。而Linux的crontab指令则可以帮助我们实现对数据库定时进行备份。首先我们来简单了解crontab指令,如果你会了请跳到下一个内容mysql备份。
本文章的mysql数据库是安装在docker容器当中,以此为例进行讲解。没有安装到docker容器当中也可以参照参照。
contab定时任务
使用crontab -e来编写我们的定时任务。
0 5 * * 1 [command]
0 8 * * * [command]
- crontab -l 可以查看自己的定时任务
- crontab -r 删除当前用户的所有定时任务
mysql备份
快速上手
这里我的mysql数据库是docker容器。假如你需要在每天晚上8点整执行定时任务,那么可以这么写。
首先执行命令crontab -e。
0 8 * * * docker exec mysql_container mysqldump -uroot -proot_password database_name > /var/backups/mysql/$(date +%Y%m%d_%H%M%S).sql
如果你没什么要求,单纯的只是想要备份,那么上面那个命令就可以帮你进行定时备份。
小坑: mysql备份的时候我使用了docker exec -it mysqldump
... 这样的命令去做bash
脚本,因为-i参数是有互动的意思,导致在crontab
中执行定时任务的时候,没有输出数据到sql
文件当中。所以使用crontab
定时的对docker容器进行备份命令的时候不要添加-i
参数。
crontab优化
我不建议直接在crontab -e
里面写要执行的命令,任务多了就把这个文件写的乱七八招了。
建议把数据库备份的命令写成一个bash
脚本。在crontab
这里调用就好了
如:建立一个/var/backups/mysql/mysqldump.sh
文件,内容如下
docker exec mysql_container mysqldump -uroot -pmypassword database_name > /var/backups/mysql/$(date +%Y%m%d_%H%M%S).sql
chmod 711 /var/backups/mysql/mysqldump.sh
0 20 * * * /var/backups/mysql/mysqldump.sh
mysql备份优化
因为sql文件比较大,所以一般情况下都会对sql文件进行压缩,不然的话磁盘占用就太大了。
假设你做了上面这一步 crontab优化,我们可以把mysqldump.sh脚本改成下面这样:
export mysqldump_date=$(date +%Y%m%d_%H%M%S) && \docker exec mysql_container mysqldump -uroot -pmypassword database_name> /var/backups/mysql/$mysqldump_date.sql && \gzip /var/backups/mysql/$mysqldump_date.sqlfind /var/backups/mysql/ -name "*.sql" -mtime +15 -exec rm -f {} \;
数据恢复
若一不小心你执行drop database
,稳住,淡定。我们首先要创建数据库被删除的数据库。
>mysql create database database_name;
docker exec -i mysql_container mysql -uroot -proot_password database_name < /var/backups/mysql/20200619_120012.sql
binlog日志
binlog 是mysql的一个归档日志,记录的数据修改的逻辑,如:给 ID = 3 的这一行的 money 字段 + 1。
首先登录mysql后查询当前有多少个binlog文件:
> mysql show binary logs;+---------------+-----------+-----------+| Log_name | File_size | Encrypted |+---------------+-----------+-----------+| binlog.000001 | 729 | No || binlog.000002 | 1749 | No || binlog.000003 | 1087 | No |+---------------+-----------+-----------+
mysql> show master status\G;
mysql> flush logs
mysql> show binlog events in 'binlog.000003';
恢复数据
拿回上面例子的这段话。
晚上8点进行定时备份,但是却在晚上9点drop database,那么晚上8点到晚上9点这一个小时之内的数据却没有备份到。。
首先进入到mysql容器后,切换到/var/lib/mysql目录下,查看binlog文件的创建日期
cd /var/lib/mysqlls -l...-rw-r----- 1 mysql mysql 729 Jun 19 15:54 binlog.000001-rw-r----- 1 mysql mysql 1749 Jun 19 18:45 binlog.000002-rw-r----- 1 mysql mysql 1087 Jun 19 20:58 binlog.000003...
恢复命令格式:
mysqlbinlog [options] file | mysql -uroot -proot_password database_name
--start-datetime 开始时间,格式 2020-06-19 18:00:00
--stop-datetime 结束时间,格式同上
--start-positon 开始位置,(需要查看binlog文件)
--stop-position 结束位置,同上
...
恢复备份数据和binlog数据前建议先登录mysql后执行flush logs
生成新的binlog
日志,这样可以专注需要恢复数据的binlog
文件。
首先我们需要查看binlog日志,在哪个位置进行了drop database
操作:
mysql> show binlog events in 'binlog.000003';+---------------+-----+----------------+-----------+-------------+---------------------------------------------------------------------------------------------------------------------------------------------+| Log_name | Pos | Event_type | Server_id | End_log_pos | Info |+---------------+-----+----------------+-----------+-------------+---------------------------------------------------------------------------------------------------------------------------------------------+| binlog.000003 | 4 | Format_desc | 1 | 125 | Server ver: 8.0.20, Binlog ver: 4 || binlog.000003 | 125 | Previous_gtids | 1 | 156 | || binlog.000003 | 156 | Anonymous_Gtid | 1 | 235 | SET @@SESSION.GTID_NEXT= 'ANONYMOUS' || binlog.000003 | 235 | Query | 1 | 318 | BEGIN || binlog.000003 | 318 | Rows_query | 1 | 479 | # INSERT INTO `product_category` SET `name` = '床上用品' , `create_time` = 1592707634 , `update_time` = 1592707634 , `lock_version` = 0 || binlog.000003 | 479 | Table_map | 1 | 559 | table_id: 139 (hotel_server.product_category) || binlog.000003 | 559 | Write_rows | 1 | 629 | table_id: 139 flags: STMT_END_F || binlog.000003 | 629 | Xid | 1 | 660 | COMMIT /* xid=2021 */ || binlog.000004 | 660 | Anonymous_Gtid | 1 | 739 | SET @@SESSION.GTID_NEXT= 'ANONYMOUS' || binlog.000004 | 739 | Query | 1 | 822 | drop database hotel_server /* xid=26 */ |+---------------+-----+----------------+-----------+-------------+---------------------------------------------------------------------------------------------------------------------------------------------
mysqlbinlog --start-datetime=2020-06-19 20:00:00 --stop-position=660 /var/lib/mysql/binlog.000003 | mysql -uroot -proot_password datbase_name
总结
因为mysql定时备份是在生产环境上必须的任务。是很常用的。所以我就迫不及待的写博客。当然也很感谢我同事的帮助。这篇文章已经写了三天了,因为我也是在不断地试错,不断的更新文章。避免把错误的知识点写出来。如果帮到你了,关注我一波呗!谢谢。
更多相关文章
- Android(安卓)之 AsyncTask 异步任务
- Android(安卓)任务和回退堆栈---启动任务
- Android(安卓)后台任务(五)Service
- Windows环境下Android(安卓)Studio系列4—界面介绍
- Android监听Home键和最近任务
- Android中对后台任务线程性能的说明及优化
- Android(安卓)线程池管理工具类
- Android(安卓)创建线程执行任务
- 获取Android正在运行的任务和服务