《MySQL技术内MU》读书笔记(1)

2.4 CheckPoint,讲到了CheckPoint解决的问题,其中第三点是“重做日志不可用时,刷新脏页”。详细的描述是这样的:

重做日志可以被重用的部分是指这些重做日志已经不再需要,即当数据库发生宕机时,数据库恢复操作不需要这部分的重做日志,因此这部分就可以被覆盖重用。若此时重做日志还需要使用,那么必须强制产生CheckPoint,将缓冲池中的页至少刷新到当前重做日志的位置。

读到这一段的时候,尤其是加粗部分的内容,我不禁产生疑惑:缓冲池中的页不是本来就和redolog状态相同吗?为什么还需要将缓冲池中的页刷新?

第二天回顾的时候,我思考了一下。(以下为是个人解读,不一定对,如有错误欢迎批评指正!

首先,由于InnoDB采用WAL搭配redolog保证crash safe,也就是更新数据的时候,先写redolog,再写buffer pool中的数据页。又由于写redolog时需要先写redolog buffer,而这个过程由于不需要doublewrite,应该是比较快的。所以,这就可能导致在数据量大、并发写多的情况下,很多操作都被写到了redolog中,但还没有写到buffer pool中的数据页中,如图:

而这时,由于redolog是循环写,在空间不足时(写不下了),就产生了书上说的“不可用”状态。

因此此时,必须强制先将buffer pool中的数据页写入一部分(刷回盘),和redolog保持一致,从而腾出空间。具体的解决措施,即是属于Fuzzy CheckPoint的Async/Sync Flush CheckPoint,根据checkpoint_age,分别和async_water_mark以及sync_water_mark比较,选择相应的Flush操作。具体判断过程如下:

  • 当checkpoint_age < async_water_mark时,无需刷页
  • 当async_water_mark < checkpoint_age < sync_water_mark时,触发Async Flush
  • 当sync_water_mark < checkpoint_age时,触发Sync Flush(一般很少发生)

其中,water_mark的计算公式为:

async_water_mark = 75% * total_redo_log_file_size

sync_water_mark = 90% * total_redo_log_file_size

而checkpoint_age的计算公式为:

checkpoint_age = redo_lsn - checkpoint_lsn

LSN即Log Sequence Number,我的理解里,其实就和kafka里的offset作用差不多。

经过Flush操作之后,确保checkpoint_age < async_water_mark。

回到刚才的问题,所以,文中的“不可用”,指的应该是redolog写空间不足

写在最后:

之前读书做的笔记基本都在书上或者本地的markdown上,但是对于有价值的问题,我决定还是放在博客上和大家共同讨论,毕竟更多的交流往往意味着更多的收获。

并且,这篇文章应该也是我写博客比较多的时间段的一个开始。时值寒假,空闲时间相对较多;也有之前吸取的一些经验教训,督促我在这个时间沉下心去学一些知识。

希望自己能坚持下去。

(cndn不给标题名带内幕,说我标题夸张,可是这本书名字就叫技术内幕啊 ; )

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值