整体架构

事务的基本概念

事务就是一组原子性的sql查询,或者是一个独立的工作单元

事务内的语句,要么全部执行成功,要么全部执行失败

ACID标识原子性(atomicity)、一致性(consistency)、隔离性(isolation)和持久性(durability)

一个运行良好的事务处理系统,必须要具备这些标准特征

原子性

要么所有操作全部成功,要么全部失败回滚,不可能执行其中的一部分操作

一致性

失败后事务最终没有提交,所做的修改不会保存到数据库中

隔离性

事务所做的修改在最终提交前,对其他事务是不可见的

持久性

一旦事务提交,所做的修改就会永久保存到数据库中

事务需要用到更多的处理能力

可选择适合业务的存储引擎

事务的过程就是一个日志的写入过程

以下从缓冲池和日志的角度,描述事务的提交

InooDB体系架构

InnoDB存储引擎有多个内存块,组成一个大的内存池,负责如下工作

维护所有进程/线程需要访问的多个内部数据结构

缓存磁盘上的数据,方便快读地读取,同时在对磁盘文件的数据修改之前在这里缓存

重做日志(redo log)缓冲

其中,后台线程的主要作用是负责刷新内存池中的数据,保证缓冲池中的内存缓存是最近的数据。此外将已修改的数据文件刷新到磁盘,同事保证数据库发生异常的情况下InnoDB能回复到正常运行状态

后台线程

Master Thread

非常核心的后台线程,负责将缓冲池中的数据异步刷新到磁盘,保证数据的一致性

IO Thread

InnoDB存储引擎大量使用了AIO(Async IO异步IO)来处理IO请求,以提高性能。而IO Thread主要负责这些IO请求的回调处理

Purge Thread

回收已提交事务后,不需要的undolog

内存

缓冲池

InnoDB存储引擎基于磁盘存储,记录则按页的方式进行管理

缓冲池用于连接CPU与磁盘速度质检的鸿沟,来提高数据库的整体性能,就是一块内存区域

在读取页的操作,会将磁盘放到缓冲池中(FIX)。下次读取相同页会先从缓冲池里拿

修改时会先修改缓冲池中的页,然后按一定频率刷新到磁盘(通过checnkpoint机制)

缓冲池中缓存的数据页类型有:索引页、数据页、undo页、插入缓冲、自适应哈希索引、InnoDB存储的锁信息、数据字典信息等

LRU List、FreeList和Flush List

LRU

缓冲池通过LRU(Lastest Recent Used,最近最少使用)算法进行管理

最频繁使用的夜放在LRU列表的前端,最少使用的放在尾端

不能存储新读的页时,首先释放LRU尾端的页(页的大小默认为16kb)

InnoDB的LRU算法不是朴素的LRU算法,加入了midpoint位置

默认midpoint位置为5/8处,midpoint之前是old列表、之后是new列表(活跃的热点数据在new列表)

为了防止热点数据从LRU列表中擦除,引入了innodb_old_blocks_time表示读取到mid位置后等待多久才会被加入到LRU列表的热端

Free list

当数据库刚启动,LRU列表是空的,此时页都存放在Free列表中

会先从Free列表中查找是否有可用的空闲页,如有,则放到LRU列表中,否则根据LRU算法淘汰列表末尾的页(不活跃的部分),分配给新页

InnoDB的策略是尽量使用内存,因此对于一个长期运行的库来说,未被使用的页很少

Flush list

Flush列表中的页都为脏页列表,但脏页也存在于LRU列表中

LRU列表用来管理缓冲池中页的可用性,Flush列表用来管理将页刷新回磁盘,二者互不影响

redo log

redo log buffer

在缓冲池中,有日志缓冲(默认8m)。在写入的时候,会先写入日志缓冲中

以下三种情况,会将日志缓冲刷新到磁盘的重做日志中

Master Thread会每秒都会把日志缓冲的数据刷新到日志文件

每个事务提交(事务commit)

日志重做的缓冲池剩余空间小于1/2时

redo log file

是innoDB本身的日志文件,在存储引擎层

在事务提交时,必须把所有的日志写入到redo log file进行持久化(Write Ahead Log)

重做日志分为多组(至少一组),每组至少有两个日志文件

