【MySQL基本功系列】第二篇 InnoDB事务提交过程深度解析

通过上一篇博文,我们简要了解了MySQL的运行逻辑,从用户请求到最终将数据写入磁盘的整个过程。

当数据写入磁盘时,存储引擎扮演着关键的角色,它负责实际的数据存储和检索。

在MySQL中,有多个存储引擎可供选择,每个存储引擎都具有不同的特性和适用场景,但目前最常用的存储引擎之一是InnoDB。

今天,我们将学习InnoDB存储引擎的架构设计和核心特点,以及InnoDB事务提交过程深度解析。

UPDATE users set name='张老三' WHERE id = 1

如果我们执行上述update语句,它在整个执行过程中会发生什么?

接下来,我们将围绕这个update语句,熟悉整个的执行过程。

一、InnoDB存储引擎的特性:

1. 缓冲池(Buffer Pool)

缓冲池是InnoDB内部的一个重要内存结构,用于高效管理数据库表的数据和索引的缓存。

它在内存中存储了常用的数据页,以加速数据的读取和写入。

我们要更新上述sql

这个时候,它会先找 id = 1 这行数据是否在缓冲池中,如果不在,就将这条数据从磁盘加载到缓存池中。
缓冲池
当我们此时update的时候,也是先将新的数据更新到缓冲池,再写入到磁盘。

2. undo log(回滚日志)

我们知道,事务的所有操作要么全部成功(提交),要么全部失败(回滚)。

那么事务如何回滚呢?我们就要介绍到undo log

unod log文件顾名思义,就是回滚日志。

Undo Log 记录了事务对数据所做的修改,以便在需要回滚时能够撤销或者反向执行这些修改。

就是说我们写入新的数据到内存(缓冲池之前),会把更新之前的数据,也就是说原来的数据写入undo log文件,方便回滚的时候将数据恢复到事务开始之前的状态。

当我们把要更新的那行记录从磁盘文件加载到缓冲池,同时把更新前的旧值写入undo日志文件之后,就可以正式开始更新这行记录了。
在这里插入图片描述
根据上图我们看到,InnoDB收到更新请求后,查看缓冲池中是否有要更新这条数据的缓存页,如果没有则从磁盘文件中加载到缓冲池,再将更新前的数据写入undo log,最后进行数据的更新(更新到内存)

3. Redo Log(重做日志)

现在我们已经把内存里(缓冲池)的数据进行了修改,但是磁盘上的数据还没修改。

如果这时候MySQL机器宕机了,导致内存里修改过的数据丢失,应该怎么办呢?

为了防止这种情况发生,InnoDB 存储引擎在处理事务时采用了一种称为"write-ahead logging" (WAL) 的机制。

这种机制在更内存(缓冲池)时,会同时更新 Redo Log(重做日志)。

Redo Log是用于记录数据库引擎在执行事务期间对数据所做的所有修改操作,它记录了对数据页的物理修改操作,例如在磁盘上某个位置上的某个字节被修改成什么值。

当我们提交事务时,会把操作记录到 Redo Log 中,然后再更新到磁盘。这样做的目的是在系统崩溃时,可以通过重新执行 Redo Log 中的操作来还原已提交的事务,确保数据的一致性和完整性。
在这里插入图片描述

通过上图第5步,我们看到,当事务提交时,会将Redo Log写入到磁盘中,这是InnoDB的默认策略,也有其他方式可以自己配置

它由innodb_flush_log_at_trx_commit 参数进行控制:

3.1 innodb_flush_log_at_trx_commit = 0:

事务提交时,并不会立即将事务日志刷新到磁盘,而是每秒执行一次日志刷新操作。

也就是说,提交事务之后,mysql宕机,那么此时redo日志没有刷盘,导致内存(MySQL内存)里的redo日志丢失,我们提交的事务更新的数据就丢失了。

可能会丢失最多一秒钟的事务。

3.2 innodb_flush_log_at_trx_commit = 1(默认值):

每次事务提交时,都会将事务日志立即刷新到磁盘。

这种配置提供了 最高的事务持久性 ,因为在事务提交后,日志已经被写入磁盘,即使系统崩溃,也能够最小程度地丢失数据。

3.3 innodb_flush_log_at_trx_commit = 2:

每次事务提交时,事务日志会被写入到操作系统的缓存,而不是直接刷新到磁盘。
然后,日志会被每秒钟刷新到磁盘。这样可以提高性能,同时在机器崩溃时可能会丢失最多一秒钟的事务。

所以对于数据库这样严格的系统而言,一般建议redo日志刷盘策略设置为1,保证事务提交之后,数据绝对不能丢失。

当然,我们应该根据业务需要适当调整配置。

在整个事务提交的过程中,还有一点不得不提,那就是Binlog

根据我的经历,其实在实际工作中,我们更频繁地听到的是 Binlog(归档日志)。

例如,在数据库备份、数据恢复以及通过 CDC 同步数据等方面,Binlog 扮演着至关重要的角色。

二、 Binlog()

MySQL Binlog(二进制日志)是一种记录数据库中修改操作的日志。

