MySQL是如何保证数据不丢失的

news2025/2/24 1:05:16

一.什么是两阶段提交

1.SQL语句(update user set name=‘李四’ where id=3)的执行流程是怎样的呢?
在这里插入图片描述

1.执行器先找引擎取 ID=3这一行。ID 是主键,引擎直接用树搜索找到这一行。
2.如果 ID=3 这一行所在的数据页本来就在内存中,就直接返回给执行器;否则,需要先从磁盘读入内存,然后再返回。
3.执行器拿到引擎给的行数据,把name这个值改成李四 得到新的一行数据,再调用引擎接口写入这行新数据。
4.引擎将这行新数据更新到内存中,同时将这个更新操作记录到 redo log 里面,此时 redo log 处于 prepare 状态。然后告知执行器执行完成了,随时可以提交事务。
5.执行器生成这个操作的 binlog,并把 binlog 写入磁盘。
6.执行器调用引擎的提交事务接口,引擎把刚刚写入的 redo log 改成提交(commit)状态,更新完成。

2.redo log 和 binlog有什么不同?

1.redo log 是物理日志,记录的是“在某个数据页上做了什么修改”;
2.binlog 是逻辑日志,记录的是这个语句的原始逻辑,比如“给 ID=3 这一行的 name 字段改成李四 ”。

3.为什么必须有“两阶段提交”呢?

这是为了让两份日志之间的逻辑一致。所以只要 redo log 和 binlog 持久化到磁盘,即使 MySQL 异常,重启后数据依然可以恢复。

二:binlog是怎么写入的

1.binlog是怎么进行写入的呢?

1.事务执行过程中先把日志写到binlog cache 中,
2.吧日志写入到文件系统的 page cache中
3. 事务提交时,将 binlog cache 写入 binlog 文件

2.什么是binlog cache?

在执行事务过程中系统为每个线程分配了一片binlog cache内存。参数binlog_cache_size控制单个线程内binlog cache大小。如果超过这个大小就要暂存到磁盘,类似于先写入临时文件,在写入磁盘。

在这里插入图片描述
如上图所示,可以看到,每个线程有自己的 binlog cache,但是共用同一份 binlog 文件。

3.图中的 write,指的就是指把日志写入到文件系统的 page cache,并没有把数据持久化到磁盘,所以速度比较快。

page cache:是OS关于磁盘IO的缓存,位于内核中,不适用于大文件传输,因为大文件传输page cache的命中率比较低,这个时候page cache不仅没有起到作用还增加了一次数据从磁盘buffer到内核page cache的开销

4.图中的 fsync,才是将数据持久化到磁盘的操作。一般情况下,我们认为 fsync 才占磁盘的 IOPS。

也可以理解为,write是写入内存,而fsync才是写磁盘。

5.bin log有哪些写盘策略?
通过控制参数sync_binlog来进行控制

  1. sync_binlog=0 的时候,表示每次提交事务都只 write,不 fsync;
  2. sync_binlog=1 的时候,表示每次提交事务都会执行 fsync;(一般设置为1);
  3. sync_binlog=N(N>1) 的时候,表示每次提交事务都 write,但累积 N 个事务后才 fsync;

如果参数是0,MySQL发生异常重启会丢失内存里的bin log
如果参数是N,MySQL发生异常重启会丢失内存里的最近N个事务的bin log

三:redlog的是怎么写入的

写盘执行流程
其实redlog和binlog写盘机制都差不多,都是先写内存在写磁盘。

  1. 先写入 redo log buffer
  2. 吧 redo log buffer 写入 page cache中
  3. 持久化 到磁盘当中

1.什么是redo log buffer?

redo log buffer是一块内存,事务执行过程中会多次写入buffer,等到事务commit的时候才会写入redo log中

2.redo log buffer和binlog cache都是临时内存有什么不同

1.binlog cache是每一个线程都共有的,而redo log buffer是多个线程公用的。
2.binlog存储是以statement或者row格式存储的,
3.redo log是以page页格式存储的

3.red log有哪些写盘策略?
通过控制参数innodb_flush_log_at_trx_commit来进行控制

  1. 设置为 0 的时候,表示每次事务提交时都只是把 redo log 留在 redo log buffer 中;
  2. 设置为 1 的时候,表示每次事务提交时都将 redo log 直接持久化到磁盘;
  3. 设置为 2 的时候,表示每次事务提交时都只是把 redo log 写到 page cache;

4.redo log buffer什么时候 write?

1.InnoDB 有一个后台线程,每隔1秒,就会把 redo log buffer中的日志,调用 write 写到 page cache,然后 fsync 持久化到磁盘。
需要注意的是,事务执行中的 redo log 也是存在于 redo log buffer 的,也会被一起持久化到磁盘。(也就是说,一个还没有提交事务的 redo log,也可能已经被持久化到磁盘了)

2.一种是,redo log buffer 占用的空间即将达到 innodb_log_buffer_size 一半的时候,后台线程会主动写入 page cache。

5.写入 page cache后什么时候fsync?