以循环的方式写文件,文件1满切换文件2,反之切换回文件1

日志大小太大会导致恢复时间很长,太小,可能会导致多次切换重做日志文件

会导致async checkpoint(下面有解释),造成性能抖动

checkpoint技术

checkpoint本身是缓冲池

解决了以下问题

缩短数据库的回复时间

缓冲池不够用时,将页刷新到磁盘

重做日志不可用时,刷新脏页

具体来说

通过LSN(Log Sequence Number)来标记版本,缓冲池的页有LSN,重做日志中也有LSN,Checkpoint也有LSN

缓冲池的页会根据LRU算法算出最少使用的页作为脏页,刷回到磁盘

日志可以根据标记的LSN版本,来计算出需要需要重做的日志的部分是哪些

checkpoint的触发有两种

Sharp Checkpoint,在数据库关闭的时候将所有脏页都刷新回磁盘

Fuzzy Checkpoint

Master Thread Checkpoint 以每秒或者每十秒的速度从缓冲池的脏页列表以一定比例的页刷回磁盘

FLUSH_LRU_LIST Checkpoint 保证LRU列表中有差不多100个空闲页可用,会从LRU列表尾端的页移除

Async/Sync Flush Checkpoint

当重做日志不可用,则需要强制刷新一些页回磁盘,脏页从脏页列表(Flush List)中选取

写入到重做日志的LSN记为redo_lsn,已经刷新磁盘最新页的LSN记为checkpoint_lsn

通过redo_lsn和checkpoint_lsn来判断是否需要触发Async/Sync Flush Checkpoint,算法如下

checkpoint_age = redo_lsn - checkpoint_lsn 记录未刷到磁盘的日志

定义变量asycn_water_mark = 75% * total_redo_log_file_size

定义变量sycn_water_mark = 90% * total_redo_log_file_size

当async_water_mark < checkpoint_age < sycn_water_mark,触发Async Flush,从Flush列表中刷新足够的脏页回磁盘,以满足checkpoint_age < async_water_mark

Dirty Page too much Checkpoint,脏页数量太多,导致强制进行Checkpoint,目的还是为了保证缓冲池有足够可用的页

缩短数据库的恢复时间,在数据更新的时候,会同时更新redo log以及缓冲池缓存,数据库异常(如断电等)的时候,可以直接从checkpoint的点开始从redolog恢复数据

redo log与bin log

redo log是发生在存储引擎这一层,是innodb的日志文件系统,而bin log是在mysql的server层,所有的日志都有

两个日志必须是状态一致的,所以他们的日志写入,则是一个事务的提交过程

bin log记录的是完整的逻辑记录,redo log记录的是物理日志

事务提交的过程,称为两阶段提交

在进行一个事务的时候(未提交),会把redo log写到缓存buffer中,再通过master thread刷到磁盘中,此时标记为未提交(prepare)

接着在binlog中,写入二进制日志

当binlog写完,再把redo log从prepare状态改为commit,此时事务提交完成

为什么要进行这样的一个提交流程呢?

如果刚好在写入redo log的时候断点,那重启后事务回滚,日志一样同步

如果redo log已经写完,在bin log写入的时候断电,重启后发现二者日志的状态不一致,则事务未提交,根据日志回滚

都写完日志,但未commit,依然回滚

都写完,已commit,状态同步,完成事务提交

二阶段的提交保证了两者日志的一致性

总结

本文大致描述了事务、缓冲池、checkpoint、日志之间的关联,但还有许多细节需要深究。例如redo log以及undo log的关系、checkpoint的运行机制等等。

参考文档

MySQL技术内幕(InnoDB存储引擎)

高性能MySQL