与上面介绍的Redo Log偏向于物理性质的重做日志不同,Binlog更倾向于逻辑性的日志。

它记录了诸如“对users表中id = 1的一行数据进行更新,更新后的值是什么”之类的逻辑操作。

Binlog不是InnoDB存储引擎特有的日志文件,而是属于MySQL服务器自身的日志文件

在事务提交时,MySQL会将修改操作先写入Redo log,以确保这些修改操作在系统崩溃或故障时不会丢失。

然后,再将事务写入binlog,以记录详细的修改操作信息,并用于数据复制和恢复。

这种顺序的执行方式是为了确保数据的一致性和可恢复性。

通过先写redo log,可以确保事务的持久性,避免数据丢失。

然后,通过写binlog可以记录详细的修改操作信息,并用于数据复制和恢复。
在这里插入图片描述

1. binlog 刷盘策略

当然,与Redo Log一样,对于Binlog日志,也有不同的同步策略。

它是通过sync_binlog参数可以控制Binlog的刷盘策略

1.1 sync_binlog=0:

sync_binlog=0是MySQL的默认值。

在提交事务时,将Binlog写入磁盘时先进入操作系统(OS)的Cache内存缓存。

这意味着Binlog首先被写入内存,而不是直接持久化到磁盘。

这样的方式在性能上更高,但在机器宕机时可能导致数据丢失。

1.2 sync_binlog=1

sync_binlog=1,在提交事务时,强制将Binlog直接写入磁盘文件,而不经过操作系统的Cache内存缓存。

这样做可以提高数据持久性,即使机器宕机,也不会丢失Binlog日志。

但是,这可能会对性能产生一定影响。

通过设置sync_binlog的不同取值,可以在数据安全性和性能之间进行权衡。

如果对数据的持久性要求较高,可以将其设置为1,确保在提交事务时Binlog立即写入磁盘。

如果更注重性能,可以使用默认值0,利用操作系统的Cache提高写入速度。

在提交了事务之后,MySQL有一个后台的IO线程,会不定期随机的把内存buffer pool中的修改后的脏数据写到磁盘中。

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

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

vColorPicker——基于 Vue 的颜色选择器插件

文章目录 前言样例特点 一、使用步骤?1. 安装2.引入3.在项目中使用 vcolorpicker 二、选项三、事件 前言 vColorPicker——官网 vColorPicker——GitHub 样例 vColorPicker是基于 Vue 的一款颜色选择器插件,仿照Angular的color-picker插件制作 特点 …

【GIT】git分支命令,使用分支场景介绍git标签介绍,git标签命令,git标签使用的场景git查看提交历史

目录 一,git分支命令,使用分支场景介绍 二,git标签介绍,git标签命令,git标签使用的场景 三,git查看提交历史 前言: 今天我们来聊聊关于Git 分支管理。几乎每一种版本控制系统都以某种形式支持…

第24章_mysql性能分析工具的使用

文章目录 1. 数据库服务器的优化步骤2.查看系统性能参数3. 统计SQL的查询成本:last_query_cost4. 定位执行慢的 SQL:慢查询日志4.1 开启慢查询日志参数4.2 查看慢查询数目4.3 测试慢sql语句,查看慢日志4.4 系统变量 log_output, l…

【蓝桥杯 第十三届省赛Java B组】真题训练(A - F)

目录 A、星期计算 - BigInteger B、山 - 暴力判断 字符串 C、字符统计 - 简单哈希 D、最少刷题数 - 排序 思维 二分 分情况讨论 (1)(错误)自写哈希表 (2)正解 E、求阶乘 - 数学思维 二分 F、…

SAP实现文本框多行输入(类cl_gui_textedit)

参考文章:https://blog.csdn.net/SAPmatinal/article/details/130882962 先看效果,在输入框先来一段《赤壁赋》 然后点击 ‘保存输出’按钮,就能把输入内容从表里读取并输出来 源代码: *&-------------------------------…

多个div横向排列的几种方法

以下面这组 div 为例&#xff0c;group的高度由内容撑开 <div id"group"><div id"div1">div1</div><div id"div2">div2</div><div id"div3">div3</div> </div>显示结果如下为上下排…

Go常见数据结构的实现原理——map

&#xff08;一&#xff09;基础操作 版本&#xff1a;Go SDK 1.20.6 1、初始化 map分别支持字面量初始化和内置函数make()初始化。 字面量初始化&#xff1a; m : map[string] int {"apple": 2,"banana": 3,}使用内置函数make()初始化&#xff1a; m …

19.删除链表的倒数第N个结点(LeetCode)

想法一 先用tail指针找尾&#xff0c;计算出节点个数&#xff0c;再根据倒数第N个指定删除 想法二 根据进阶的要求&#xff0c;只能遍历一遍链表&#xff0c;那刚刚想法一就做不到 首先&#xff0c;我们要在一遍内找到倒数第N个节点&#xff0c;所以我们设置slow和fast两个指…

Python----元组的定义与使用

