MySQL中的 redo 日志文件

MySQL中的 redo 日志文件

MySQL中有三种日志文件,redo log、bin log、undo log。redo log 是 存储引擎层(innodb)生成的日志,主要为了保证数据的可靠性;bin log 是 MySQL 数据库层面上生成的日志,主要用于 point in time 恢复和主从复制。undo log 主要用于事务的回滚(undo log 记录的是每个修改操作的逆操作) 和 一致性非锁定读(undo log 回滚行记录到某种特定的版本---MVCC 多版本并发控制)。

redo log 和 undo log 都是存储引擎层面上生成的日志,并且都记录了数据的修改:只不过 redo log记录的是"物理级别"上的页修改操作,比如页号xxx、偏移量yyy写入了'zzz'数据;而undo log 记录的是逻辑操作日志,比如对某一行数据进行了INSERT语句操作,那么 undo log就记录一条与之相反的DELETE操作。

redo log 作用

MySQL作为一个存储系统,为了保证数据的可靠性,最终得落盘。但是,又为了数据写入的速度,需要引入基于内存的"缓冲池"。其实不止MySQL,这种引入缓冲来解决速度问题的思想无处不在。既然数据是先缓存在缓冲池中,然后再以某种方式刷新到磁盘,那么就存在因宕机导致的缓冲池中的数据丢失,为了解决这种情况下的数据丢失问题,引入了redo log。在其他存储系统,比如Elasticsearch中,也有类似的机制,叫translog。

但是一般讨论数据写入时,在MySQL中,一般叫事务操作,根据事务的ACID特性,如何保证一个事务提交后Durability的保证?而这就是 redo log 的作用。当向MySQL写用户数据时,先写redo log,然后redo log根据"某种方式"持久化到磁盘,变成redo log file,用户数据则在"buffer"中(比如数据页、索引页)。如果发生宕机,则读取磁盘上的 redo log file 进行数据的恢复。从这个角度来说,MySQL 事务的持久性是通过 redo log 来实现的。

redo log 写入磁盘

在事务运行过程中,会不断地产生 redo log,这些 redo log 会先定入 redo log buffer中,然后再将 redo log buffer 中的数据以某些方式顺序地写入到磁盘(各个操作的redo log 汇总到 redo log buffer,再由 redo log buffer 统一写磁盘,就能做到顺序写了)。这些方式有:

  • MySQL master 线程周期性任务 每秒一次,将 redo log buffer 刷新到磁盘(即使这个事务尚未提交)

  • MySQL master 线程周期性任务 每10秒一次,将 redo log buffer 刷新到磁盘

  • 当redo log buffer size 剩余空间小于1/2时(innodb_log_buffer_size参数),将 redo log buffer 刷新到磁盘

  • 当 redo log file 大小已经达到某个域值快要"不可用"时(日志文件组轮流写文件),触发 async/sync flush checkpoint,及时将一些脏页刷新到磁盘,并同时将redo log buffer刷新到磁盘,然后更新redo log file 相应的 log sequence number值。

    MySQL中的 redo 日志文件_第1张图片

redo log buffer 的刷新到磁盘的时机由参数 innodb_flush_log_at_trx_commit 参数控制,可取的值有:0、1、2:

  • 0 由master 线程周期性任务刷新
  • 1 在事务 commit 时 redo log buffer 同步写入 disk,伴随 fsync 调用
  • 2 将 redo log 日志数据异步写入 disk,即只写到文件系统缓存中,在事务成功提交后并不能保证 redo log 数据一定存储到磁盘上了

redo log 写入磁盘时,是以扇区大小512B写入的,保证每次写都能写入成功,不需要有 double write 机制。

MySQL中的 redo 日志文件_第2张图片

原文:https://www.cnblogs.com/hapjin/p/11521506.html

你可能感兴趣的:(MySQL中的 redo 日志文件)