暂无图片
暂无图片
暂无图片
暂无图片
暂无图片

redo log与binlog

卧龙宝宝 2020-03-21
195

   mysql事务中有个特性叫持久性,就是说事务在提交后即便mysql挂掉,这个事务也不会丢失。那么mysql是如何保障持久性呢?

redo log物理结构

  mysql会在磁盘上建一个或多个物理文件,如果对数据页做修改操作都会记录到文件中,随着mysql的生产数据积累当redolog文件写完时会重新再覆盖写入。下图就是redolog物理结构。

write pos表示当前写入的位置,一边写入一边向后移动(顺时针)。

chek point表示需要擦除的位置。

  再说redo log如何保障持久性之前还需要引入一个重要的日志binlog。binlog是mysql server层提供的用于日志归档,主要记录了用户对表进行修改的sql语句。binlog与redolog很容易混淆,实际上它们有各自的功能,当然在特定场景下需要两种日志配合使用。

redo日志与binlog有以下几点不同

1.redolog是Innodb引擎层的,binlog是server层的,所有存储引擎都可以使用。

2.redo log是物理日志,记录的是在哪个物理页做了什么修改,binlog是逻辑日志比如给id=2这行的字段a加一。

3.redo log循环写,空间用完会覆盖不能用于归档,binlog是追加写入,文件达到一定大小会切换到下一个,不会覆盖之前的日志。

redolog与binlog写入流程

上图倒数第三步与倒数第一步就是两阶段提交,通过该提交方式可以保证mysql异常崩溃时的数据恢复。

  当mysql执行到步骤3时,此时如果mysql发生崩溃,在重启时会读取redolog发现该日志不是完整的那么放弃对磁盘数据页的更改。

  当msyql执行到步骤4时,写入binlog发生崩溃,再重启时如果发现binlog某个事务不是完整的那么依然放弃对数据页的更改,如果binlog的某个事务是完整的那么mysql会对磁盘数据页做更改,也就是事务提交,尽管redolog并未执行commit。

如果不用两阶段提交呢?

  情况1:先写redolog后写binlog.假设redolog写完后binlog写入一半,mysql异常崩溃,那么mysql在恢复过程中会提交对本次的更改,比如给c+1。但是由于binlog不完整,如果用此数据恢复临时库或者数据同步到备库就会造成和原始库数据不一致。

  情况2:先写binlog后写redolog.假设binlog写完后redolog写入一半,mysql异常崩溃,那么mysql在恢复过程中不会提交本次更改(redolog不完整),比如更改的内容是c+1。但是由于binlog是完整的会把c+1的结果同步备库或者用此日志恢复临时表会造成与原始库数据不一致。可以看到,如果不用“两阶段提交”那么就不能保证数据一致性。

  

文章转载自卧龙宝宝,如果涉嫌侵权,请发送邮件至:contact@modb.pro进行举报,并提供相关证据,一经查实,墨天轮将立刻删除相关内容。

评论