1、为什么需要元组 思考&#xff1a;如果想要存储多个数据&#xff0c;但是这些数据是不能修改的数据&#xff0c;怎么做&#xff1f; 首先&#xff0c;列表可以一次性存储多个数据&#xff0c;但是列表中的数据允许更改。 相关链接&#xff1a;Python--列表及其应用场景-CS…

Retrieval-Augmented Generation for Knowledge-Intensive NLP Tasks - 翻译学习

知识密集型NLP任务的检索增强生成 - 论文学习 文章目录 Abstract1 Introduction2 Methods2.1 Models2.2 Retriever: DPR2.3 Generator: BART2.4 Training2.5 Decoding 3 Experiments3.1 Open-domain Question Answering3.2 Abstractive Question Answering3.3 Jeopardy Questio…

[工业自动化-14]:西门子S7-15xxx编程 - 软件编程 - STEP7 TIA博途是全集成自动化软件TIA portal快速入门

目录 一、TIA博途是全集成自动化软件TIA portal快速入门 1.1 简介 1.2 软件常用界面 1.3 软件安装的电脑硬件要求 1.4 入口 1.5 主界面 二、PLC软件编程包含哪些内容 2.1 概述 2.2 电机运动控制 一、TIA博途是全集成自动化软件TIA portal快速入门 1.1 简介 Siemens …

Leetcode -463.岛屿的周长 - 476.数字的补码

Leetcode Leetcode -463.岛屿的周长Leetcode - 476.数字的补码 Leetcode -463.岛屿的周长 题目&#xff1a;给定一个 row x col 的二维网格地图 grid &#xff0c;其中&#xff1a;grid[i][j] 1 表示陆地&#xff0c; grid[i][j] 0 表示水域。 网格中的格子 水平和垂直 方向…

小样本目标检测(Few-Shot Object Detection)综述

背景 前言:我的未来研究方向就是这个,所以会更新一系列的文章,就关于FSOD,如果有相同研究方向的同学欢迎沟通交流,我目前研一,希望能在研一发文,目前也有一些想法,但是具体能不能实现还要在做的过程中慢慢评估和实现.写文的主要目的还是记录,避免重复劳动,我想用尽量简洁的语言…

MATLAB的编程与应用,匿名函数、嵌套函数、蒙特卡洛法的掌握与使用

目录 1.匿名函数 1.1.匿名函数的定义与分类 1.2.匿名函数在积分和优化中应用 2.嵌套函数 2.1.嵌套函数的定义与分类 2.2.嵌套函数彼此调用关系 2.3.嵌套函数在积分和微分中应用 3.微分和积分 4.蒙特卡洛法 4.1.圆周率的模拟 4.2.计算N重积分&#xff08;均匀分布&am…

计算机毕业设计 基于Springboot的影院购票管理系统的设计与实现 Java实战项目 附源码+文档+视频讲解

博主介绍&#xff1a;✌从事软件开发10年之余&#xff0c;专注于Java技术领域、Python人工智能及数据挖掘、小程序项目开发和Android项目开发等。CSDN、掘金、华为云、InfoQ、阿里云等平台优质作者✌ &#x1f345;文末获取源码联系&#x1f345; &#x1f447;&#x1f3fb; 精…

【入门Flink】- 09Flink水位线Watermark

在窗口的处理过程中&#xff0c;基于数据的时间戳&#xff0c;自定义一个“逻辑时钟”。这个时钟的时间不会自动流逝&#xff1b;它的时间进展&#xff0c;就是靠着新到数据的时间戳来推动的。 什么是水位线 用来衡量事件时间进展的标记&#xff0c;就被称作“水位线”&#x…

AIGC ChatGPT 4 轻松实现小游戏开发制作

贪吃蛇的小游戏相信大家都玩儿过,我们让ChatGPT4来帮我们制作一个贪吃蛇的小游戏。 在ChatGPT中发送Prompt如下图: 完整代码如下: <!DOCTYPE html> <html> <head> <title>贪吃蛇游戏</title> <style type="text/css"> #can…

UPLAOD-LABS2

less7 任务 拿到一个shell服务器 提示 禁止上传所有可以解析的后缀 发现所有可以解析的后缀都被禁了 查看一下源代码 $is_upload false; $msg null; if (isset($_POST[submit])) {if (file_exists($UPLOAD_ADDR)) {$deny_ext array(".php",".php5&quo…

第一百六十九回 如何修改NavigationBar的形状

文章目录 1. 概念介绍2. 使用方法3. 代码与效果3.1 示例代码3.2 运行效果 4. 内容总结 我们在上一章回中介绍了"如何修改按钮的形状"相关的内容&#xff0c;本章回中将介绍NavigationBar组件.闲话休提&#xff0c;让我们一起Talk Flutter吧。 1. 概念介绍 我们在本章…

javaEE案例,前后端交互,计算机和用户登录

加法计算机,前端的代码如下 : 浏览器访问的效果如图 : 后端的代码如下 再在浏览器进行输入点击相加,就能获得结果 开发中程序报错,如何定位问题 1.先定位前端还是后端(通过日志分析) 1)前端 : F12 看控制台 2)后端 : 接口,控制台日志 举个例子: 如果出现了错误,我们就在后端…
最新文章