1.当我们innodb_flush_log_at_trx_commit设置为1时,假设一个事务 A 执行到一半,已经写了一些 redo log 到 buffer 中,这时候有另外一个线程的事务 B 提交,那么按照这个参数的逻辑,事务 B 要把 redo log buffer 里的日志全部持久化到磁盘。这时候,就会带上事务 A 在 redo log buffer 里的日志一起持久化到磁盘。
2.事务提交时

四:组提交(group commit)

为什么要组提交?
简单来说其实组提交顾名思义就是是多个事务成为一’组’,一起刷盘,减少磁盘IO。
详细可以参考这篇文档 组提交的好处

在这里插入图片描述
上图就是MySQL没有优化前的提交方式。

  1. .先写入 redo log buffer
  2. 吧 redo log buffer 写入 page cache中
  3. 持久化 到磁盘当中,red log处于perpare阶段
  4. 事务执行过程中先把日志写到binlog cache 中,
  5. 把日志写入到文件系统的 page cache中
  6. 事务提交时,将 binlog cache 写入 binlog 文件
    在这里插入图片描述
    上图就是MySQL优化后的提交方式。
    1 .先写入 redo log buffer
    2.吧 redo log buffer 写入 page cache中
    3.事务执行过程中先把日志写到binlog cache 中,
    4.持久化 到磁盘当中,red log处于perpare阶段
    5 把日志写入到文件系统的 page cache中
    6.事务提交时,将 binlog cache 写入 binlog 文件

优化了哪里?
将red log持久化到磁盘当中的时间往后移了,这样组提交时可以提交组员会更多,组员越多节约磁盘 IOPS 的效果越好。

五.什么是双 ‘1’ 配置,配置后数据就不丢失吗?

只有在 sync_binlog 和 innodb_flush_log_at_trx_commit 都等于1的情况下,才能保证数据不丢失。

写 redo log 时,每次事务提交时,都将所有redo log fsync到磁盘

写 binlog 时,每次事务提交时,binlog 都会执行 fsync到磁盘。

数据丢失情况分析
在这里插入图片描述

情况一:redolog在prepare阶段持久化到磁盘(可能失败)也就是上图步骤3失败
mysql异常重启,redo log没有fsync,内存丢失,直接回滚,这种情况是不影响数据一致性

情况二:紧接着binlog持久化(可能失败)也就是上图步骤4失败
redolog fsync成功,但是binlog写入错误,此时mysql异常重启,现在有redolog的磁盘数据没有binlog的数据,此时检测redolog处于prepare阶段,但是没有binlog,回滚(虽然刚刚redolog fsync了但是不影响数据一致性,因为redolog的操作并没有写入mysql,也永远不会写入mysql)— 不懂的可以去看看我的MySQL刷脏页专栏,什么时候red log会进行刷盘

情况三:binlog完整但未commit 也就是上图步骤5失败
此时检测redolog处于prepare阶段,且binlog完整但未提交,默认添加commit标记,进而提交,写入mysql,满足数据一致性; 情况四:binlog完整且提交,写入musql,满足一致性;

情况四:binlog完整且提交,也就是图6步骤执行完成
写入musql,满足一致性;

至此MySQL的bin log和red log的两阶段提交,可以完整的保证我们数据一致性,从而保证数据不丢失。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/2786.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

力扣算法入门刷题

1、回文数 判断输入的整数是否是回文 我的一般思路: 将输入的整数转成字符串,再将这个字符串转成字符数组c,对字符数组进行遍历,如果第i个元素与第 c.length - i - 1 元素不相等,也就是通过比较首尾元素是否相同来判断…

自动化早已不是那个自动化了,谈一谈自动化测试现状和自我感受……