mysql 活跃事务_MySQL日志与事务相关推荐

  1. mysql xid原理_MySQL数据库分布式事务XA实现原理分析

    [IT168 技术]MySQL XA原理 MySQL XA分为两类,内部XA与外部XA;内部XA用于同一实例下跨多个引擎的事务,由大家熟悉的Binlog作为协调者;外部XA用于跨多MySQL实例的分布 ...

  2. mysql xa 演示_mysql的XA事务恢复过程详解

    mysql数据库开机报错: InnoDB: The log sequence number in ibdata files does not match InnoDB: the log sequenc ...

  3. mysql xa 实现_MySQL数据库分布式事务XA的实现原理分析

    1 原理 关于MySQL数据库的分布式事务XA,分布式事务实现的原理,可见[3];关于MySQL XA的说明,可见[1][2]. MySQL XA分为两类,内部XA与外部XA;内部XA用于同一实例下跨 ...

  4. mysql xa 事务_MySQL的XA事务问题分析

    mysql5.7以后的版本支持了xa prepare事务的持久化,这使得基于mysql xa的分布式事务方案变的可行.但mysql目前的XA实现在极端故障场景下是会出现事务丢失或innodb数据与bi ...

  5. mysql开启事务_MySQL入门之事务(上)

    事务 事务介绍 事务的概念 事务指逻辑上的一组操作,组成这组操作的各个单元,要不全部成功,要不全部不成功 数据库开启事务命令 start transaction 开启事务 (等同于set autoco ...

  6. mysql中的事务_mysql中的事务,你理解嘛?

    事务又叫做TCL,全称是transaction control language,意思是事务控制语言.这篇文章还是属于我的mysql基础文章,在前面我们介绍了下面这些基础知识: 1.数据库的增查改删操 ...

  7. redis mysql 事务_Mysql与Redis事务

    Mysql事务ACID基于日志 AC:回滚日志实现回滚(原子性) D:重做日志实现持久化 I:加锁实现隔离级别  (MVVC无锁机制也可实现可重复读) 读未提交 存在问题:脏读(外部select事务内 ...

  8. mysql数据库事务_MySQL数据库的事务管理

    小伙伴们不好意思,这两天有事没有及时的更新哈~希望小伙伴们见谅,那么开始我们今天的分享. MySQL 数据库的事务 我们之前分享数据库的数据操作,无外乎对数据库的数据进行增.删.改.查.就比如我们去买 ...

  9. mysql不同连接的事务_mysql中不同事务隔离级别下数据的显示效果--转载

    事务是一组原子性的SQL查询语句,也可以被看做一个工作单元.如果数据库引擎能够成功地对数据库应用所有的查询语句,它就会执行所有查询,如果任何一条查询语句因为崩溃或其他原因而无法执行,那么所有的语句就都 ...

最新文章

  1. mysql計劃任務_MySQL計劃任務 | 學步園
  2. 不管马斯克怎么说,中国智能汽车激光雷达军备竞赛已经开始
  3. linux技术理解,技术|理解 Linux 链接(二)
  4. Extra Data after Last Expected Column:hawq建外表load数据报错
  5. 图像处理【代码合集】
  6. php删除记录图片吗,php 删除记录同时删除图片文件的实现代码_PHP教程
  7. 第一:MySQL安装和配置(超详细)
  8. Codeforces 700 C. Break Up(Tarjan求桥)
  9. 一分钟了解阿里云产品:绿网
  10. 【GEE笔记】最大类间方差法(otsu、大津法)算法实现——计算阈值、图像二值化分割
  11. linux打开pkg文件怎么打开,linux中怎么打开tar.rar.gz文件
  12. 什么是服务器安全性?
  13. java自动装箱|拆箱解密
  14. 【人情世故】汇报措辞
  15. C语言——分支语句和循环语句
  16. 惠普暗影精灵4pro安装ubuntu16.04
  17. JS ListBox动态加载数据
  18. Nokia的操作技巧
  19. Flutter 调用百度地图APP实现位置搜索、路线规划
  20. volatile,CAS,ABA三个关键字

热门文章

  1. Java自动装箱后的值比较
  2. 《爱上统计学》读书笔记
  3. python获取原图GPS位置信息,轻松得到你的活动轨迹
  4. harbor的镜像复制功能使用教程
  5. Linux nginx搭建文件服务器
  6. Spark累加器实现原理及基础编程
  7. Win10自带的邮件客户端配置腾讯企业邮箱账号
  8. 【收藏】wsl2 出现 Vmmem内存占用过大问题解决
  9. 详解spark任务提交至yarn的集群和客户端模式
  10. Redis命令:EXPIREAT key timestamp(设置key在某一时间过期)