原创作者:黄炎 王悦 周海鸣

引  言

本文是由爱可生研发团队出品的「图解MySQL」系列文章,不定期更新,但篇篇精品。

爱可生开源社区持续运营维护的小目标:

每周至少推送一篇高质量技术文章

每月研发团队发布开源组件新版

每年1024开源一款企业级组件

2019年至少25场社区活动

欢迎大家持续关注~

前提:

sync_binlog=1

innodb_flush_log_at_trx_commit=1

以下讨论的前提 是设置MySQL的crash safe相关参数为双1:

背景说明:

WAL机制 (Write Ahead Log)定义:

WAL指的是对数据文件进行修改前,必须将修改先记录日志。MySQL为了保证ACID中的一致性和持久性,使用了WAL。

Redo log的作用:

Redo log就是一种WAL的应用。当数据库忽然掉电,再重新启动时,MySQL可以通过Redo log还原数据。也就是说,每次事务提交时,不用同步刷新磁盘数据文件,只需要同步刷新Redo log就足够了。相比写数据文件时的随机IO,写Redo log时的顺序IO能够提高事务提交速度。

组提交的作用:

Redo log的刷盘操作将会是最终影响MySQL TPS的瓶颈所在。为了缓解这一问题,MySQL使用了组提交,将多个刷盘操作合并成一个,如果说10个事务依次排队刷盘的时间成本是10,那么将这10个事务一次性一起刷盘的时间成本则近似于1。

为了保证Redo log和binlog的数据一致性,MySQL使用了二阶段提交,由binlog作为事务的协调者。而 引入二阶段提交 使得binlog又成为了性能瓶颈,先前的Redo log 组提交 也成了摆设。为了再次缓解这一问题,MySQL增加了binlog的组提交,目的同样是将binlog的多个刷盘操作合并成一个,结合Redo log本身已经实现的 组提交,分为三个阶段(Flush 阶段、Sync 阶段、Commit 阶段)完成binlog 组提交,最大化每次刷盘的收益,弱化磁盘瓶颈,提高性能。

在没有开启binlog时

当开启binlog时

图解:

下图我们假借“渡口运输”的例子来看看binlog 组提交三个阶段的流程:

在MySQL中每个阶段都有一个队列,每个队列都有一把锁保护,第一个进入队列的事务会成为leader,leader领导所在队列的所有事务,全权负责整队的操作,完成后通知队内其他事务操作结束。

Flush 阶段 (图中第一个渡口)

首先获取队列中的事务组

将Redo log中prepare阶段的数据刷盘(图中Flush Redo log)

将binlog数据写入文件,当然此时只是写入文件系统的缓冲,并不能保证数据库崩溃时binlog不丢失 (图中Write binlog)

Flush阶段队列的作用是提供了Redo log的组提交

如果在这一步完成后数据库崩溃,由于协调者binlog中不保证有该组事务的记录,所以MySQL可能会在重启后回滚该组事务

Sync 阶段 (图中第二个渡口)

这里为了增加一组事务中的事务数量,提高刷盘收益,MySQL使用两个参数控制获取队列事务组的时机:

binlog_group_commit_sync_delay=N:在等待N μs后,开始事务刷盘(图中Sync binlog)

binlog_group_commit_sync_no_delay_count=N:如果队列中的事务数达到N个,就忽视binlog_group_commit_sync_delay的设置,直接开始刷盘(图中Sync binlog)

Sync阶段队列的作用是支持binlog的组提交

如果在这一步完成后数据库崩溃,由于协调者binlog中已经有了事务记录,MySQL会在重启后通过Flush 阶段中Redo log刷盘的数据继续进行事务的提交

Commit 阶段 (图中第三个渡口)

首先获取队列中的事务组

依次将Redo log中已经prepare的事务在引擎层提交(图中InnoDB Commit)

Commit阶段不用刷盘,如上所述,Flush阶段中的Redo log刷盘已经足够保证数据库崩溃时的数据安全了

Commit阶段队列的作用是承接Sync阶段的事务,完成最后的引擎提交,使得Sync可以尽早的处理下一组事务,最大化组提交的效率

缺陷分析:

本文最后要讨论的bug(可通过阅读原文查看)就是来源于Sync 阶段中的那个binlog参数binlog_group_commit_sync_delay,在MySQL 5.7.19中,如果该参数不为10的倍数,则会导致事务在Sync 阶段等待极大的时间,表现出来的现象就是执行的sql长时间无法返回。该bug已在MySQL 5.7.24和8.0.13被修复。

