深入学习MySQL 02 日志系统:bin log,redo log,undo log
点击上方“java从心”,设为星标
每天进步一丢丢,连接梦与想
上一篇文章中,我们了解了一条查询语句的执行过程,按理说这篇应该讲一条更新语句的执行过程,但这个过程比较复杂,涉及到了好几个日志与事物,所以先梳理一下3个重要的日志,bin log(归档日志)、redo log(重做日志)、undo log(回滚日志)
概括
MySQL中有六种日志文件,分别是:重做日志(redo log)、回滚日志(undo log)、二进制日志(bin log)、错误日志(error log)、慢查询日志(slow query log)、一般查询日志(general log),中继日志(relay log)。
其中bin log和undo log与事务操作息息相关,bin log也与事务操作有一定的关系,这三种日志,对理解MySQL中的事务操作有着重要的意义。
接下来,分别对3种日志做总结概括
bin log
是个啥
由Mysql的Server层实现,是逻辑日志,记录的是sql语句的原始逻辑,比如"给 ID=2 这一行的C字段加1"
怎么工作的
binlog会写入指定大小的物理文件中,是追加写入的,当前文件写满则会创建新的文件写入。
产生:事务提交的时候,一次性将事务中的sql语句,按照一定的格式记录到binlog中。
清理:可设置参数expire_logs_days,在生成时间超过配置的天数之后,会被自动删除。
有啥用
1.用于复制,在主从复制中,从库利用主库上的binlog进行重播(执行日志中记录的修改逻辑),实现主从同步。
2.用于数据库的基于时间点的还原。
3种记录模式
-
statement:基于SQL语句的模式,某些语句中含有一些函数,例如 UUID,NOW 等在复制过程可能导致数据不一致甚至出错。
-
row:基于行的模式,记录的是行的变化,很安全。但是 binlog 的磁盘占用会比其他两种模式大很多,在一些大表中清除大量数据时在 binlog 中会生成很多条语句,可能导致从库延迟变大。
-
mixed:混合模式,根据语句来选用是 statement 还是 row 模式。表结构变更使用 statement 模式来记录,如果 SQL 语句是 update 或者 delete 语句,那么使用row模式。
redo log
是个啥
由引擎层的InnoDB引擎实现,是物理日志,记录的是物理数据页修改的信息,比如"某个数据页上内容发生了哪些改动"
怎么工作的
原理:当一条数据需要更新时,InnoDB会先将更新操作记录到rodolog中,并更新到内存中,这个更新就算是完成了。InnoDB引擎会在mysql空闲时将这些更新操作更新到磁盘中(数据文件)。
(这个就是MySql经常说到的WAL技术,Write-Ahead Logging ,关键点是先写日志,再写磁盘)
存储:redolog是顺序写入指定大小的物理文件中的。是循环写入的,当文件快写满时,会边擦除边刷磁盘,即擦除日志记录(redolog file)并将数据刷到磁盘中。
有啥用
1.提供crash-safe 能力(崩溃恢复),确保事务的持久性。
数据库突然崩溃,有些数据并未刷到数据文件中,当重启MySQL数据库,会从redolog中未刷到磁盘的数据刷到磁盘中。
2.利用WAL技术推迟物理数据页的刷新,从而提升数据库吞吐,有效降低了访问时延。
undo log
是个啥
由引擎层的InnoDB引擎实现,是逻辑日志,记录数据修改被修改前的值,比如"把Name='B' 修改为Name = 'B2' ,那么undo日志就会用来存放Name='B'的记录"
怎么工作的
当一条数据需要更新前,会先把修改前的记录存储在undolog中,如果这个修改出现异常,,则会使用undo日志来实现回滚操作,保证事务的一致性。
当事务提交之后,undo log并
有啥用
3种日志在事物执行过程中的工作
user表
id name
1 ken
2 river
执行一个事务
BEGIN
update name = 'wk' from user where id = 1
update name = 'river' from user where id = 2
commit
总结
如果觉得不错,请给个「好看」
分享给你的朋友!

THANDKS
- End -
一个立志成大腿而每天努力奋斗的年轻人
伴学习伴成长,成长之路你并不孤单!
java从心
扫描二维码,关注公众号
原文始发于微信公众号(java从心):深入学习MySQL 02 日志系统:bin log,redo log,undo log