Log日志
redo机制
如果CRUD
的过程中数据库宕机,那么之前插入、更新或删除的数据就有可能会丢失。
由于随即磁盘读写的性能较差,因此更新缓存页的数据之后,并不会立即就写回磁盘去,这也容易导致数据丢失。
基于以上原因,引入了redo log
日志机制。MySQL会在提交事务前,把对缓存页做过的数据修改以日志形式,顺序写入到磁盘上的redo log
中。
redo log
日志格式大致为:表空间号 + 数据页号 + 页内偏移量 + 被修改的字节值 + 具体值
。
MySQL重启后,会将redo log
中记录的未完成的内容重新执行一遍,然后再将缓存页的内容不定时地刷新到磁盘。
redo log
并不是一条条地写入直接往磁盘里写数据,一个redo log block
大小为512字节,分为三个部分。
header
头部:12字节。block no
:4字节。data length
:2字节。first record group
:2字节。checkpoint no
:4字节。
body
数据体:496字节。trailer
尾部:4字节。

MySQL先在内存里将redo log
数据一条条地写入到redo log block
的body
数据块中,当内存里的一个redo log block
写满,就会把这个block
写入磁盘。

redo log buffer
redo log buffer
是专门用来缓冲redo log
写入的一片连续内存空间。与buffer pool
类似,刚启动时,redo log buffer
也包含很多空的redo log block
。
innodb_log_buffer_size
设置redo log buffer
大小,默认16MB。要写redo log
的时候,会从redo log buffer
的第一个redo log block
开始,写满之后继续写下一个。
如果所有redo log block
都写满,就会强制把他们刷入磁盘。

redo log buffer
的写入时机是。
如果
redo log buffer
的日志已经超过其容量的一半(8MB),会把它们的数据写入磁盘文件。事务提交时,必须把事务所对应的
redo log
所在的redo log block
都写回磁盘文件。后台
I/O
线程每隔1s就会把redo log buffer
里的redo log block
数据写回磁盘文件。MySQL关闭时,
redo log block
都会写入磁盘。
默认情况下,redo log
都会写入一个目录中的文件,可以通过show variables like 'datadir';
来查看。
innodb_log_group_home_dir
用来设置redo log目录。innodb_log_file_size
可以限定每个redo log文件的大小,默认48MB。innodb_log_files_in_group
指定文件数量,默认2个,即ib_logfile0
和ib_logfile1
。
undo log
如果某个事务执行到了一半就回滚了,需要引入undo log
。
对于undo log
来说,insert
对应delete
,update
对应update
,由Buffer Pool
记录undo log
。
以INSERT
语句为例,undo log
包含下面的部分。
日志起始位置。
主键的各列长度和值。
表ID。
日志编号。
日志类型。
日志结束位置。
感谢支持
更多内容,请移步《超级个体》。