只有innoDB支持事务。redolog和undolog都只有innoDB才有。
- redolog:保证事务的持久性。用于事务中断后恢复,保证事务的改动都能落盘。
- undolog:保证事务的原子性。用于事务回滚,达到要么全部执行,要么全不执行的效果。
1. redolog
一般由2个log文件来做,默认大小48M。一行redolog包含以下部分:
type(类型)、tablespace(表空间)、page number(页编号)、改动的数据。
mysql事务提交时,要先写redolog再写数据,这样即使系统崩溃了,重启后也能从redolog恢复。
1.1. redolog的机制流程
一个事务假设有5条命令,事务提交的时候,会先将这5条命令写入redolog,然后事务提交才算成功。然后innoDB会逐条读取redolog里的记录进行执行,读一条执行完了删除它,再读一条执行完了删除它。如果这期间崩溃了,还有3条没执行,那redolog里也只剩这3条了,等下次重启后,它做事务恢复,就会继续从redolog里把这3条读出来执行、删掉。
所以说,如果数据库百分百不崩溃,其实是不需要redolog的。
1.2. 为什么要有redolog
- innoDB是以“页”为单位进行磁盘操作的,事务提交时可能只改了页里的几个字节内容,将整个页都刷盘,太浪费了。
- 事务可能对多个页里的不同字节做了修改,他们大概率是不连续的,如果事务提交的时候就把这些都刷盘,会造成随机IO,写入性能很低。
因此有了redolog,记录事务对某些页的某些偏移量做了什么操作。
1.3. redolog和binlog的区别
- redolog只有在系统崩溃重启的场景下有用,用于mysql自己保证持久性,它不是全量增删改日志;binlog主要用于人工恢复数据库和主从复制,它是全量的增删改日志。
- redolog只有innoDB才有,而binlog是mysql的。
- redolog记录上的是物理改动的日志,如“在某个表空间的某个页上做了什么改动”,而binlog是逻辑日志,记录的增删改的sql语句。
- redolog只会记录未刷盘的日志,刷盘后就会删掉这个日志,因此事务执行期间崩溃后,可以从redolog恢复,而binlog记录的是全量日志,没有区别哪些日志是刷盘还是没刷盘,因此事务执行期间崩溃后,不能从它进行恢复。
2. undolog
事务开始前产生,事务在提交时,将该事务对应的undolog放入到删除列表中,再由后台线程进行回收。
innoDB中的mvcc是通过undolog来实现的。
当事务读取一行记录时,若该记录已经被其他事务占用,当前事务通过undo log读取之前的行版本信息。行中的roll_ptr就是指向的undolog。