前言 从2017年6月开始接触自动化至今,已经有好几年了,从17年接触UI自动化(unittestselenium)到18年接触接口自动化(unittestrequests)再到18年自己编写自动化平台(后台使用python的flask&#…

风、光、柴油机、蓄电池、电网交互微电网经济调度优化问题研究附Matlab代码

✅作者简介:热爱科研的Matlab仿真开发者,修心和技术同步精进,matlab项目合作可私信。 🍎个人主页:Matlab科研工作室 🍊个人信条:格物致知。 更多Matlab仿真内容点击👇 智能优化算法 …

爆破校园网的宽带

前提:学校的手机号前7位相同,宽带密码都是手机号后六位。仅供学习。 准备工作:电脑一台,把校园网的宽带水晶头插在电脑上, 步骤: winR输入Rasphone点击新建,宽带,输入宽带名称&am…

Vue复刻华为官网 (一)

1 分析 根据华为网页的布局,我们大体上可以将其划分为7个盒子,如下,由于写一个这样的网页再加上部分动态效果,需要的时间很长,本篇博客只记录了div1、div2、div3的静态效果轮播图的实现。 2 顶部盒子的实现 想要实现的…

【C++AVL树】4种旋转详讲

目录 引子:AVL树是因为什么出现的? 1.AVl树的的特性 2.AVl树的框架 3.AVL树的插入 3.1四种旋转(左单旋、右单旋、左右双旋、右左双旋) 3.1.1左单旋 3.1.2右单旋 3.1.3左右双旋 3.1.4右左双旋 总结 引子:AVL树是因…

【单片机】单片机的核心思想

💬推荐一款模拟面试、刷题神器 、从基础到大厂面试题:👉点击跳转刷题网站进行注册学习 目录 一、单片机的核心思想 二、单片机核心图 三、上拉电路及应用 排阻的优势 四、单片机的输入输出模式 1、接收外部电压信号 2、向外输出电压信…

0089 时间复杂度,冒泡排序

/* * 排序也称排序算法(Sort Algorithm) * 排序是将一组数据,依指定的顺序进行排列的过程。 * * 排序分类 * 1.内部排序:将需要处理的所有数据都加载到内存存储器中进行排序(使用内存) * 插…

彻底搞懂WeakMap和Map

一 、Map Map是一种叫做字典的数据结构,Map 对象保存不重复键值对,并且能够记住键的原始插入顺序 Map的属性和方法* 属性: size: 返回所包含的键值对长度* 操作方法:* set(key,val): 添加新键值对* get(key): 通过传…

Linux--信号signal、父子进程、SIGCHLD信号相关命令

目录 1.概念: 2.信号的存储位置: 3.常见的信号的值以及对应的功能说明: 4.信号的值在系统源码中的定义: 5.响应方式: 6.改变信号的相应方式: (1)设置信号的响应方式: (2)默认:SIG_DFL;忽略:SIG_IGN…

Android Studio 新版本 Logcat 的使用

前言 最近,Android Studio 自动更新了自带的 Logcat 工具,整体外观和使用方法变得和之前完全不同了。一开始我以为是自己按到什么不该按的按钮,把 Logcat 弄坏了,后来才知道是版本更新导致的。新版本的 Logcat 用命令来过滤信息&…

jmeter变量函数以及抓包用法

抓包 代理服务器: 自己启动一个代理服务器 本地,要使用代理服务器的ip和端口,使用自己启动的代理服务器 操作步骤 添加线程组测试计划 > 非测试元件 > http代理服务器一定要修改 修改为** 测试计划>线程 ip就是你自己电脑的ip&…

Activity

Activity生命周期图 官网的 Activity 的生命周期图: 在官方文档中给出了说明,不允许在 onPause() 方法中执行耗时操作,因为这会影响到新 Activity 的启动。 常见情况下Activity生命周期的回调 (A 与 B 表示不同的 Activity &a…

(硬件设计)老工程师的经验之道

系列文章目录 1.元件基础 2.电路设计 3.PCB设计 4.元件焊接 5.板子调试 6.程序设计 7.算法学习 8.编写exe 9.检测标准 10.项目举例 11.职业规划 文章目录前言1、用蜡烛油固定电位器2、电路板接插件用彩色接插件前言 送给大学毕业后找不到奋斗方向的你(每周不定时…

Python----科学计数法、同时给多个变量赋值、eval函数、math库函数、复数(complex())、内置的数值运算函数、内置的数值运算操作符

科学计数法使用字母"e"或者“E”作为幂的符号,以10为基数,科学计数法的含义如下: 96e4:96乘10的4次幂 4.3e-3:4.3乘10的负三次幂 aeb:a*10*b 同时给多个变量赋值格式: 变量1,变量2表…

基于Python的电影推荐系统

电影推荐系统 目录 电影推荐系统 1 数据描述 1变量说明 1程序介绍 2 本次课程作业在 small-movielens 数据集的基础上,对用户、电影、评分数据进行了处理,然后根据 Pearson 相关系数计算出用户与其他用户之间的相似度,根据相似度进行推荐和…

用Python来表白,把情书写进她的照片里

前言 这不已经十一月了,22年马上就过完了,各位兄弟有对象了吗,现在就是缺钱还缺对象 退一步来说,有心仪的人吗啊,如果有的话,看看这篇 程序员的表白小妙招吧 实现步骤 想要实现把情书写在像素中&#xf…

【Web-HTML基础】颜色赋值、背景图片、文本和字体相关样式、元素的显示方式display、盒子模型、部分标签自带外边距或内边距

目录 颜色赋值 背景图片 文本和字体相关样式 元素的显示方式display 盒子模型 盒子模型之content内容 盒子模型之margin外边距 盒子模型之border边框 盒子模型之padding内边距 部分标签自带外边距或内边距 综合代码实现 颜色赋值 三原色: 红绿蓝 RGB RedGreenBlue …

【2022秋招面经】——深度学习

文章目录请写出常用的损失函数,平方损失、交叉熵损失、softmax损失函数和hinge1. 0-1 损失函数2. 绝对值损失函数3. 平方损失函数4. log 对数损失函数5. 指数损失函数(exponential loss)6. Hinge 损失函数7. 感知损失(preceptron loss)函数8.…

网课查题接口系统使用教程

网课查题接口系统使用教程 本平台优点:免费查题接口搭建 多题库查题、独立后台、响应速度快、全网平台可查、功能最全! 1.想要给自己的公众号获得查题接口,只需要两步! 2.题库:题库后台http://daili.jueguangzhe.cn/…