zl程序教程

您现在的位置是:首页 >  数据库

当前栏目

MySQL必知必会:简介undo log、truncate、以及undo log如何帮你回滚事务(一)

mysqllog事务 如何 以及 简介 必会 必知
2023-09-27 14:25:58 时间
一、前言#

在整理undo log笔记前我感觉它应该是在 undo、redo、bin log三者中需要整理的内容最少的。但是实际上并不是想象的那么简单。

关于undo log需要整理的两大块知识点分别是

1、简介undo log、truncate、以及undo log如何帮你回滚事务 本篇分享

2、undolog链条、ReadView、以及undo log如何帮你实现MVCC多版本并发控制 明天分享


二、undo log表空间#

如果你看了白日梦前面的分享的笔记 你肯定知道了什么表空间。其实所谓的表空间其实是真实存在于磁盘上的数据文件。而这里的所说的undolog表空间其实就是磁盘上专门存放undo log的文件。


表空间由很多 segment 段 组成 而这众多的段中有一种就是 undo segment。

默认情况下undo segment 会存放于系统表空间中 或者说undo log默认会记录在共享表空间文件中 文件真实存在 。


但是MySQL也提供了参数 让你可以控制MySQL讲undo log写入到单独的表空间文件中去。尤其是当你使用SSD这种存储时 尤为推荐将undo log从共享表空间中拿出去。


三、关于undo log默认的配置#

默认情况下undo log tablespace个数是0 也就是说如果你不干涉MySQL的配置。那么MySQL就会帮你将undo log记录到共享表空间中。


image


MySQL默认的配置文件 my.cnf 长下面这样


image


如果你现在仅仅是安装了MySQL 而不曾启动过mysql 那你去datadir中查看会发现它只是个空目录。


但是当你启动过MySQL之后 再去这个datadir中查看会发现里面多了很多文件 其中就包括共享表空间文件ibdata1 但是没有undolog表空间文件 。如下


image


四、如何将undo log放到单独的表空间#

如果你想将undo log拿到undo log表空间文件中。那你可以像下面这样修改MySQL的配置文件my.cnf


image


修改完后通过如下命令启动mysql


systemctl start mysqld.service


但是你会发现启动不了 如果你去排查原因就会发现 因为曾经初始化过 datadir 目录中的文件 你添加的新配置innodb_undo_tablespaces和原来的配置是冲突的 需要开辟新的表空间文件 所以导致启动失败。


解决的方式 简单粗暴的将换个datadir文件就好啦 所以如果你从一开始就想将undolog拿到单独的表空间中 那么最好从一开始就将这个配置添加进去 否则还是挺麻烦的。


image


本文是MySQL专题第14篇 全文近100篇#


本文是第14篇 全文近100篇 点击查看目录


五、rollback segment#

提到了undo log 就不得不说roll back segment这个知识点了。它并不难理解 你可以阅读下面的介绍了解一下。


InnoDB存储引擎会先初始化好rollback segment 回滚段 在每个回滚段中会记录N个undo log segment 而我们说的undo log就是在 undo log segment中申请出来的

在早期的InnoDB版本中只有一个rollback segment 因此在同一时刻它支持的在线事务的上限被限制在1024个。


在MySQL5.7中回滚段已经支持到了128个 上限是128 。其中32个分配给临时表空间。剩下的96个回滚段可以分配给修改常规表中数据的事务。


用户可以通过参数innodb_rollback_segments调整回滚段的数量。

另外 我们上面提到的 每个回滚段中都记录了N个undolog segment 这里的N和数据页大小有关


InnoDB页面大小回滚段中的撤消插槽数 InnoDB页面大小/ 16 4096 (4KB)2568192 (8KB)51216384 (16KB)102432768 (32KB)20465536 (64KB)4096


六、什么是undo log truncate#

truncate意为 截断


其实结合 truncate table sql 就能更好的理解这个概念。当你不需要某个表中的数据时 你可以执行truncate sql将表中的数据清空掉。同样的undo log的truncate机制本质上就是为undo log 表空间文件瘦身 将不需要的undo log清理掉。


在MySQL 5.6(包括5.6)之前Undo tablespace里面的undo数据文件是无法收缩的。也就是说在实例的运行过程中如果遇到有大的事务 会把undo log的文件撑的非常大。浪费大量的空间甚至会把磁盘打爆。同时也增加了数据库物理备份的时间。

在MySQL5.7中允许用户在线truncate undo log


七、如果做 undo log truncate#

前提 必须使用独立的undo表空间

然后配合如下的参数辅助


image


创建数据表


create table test (

 id int primary key auto_increment, 

 name varchar(64)

);


然后不断的往这个测试表中插入数据


insert into test(name) values(repeat( a ,64));

insert into test(name) select name from test;


一边插入一边观察undo 表空间文件的变化 你会发现undo003这个表空间文件已经超过了参数 innodb_max_undo_log_size 100M 指定的范围 意味着这个undolog已经被标记为可回收了。


image


当事务提交时 undo log并不会被立即删除 因为可能存在其它的事务需要使用undo log将数据回滚到之前的版本。最终是否可以删除undo log由purge线程决定。

为了让pruge线程运行 可以执行如下的sql


delete from test limit 1;


image


【MySQL】通用查询日志 general query log 详解 通用查询日志(general query log)用来记录用户的所有操作,包括启动和关闭MySQL服务、所有用户的连接开始时间和截止时间、发送给MySQL数据库服务器的所有SQL指令等。当我们的数据发生异常时,查看通用查询日志,还原操作时的具体场景,准确定位问题。
【MySQL】事务日志 undo log 详解 Redo log是事务持久性的保证,Undo log是事务原子性的保证。在事务中更新数据的前置操作其实就是要写入Undo log。事务需要保证原子性,也就是事务中的操作要么全部完成,要么什么也不做。但有时候事务执行到一半会出现一些情况,比如: 情况一:事务执行过程中可能遇到各种错误,比如服务器本身的错误,操作系统错误,甚至是突然断电导致的错误。 情况二:程序员可以在事务执行过程中手动输入ROLLBACK语句结束当前事务的执行以上情况出现,我们需要把数据改回原先的样子,这个过程称之为回滚,这样就可以造成一个假象:这个事务看起来什么都没做,所以符合原子性要求每当我们要对一条记录做改动。
【MySQL】事务日志 redo log 详解 redo 日志降低了刷盘的频率,并且redo日志占用的空间非常小。(redo日志主要存储表空间ID、页号、偏移量以及需要更新的值,所需存储的空间很小,刷盘快)。Redo Log 可以简单的非为两部分组成:重做日志的缓存(redo log buffer),保存在内存中,容易丢失。重做日志文件(rodo log file),保存在硬盘中,保证持久性。Redo Log写入并不是直接写入磁盘的,Innodb引擎会在写Redo Log的时候先写redo log buffer,之后再以一定的频率刷入到真正的redo log file中。这里的一定的频率就是所谓的刷盘策略。
MySQL通过bin log恢复数据|手撕MySQL|对线面试官 作为《手撕MySQL》系列的第二篇文章,今天介绍一下MySQL的二进制日志(bin log)进行数据恢复的功能,并且配合实例演示,让你更懂MySQL。