一、redo log 和 binlog 是怎么关联起来的?

它们有一个共同的数据字段,叫 XID。崩溃恢复的时候,会按顺序扫描 redo log:

  • 如果碰到既有 prepare、又有 commit 的 redo log,就直接提交;
  • 如果碰到只有 parepare、而没有 commit 的 redo log,就拿着 XID 去 binlog 找对应的事务

二、崩溃恢复流程

如果在图中时刻 A 的地方,也就是写入 redo log 处于 prepare 阶段之后、写 binlog 之前,发生了崩溃(crash),由于此时 binlog 还没写,redo log 也还没提交,所以崩溃恢复的时候,这个事务会回滚。这时候,binlog 还没写,所以也不会传到备库。到这里,大家都可以理解。
大家出现问题的地方,主要集中在时刻 B,也就是 binlog 写完,redo log 还没 commit 前发生 crash,那崩溃恢复的时候 MySQL 会怎么处理?

image.jpeg
1、如果 redo log 里面的事务是完整的,也就是已经有了 commit 标识,则直接提交;
2、如果 redo log 里面的事务只有完整的 prepare,则判断对应的事务 binlog 是否存在并完整:

  • forwards pass:如果是,则提交事务
    • redo committed but not flushed
    • last valid ⟨start ckpt(T1,…,Tk)⟩ → end
  • backwards pass:否则,回滚事务。
    • undo not committed
    • end → last valid ⟨start ckpt(T1,…,Tk)⟩

三、backward pass

image.png

image.png


三、forwards pass

image.png

image.png