了解了SQL执行的流程,知道每一条语句都经过连接器、查询存储、分析器、优化器、执行器最后到存储引擎的过程。查询语句是如此,更新语句也不例外。不同的是,更新语句会修改表数据,这里就涉及到两个重要的日志模块redolog和binlog。本篇还是选用InnoDB搜索引擎。
系统的日志模块
之一redolog
下面引入丁奇的经典比喻。
《孔乙己》这篇文章中,酒店掌柜有一个粉板,专门用来记录客人的赊账记录。如果赊账的人不多,他可以把顾客名和账目写在板上。但如果赊账的人多了,粉板总会有记不下的时候,这个时候掌柜一定还有一个专门记录赊账的账本。如果有人要赊账或者还账的话,掌柜一般有两种做法:一是直接把账本翻出来,把这次赊的账加上去或者扣除掉;另一种是先在粉板上记下这次的账,等打烊以后再把账本翻出来核算。在生意红火柜台很忙时,掌柜一定会选择后者,因为前者操作实在是太麻烦了。首先,你得找到这个人的赊账总额那条记录。你想想,密密麻麻几十页,掌柜要找到那个名字,可能还得带上老花镜慢慢找,找到之后再拿出算盘计算,最后再将结果写回到账本上。你想想,如果掌柜没有粉板的帮助,每次记账都得翻账本,效率是不是低得让人难以忍受?
上面的比喻非常形象地说明了Mysql中的WAL(Write-Ahead-Logging)技术。
先写日志(redolog),再写磁盘。也就是先写粉板再写账本。
redolog是InnoDB引擎特有的日志。
当有数据要更新时,InnoDB会先记录redolog,同时更新内存,更新操作就结束了。等到合适的时候(空闲或者粉板写满了),再更新磁盘。
redolog有固定大小,就像固定大小的粉板,写满就得回到开头循环写。
writepos是当前记录粉板的位置,一边写一边往后移。
checkpoint是擦除的位置,擦除前会把更新记录到数据文件。
redolog保证了数据库异常重启时数据不丢失,这个能力被称为crash-safe。
(丁奇原图)
redolog默认在Mysql的data目录下,ib_logfile0、ib_logfile1、。。。
mysqlshowvariableslike"innodb_log_group_home_dir";+---------------------------+-------+
Variable_name
Value
+---------------------------+-------+
innodb_log_group_home_dir
./
+---------------------------+-------+1rowinset(0.00sec)
设置redolog文件大小及个数,默认2个文件(innodb_log_files_in_group),每个文件32M(innodb_log_file_size)
mysqlshowvariableslike"innodb_log_file%";+---------------------------+----------+
Variable_name
Value
+---------------------------+----------+
innodb_log_file_size
innodb_log_files_in_group
2
+---------------------------+----------+2rowsinset(0.00sec)
设置redolog实时直接持久化到磁盘上,保证重启后数据不丢失。
mysqlshowvariableslike"innodb_flush_log_at_trx_