1.MySQL 如何做到数据不丢失的? 答:redo log 重做日志
1.重做日志是一种基于磁盘的数据结构,用于在崩溃恢复期间纠正由不完整事务写入的数据
2.在正常操作期间,重做日志对由 SQL 语句或低级 API 调用产生的更改表数据的请求进行编码。在意外关闭之前未完成更新数据文件的修改会在初始化期间和接受连接之前自动重播
3.默认情况下,重做日志在磁盘上由两个名为
ib_logfile0
和 的文件物理表示ib_logfile1
。MySQL 以循环方式写入重做日志文件
官方文档:MySQL :: MySQL 5.7 Reference Manual :: 14.6.6 Redo Log
2.redo log 重做日志的机制
操作先记录redo log,redo log先落盘,然后再异步刷新数据到磁盘中
1.如果redo log未记录成功就宕机,此时业务方提交不会成功
2.如redo log记录成功,但数据未落盘就宕机,重启时会根据redo log重放数据
3.解析redolog
查看redo log文件位置:
show variables like 'innodb_log_group_home_dir'
本人使用的mysql 5.7 默认在/data目录下,redo文件以ib_logfile%d结尾
logfile是二进制文件,可以参照大佬的博客解析一下
MySQL InnoDB redo Log 浅析_王伟的技术博客_51CTO博客
可以看到除了file之外还有buffer_pool,tmp和 data
ib_buffer_pool 用于存储表空间ID和页面ID( space, page_id
),缓存池缓存最近的使用的页面(1-100)个,默认25个
ibdata1 是系统表空间数据文件,系统表空间是 InnoDB
数据字典、双写缓冲区、更改缓冲区和撤消日志的存储区域
4.InndoDB崩溃后的恢复
1.先恢复表空间:
表结构是.frm文件,表数据.ibd文件,一般在data/***/xxx.frm 目录下
2.重放redo log
3.回滚不完整的事务
4.合并&更新buffer
重放后可能影响现有的缓存结构,需要合并数据更新缓存
5.净化数据
删除被标记的事务,使之不重新被激活
MySQL :: MySQL 5.7 Reference Manual :: 14.19.2 InnoDB Recovery
5.什么是binlog?
二进制日志文适用于mysql服务器之间复制数据的文件,源操作的 MySQL 将更新和更改作为“事件”写入二进制日志,其副本文件同步源文件数据,用于从库读取,通常情况下没有开启binlog文件
1.源文件全量同步主库事件(无法定制设置),而副本则可以定制你需要同步的操作
2.每个副本都会记录二进制日志坐标:它从源读取和处理的文件中的文件名和位置。这意味着多个副本可以连接到源并执行同一二进制日志的不同部分