mysql 组提交原理_图解MySQL | [原理解析] MySQL组提交(group commit)相关推荐

  1. Mysql disk write 高_优化系列|实例解析MySQL性能瓶颈排查定位 导读 排查过程

    导读 从一个现场说起,全程解析如何定位性能瓶颈. 排查过程 收到线上某业务后端的MySQL实例负载比较高的告警信息,于是登入服务器检查确认. 1. 首先我们进行OS层面的检查确认 登入服务器后,我们的 ...

  2. 自动获取mysql建表语句_脚本工具---自动解析mysql建表语句,生成sqlalchemy表对象声明...

    常规建表语句: CREATE TABLE `test_table` ( `id` int(11) NOT NULL, `name` char(64) NOT NULL, `password` char ...

  3. c语言连接数据库例子,c语言操作mysql数据库小例子_互帮互助(C language MySQL database operation example _ mutual help).doc...

    这是精心收集的精品经典资料,值得下载保存阅读! c语言操作mysql数据库小例子_互帮互助(C language MySQL database operation example _ mutual h ...

  4. mysql实现心跳表_第29问:MySQL 的复制心跳说它不想跳了

    问题 最近年底,大家的数据库经常跑批量大事务,会发现复制突然断开,报错"心跳与本地信息不兼容": 会是什么原因? 实验 我们先来复现一下,再进行分析. 宽油,做一对主从数据库: 我 ...

  5. mysql 性能和安全性_从源码解读Mysql 5.7性能和数据安全性的提升

    源码解析 MYSQL_BIN_LOG::ordered_commit,这个函数,核心步骤如下: 第一步骤:flush Stage#1: flushing transactions to binary ...

  6. MySQL百一题库_「灵魂拷问」MySQL面试高频一百问(工程师方向)

    前言 每当我们在生产环境服务器上执行rm命令时,总是提心吊胆的,因为一不小心执行了误删,然后就要准备跑路了,毕竟人不是机器,更何况机器也有bug,呵呵. 那么如果真的删除了不该删除的文件,比如数据库. ...

  7. mysql 创建聚集索引_索引为什么会加快Mysql的查询速度?

    为什么用了索引之后,查询就会变快? 相信很多程序员朋友对数据的索引并不陌生,最常见的索引是 B+ Tree 索引,索引可以加快数据库的检索速度,但是会降低新增.修改.删除操作的速度,一些错误的写法会导 ...

  8. mysql 2003报错_为什么不建议在 MySQL 中使用 UTF-8?

    正文 记得去年我在往MySQL存入emoji表情 时,一直出错,无法导入.后来找到办法 -- 通过把 utf8 改成 utf8mb4 就可以了,并没有深究. 一年后,我看到一篇文章讲到emoji文字占 ...

  9. mysql错误修改数据_使用正则表达式快速修改mysql中错误的varchar类型数据

    昨天早上发现日志中有错误信息:Integer到String类型转换异常. 由于程序问题,导致数据库中的varchar列存入的json字符串不符合要求,这些json字符串在反序列化成Map之后就会报错. ...

  10. mysql镜像压缩包使用_如何连接docker的mysql镜像

    展开全部 推荐使用Dockerfile方式. 服务的管理使用的是supervisord, 因为dockerfile里只会有一个cmd生效,如果我想62616964757a686964616fe5868 ...

最新文章

  1. UI设计师必备技能,看看你都学会了吗?
  2. OpenYurt 深度解读:如何构建 Kubernetes 原生云边高效协同网络?
  3. SAP IDOC开发
  4. 【Vs2015】 常用字体的设置
  5. python怎样将list转化成字典_在python 中如何将 list 转化成 dictionary
  6. 远程断点调试不需要跟时间赛跑
  7. 一致性hash算法虚拟节点_一致性Hash算法原理详解
  8. iOS开发UI篇—Quartz2D简单使用(二)
  9. [ jenkins ] git+jenkins+maven + ansible 部署java程序
  10. 如何查看java源码
  11. Autodesk 3ds Max2020安装说明
  12. 微信小程序底部导航栏小效果
  13. 深度学习与计算机视觉教程(7) | 神经网络训练技巧 (下)(CV通关指南·完结)
  14. 金山词霸java接口_使用金山词霸API做翻译(c语言实现)
  15. 春暖花开,放慢脚步,享受生活!
  16. centos 6.9部署svn服务器和客户端(客户端含windows、linux版本)
  17. 异常测试之Socket网络异常
  18. 计算机网络:非持久HTTP连接 VS 持久性HTTP 连接
  19. 【Redis】Redis常用命令
  20. 程序设计学习(c++)(课堂学习2)

热门文章

  1. Avalanche(雪崩) 生态系统中的关键基础设施
  2. matlab中并行条件,matlab中的并行方法
  3. 小红书爆款文案技巧有哪些?爆款文章可借用的技巧有哪些
  4. PIL图像处理之ImageDraw与ImageFont
  5. 【imarkdown】一个轻量级markdown图片链接转换器
  6. (Water Filling)注水算法原理与实现
  7. android office 插件开发,Office SDK
  8. 在线文档查看方案- 易度云查看
  9. Mind The Facts: Knowledge-Boosted Coherent Abstractive Text Summarization
  10. 基于java的健康管理系统设计与实现(项目报告+开题报告+答辩PPT+源代码+数据库+部署视频)