undo log, redo log, binlog

  • undo log: innodb生成的用于事务回滚和实现MVCC的日志,保障原子性
  • redo log: innodb生成的用于故障恢复日志,保障持久性
  • binlog: server生成的用于数据备份和主从复制的日志

undo log在什么情况下记录?

undo log主要用于事务回滚,因此在开始事务后执行时便会记录修改前的数据

即使没有手动进行事务开启,Mysql也会隐式开启事务

为什么需要redo log?

在谈redo log之前,得说说buffer pool。buffer pool是作为一种内存缓存,以加快数据增删改查的速度。然而加快了速度,却很容易由于断电等意外使得数据突然丢失,因此redo log作为一种持久化日志便应运而生

在记录需要修改的时候,先更新buffer pool,然后将修改通过redo log记录下来,最好会在适当的时候将buffer pool刷新到硬盘

值得注意的是undo log的记录也会记录到redo log

既然buffer pool是为了加速,那么又记录到redo log是不是与原来的目的冲突了呢?

redo log是顺序写,相对来说速度是更快的,开销较小

redo log是直接持久化吗?

不是,也是先写入redo log buffer

当然为了尽可能保证持久化,mysql在以下时机会进行持久化

  • mysql正常关闭
  • redo log buffer中记录的写入量大于 redo log buffer 内存空间的一半时,会触发落盘
  • InnoDB 的后台线程每隔 1 秒,将 redo log buffer 持久化到硬盘
  • 每次事务提交时都将缓存在 redo log buffer 里的 redo log 直接持久化到磁盘(这个策略可由 innodb_flush_log_at_trx_commit 参数控制)

对于innodb_flush_log_at_trx_commit参数,有如下设置

  • 1(default): 每次提交事务都同步到硬盘
  • 0: 每一秒写入同步
  • 2: 每次提交事务后写入,每一秒同步到硬盘

对于设置0和2,一秒的同步并不能完全保证

既然有了redo log那么为什么还要有binlog?

从历史来讲binlog先于redo log,在以前innodb还不是mysql默认引擎的时候,mysql server层便已经采用binlog记录了所有数据表结构变更和表数据修改的日志

从使用用途来讲,binlog采用的是追加写,不会覆盖原来的日志,这很适合进行数据恢复或者主从复制,而redo log由于是循环写,因此无法进行整体的恢复或者复制

binlog又是什么时候持久化的呢?

对于innoDB而言,只有在事务提交时才记录binlog。那么此时binlog还在内存中

而什么时候持久化mysql通过参数sync_binlog交由用户控制

  • 0: 由系统自行判断
  • 1: 每次提交事务之前都会同步到硬盘
  • n: 累计到n个事务之后才同步到硬盘

Ref

  1. https://xiaolincoding.com/mysql/log/how_update.html
  2. https://dev.mysql.com/doc/refman/8.0/en/innodb-parameters.html#sysvar_innodb_flush_log_at_trx_commit
  3. https://dev.mysql.com/doc/refman/8.0/en/replication-options-binary-log.html#sysvar_sync_binlog

你可能感兴趣的:(db,mysql)