返回顶部
首页 > 资讯 > 数据库 >MySQL是如何保证数据的完整性
  • 555
分享到

MySQL是如何保证数据的完整性

MySQL数据MySQL数据完整性 2022-06-01 12:06:02 555人浏览 薄情痞子
摘要

数据的一致性和完整性对于在线业务的重要性不言而喻,如何保证数据不丢呢?今天我们就探讨下关于数据的完整性和强一致性,Mysql做了哪些改进。 一. MySQL的二阶段提交     在ora

数据的一致性和完整性对于在线业务的重要性不言而喻,如何保证数据不丢呢?今天我们就探讨下关于数据的完整性和强一致性,Mysql做了哪些改进。

一. MySQL的二阶段提交

    在oraclemysql这种关系型数据库中,讲究日志先行策略(Write-Ahead Logging),只要日志持久化到磁盘,就能保证Mysql异常重启后,数据不丢失。在MySQL中,提到日志不得不提的就是redo log和binlog。

1. redo log

redo log又称重做日志文件,详细的记录了对每一个数据页里面的数据行的修改,记录的是数据修改之后的值。Redo log是用来做数据库crash recovery的,是保证数据安全的非常重要的功能之一。

redo log的写入的方式是顺序写、循环写,通过innodb_log_file_size和innodb_log_files_in_group两个参数控制redo log的文件大小和个数。redo log在写入磁盘前会先写redo log buffer中,大小由innodb_log_buffer_size控制。日志在写入redo log buffer后是如何持久化到磁盘的呢?为了控制redo log的写入策略,Innodb根据innodb_flush_log_at_trx_commit参数不同的取值采用不同的策略,它有三种不同的取值:

  • 1. 设置为 0 的时候:事务提交时由MySQL的后台Master线程每隔1秒将缓存区的文件刷新到日志文件中。
  • 2. 设置为 1 的时候,表示每次事务提交时都将 redo log 直接持久化到磁盘,保证了事务日志不丢失,但会对数据库性能稍有影响。
  • 3. 设置为 2 的时候,表示每次事务提交时都只是把 redo log 写到 日志文件中,但不会刷盘,由文件系统自行刷磁盘。

三种模式下,0的性能最好,但是不安全,MySQL进程一旦崩溃会导致丢失一秒的数据。1的安全性最高,但是对性能影响最大,2的话主要由操作系统自行控制刷磁盘的时间,如果仅仅是MySQL宕机,对数据不会产生影响,如果是主机异常宕机了,同样会丢失数据。

2. binlog

binlog又称二进制日志,记录了对MySQL数据库执行更改的所有操作,不包含select和show操作,主要起到了恢复、复制、审计等功能。Binlog的格式主要有statement、row、mixed三种。

Statement:基于操作的SQL语句记录到binlog中,不建议使用。

Row:基于行的变更情况记录,会记录行更改前后的内容,row模式也是数据库不丢数据的重要保证,推荐使用。

Mixed:混合前两个模式,不建议使用。

Binlog的写入逻辑也比较简单:事务执行过程中,先写入binlog cache,事务提交时再写入binlog文件。binlog cache由binlog_cache_size和max_binlog_size参数控制,每个线程分配一个binlog cache,但是共用binlog文件。

Binlog的写入日志文件的机制由sync_binlog控制:

  • 1. sync_binlog=0 的时候,表示每次提交事务都只 write,不 fsync;
  • 2. sync_binlog=1 的时候,表示每次提交事务都会执行 fsync,将数据刷盘;
  • 3. sync_binlog=N(N>1) 的时候,表示n次事务提交之后,MySQL才进行一次fsync动作,将binlog cache中的数据刷入磁盘。

innodb_flush_log_at_trx_commit和sync_binlog都设置为1是MySQL数据中经典的双一模式,是数据库不丢数据的保障。

MySQL数据采取WAL机制就是为了减少每次脏数据刷盘带来的性能影响,如果设置”双一”策略会不会影响数据库的性能呢?其实这主要得益于redo log和binlog都是顺序写,磁盘的顺序写比随机写的速度要快的多,加上MySQL内部的组提交机制,已经大幅降低了对磁盘的ioPS消耗了。

3. 两阶段提交

MySQL引入二阶段提交(two phase commit or 2pc),MySQL内部会将普通事务当做一个XA事务(内部分布式事务)来处理,会自动为每个事务分配一个唯一的ID(XID),COMMIT会被动的分成Prepare和Commit两个阶段。

第一阶段:Transaction Prepare Phase

此时SQL已经成功执行,并生成xid信息及redo和undo的内存日志。然后调用prepare方法完成第一阶段,将事务状态设为TRX_PREPARED,并将redo log刷盘。

第二阶段:Commit Phase

如果事务第一阶段进入prepare阶段,则将产生的binlog写入文件并刷盘,此时事务已经铁定要提交了。

具体异常场景分析:

当事务在prepare阶段crash,数据库recovery的时候该事务未写⼊Binary log并且存储引擎未提交,则该事务rollback。

当事务在binlog阶段crash,此时⽇志还没有成功写⼊到磁盘中,启动时会rollback此事务。3. 当事务在binlog⽇志已经fsync()到磁盘后crash,但是InnoDB没有来得及commit,此时MySQL数据库recovery的时候将会读出⼆进制⽇志的Xid_log_event,然后告诉InnoDB提交这些XID的事务,InnoDB提交完这些事务后会回滚其它的事务,使存储引擎和⼆进制⽇志始终保持⼀致。

MySQL的二阶段提交就保证了数据库在异常宕机重启后的数据不丢失。

二. Double Write

    前面我们说了,redo log、binlog以及二阶段提交保证了数据在MySQL异常重启后能够通过前滚和回滚恢复数据。MySQL在recovery时通过redo log进行恢复,redo log记录的是页上的物理操作,但是这里有个问题,如果页本身就是错的,比如发生页的部分写问题(页大小是 16K,假设在把内存中的脏页写到数据库的时候,写了4K 突然掉电。也就是前两 4K 是新的,后 12K 是旧的,那么这个数据页就是不完整的,是一个坏掉的数据页), 这时redo恢复的时候会去校验数据页的完整性,此时数据页已经损坏了,故无法使用 redo log 进行恢复,这个数据就丢失了。

Double Write原理:

当刷新缓冲池脏页时,并不直接写到数据文件中,而是先拷贝至double write buffer。

然后从double write buffer分两次写入磁盘共享表空间中,每次写入 1MB。

最后再从double write buffer写入数据文件。虽然数据总是写入两次,但是由于double write 写入的时候是顺序写,实际上也就牺牲了系统性能的 10%左右。

这样就可以解决上文提到的部分写失效的问题,因为在磁盘共享表空间中已有数据页副本拷贝,如果数据库在页写入数据文件的过程中宕机,在实例恢复时,可以从共享表空间中找到该页副本,将其拷贝覆盖原有的数据页,再应用重做日志即可。

3. 小结

    今天我们聊了MySQL的二阶段提交和double write机制,分别解决了在MySQL宕机重启以及发生页的部分写的场景下,MySQL是如何做到不丢失数据。那如果我们的操作系统宕机无法启动了,又该怎么办呢?MySQL在集群架构中又做了哪些优化来保证数据不丢失呢?我们下一章再来和大家分享MySQL在集群架构中的优化改进。

您可能感兴趣的文档:

--结束END--

本文标题: MySQL是如何保证数据的完整性

本文链接: https://lsjlt.com/news/9699.html(转载时请注明来源链接)

有问题或投稿请发送至: 邮箱/279061341@qq.com    QQ/279061341

猜你喜欢
  • MySQL是如何保证数据的完整性
    数据的一致性和完整性对于在线业务的重要性不言而喻,如何保证数据不丢呢?今天我们就探讨下关于数据的完整性和强一致性,MySQL做了哪些改进。 一. MySQL的二阶段提交     在Ora...
    99+
    2022-06-01
    MySQL 数据 MySQL 数据完整性
  • Oracle中的数据完整性如何保证
    在Oracle中,数据完整性可以通过以下几种方式来保证: 主键约束:主键约束是一种在表中唯一标识每条记录的约束,可以确保表中的每...
    99+
    2024-04-09
    Oracle
  • Teradata如何保证数据的一致性和完整性
    Teradata通过以下方式保证数据的一致性和完整性: ACID事务: Teradata使用ACID(原子性、一致性、隔离性和持...
    99+
    2024-04-09
    Teradata
  • MongoDB如何确保数据完整性
    MongoDB通过以下几种方式来确保数据的完整性: 数据验证规则:MongoDB支持在集合级别设置数据验证规则,可以定义数据的结...
    99+
    2024-05-07
    MongoDB
  • MySQL中如何确保数据的一致性和完整性
    在MySQL中,可以通过以下方式来确保数据的一致性和完整性: 使用主键和外键约束:定义主键和外键可以确保数据表之间的关系,避免数...
    99+
    2024-04-09
    MySQL
  • Spring Data 的数据验证:确保数据完整性和一致性
    注解验证 Spring Data 提供了几个注解,用于在实体类中直接指定验证规则: @NotNull: 字段不能为空。 @Size: 限制字符串长度或集合大小。 @Min 和 @Max: 指定数值约束。 @Pattern: 验证字符串是...
    99+
    2024-04-02
  • Teradata中怎么保证数据的安全性和完整性
    在Teradata中,可以采取以下措施来确保数据的安全性和完整性: 访问控制:通过对用户和角色进行权限管理,限制用户对数据库和表...
    99+
    2024-04-09
    Teradata
  • 如何确保Hadoop数据的准确性和完整性
    确保Hadoop数据的准确性和完整性可以通过以下几种方式来实现: 数据采集过程中的数据质量控制:在数据采集阶段,应该对数据进行有...
    99+
    2024-02-29
    Hadoop
  • PHP 函数中的日志记录,如何保证数据的准确性和完整性?
    PHP 是一门广泛使用的开源服务器端脚本语言,它支持多种数据库,并且可以用于编写网页、桌面应用程序以及命令行脚本等。在 PHP 中,函数是最基本的语言结构之一,而在函数中,日志记录是一个重要的话题。 日志记录是一种在应用程序中记录信息的方法...
    99+
    2023-06-30
    函数 日志 数据类型
  • MySQL--数据完整性
    - 数据类型 原则 尽量使用取值范围小的,节省存储空间 整数:int, bit  小数:decimal  表示浮点数  decimal(5,&nb...
    99+
    2024-04-02
  • 数据库高并发请求怎么保证数据完整性
    小编给大家分享一下数据库高并发请求怎么保证数据完整性,希望大家阅读完这篇文章后大所收获,下面让我们一起去探讨吧!存储引擎查看MySQL给开发者提供了查询存储引擎的功能,我这里使用的是MySQL5.6.4,可...
    99+
    2024-04-02
  • 怎么保证Redis序列化数据的完整性与安全性
    要保证Redis序列化数据的完整性与安全性,可以采取以下措施: 使用合适的序列化机制:选择合适的序列化机制可以确保数据的完整性和...
    99+
    2024-04-29
    Redis
  • 打包Java项目,如何保证索引完整性?
    在Java开发中,我们经常需要将项目打包成可执行的jar包或war包,以便于部署和运行。在打包过程中,我们需要考虑到jar包中包含的索引文件是否完整,因为索引文件的完整性直接影响着程序的运行效率和正确性。本文将介绍如何打包Java项目,并...
    99+
    2023-06-18
    索引 打包 缓存
  • ZooKeeper是如何保证数据的一致性的
    ZooKeeper通过以下方式保证数据的一致性: 原子性操作:ZooKeeper的所有写操作都是原子性的,要么成功要么失败,不会...
    99+
    2024-03-06
    ZooKeeper
  • 数据守护神:确保数据库的完整性
    在现代数据驱动型世界中,数据库是企业赖以生存的关键资产。因此,维护数据库的完整性和一致性至关重要,以确保数据的准确性和可靠性。以下是一些最佳实践,可帮助您担任数据库的“守护神”,确保其免受数据错误和不一致的影响: 数据验证 数据验证是确...
    99+
    2024-03-07
    数据库完整性、数据验证、约束条件、索引、触发器
  • MySQL和Redis如何保证数据一致性
    MySQL与Redis都是常用的数据存储和缓存系统。为了提高应用程序的性能和可伸缩性,很多应用程序将MySQL和Redis一起使用,其中MySQL作为主要的持久存储,而Redis作为主要的缓存。在这种情况下,应用程序需要确保MySQL和Re...
    99+
    2023-08-22
    mysql redis 数据库
  • MySQL是如何保证数据不丢失的?
    文章目录 前言Buffer Pool 和 DML 的关系DML操作流程加载数据页更新记录 数据持久化方案合适的时机刷盘双写机制日志先行机制日志刷盘机制Redo Log 恢复数据 总结 前言 上篇文章《InnoDB在SQL...
    99+
    2023-12-22
    mysql 数据库
  • mysql中数据完整性是指什么
    这篇文章给大家分享的是有关mysql中数据完整性是指什么的内容。小编觉得挺实用的,因此分享给大家做个参考,一起跟随小编过来看看吧。数据完整性是指数据的精确性和可靠性,是指在传输、存储信息或数据的过程中,确保...
    99+
    2024-04-02
  • MySQL的原子性是如何保证的?
    原子性是指一个事务中的所有操作要么全部成功提交,要么全部回滚撤销,不存在部分成功部分失败的情况。MySQL通过以下方式来保证事务的原子性: 事务日志(transaction log):MySQL使用...
    99+
    2023-09-23
    mysql 数据库
  • cookie加密解密和保证数据完整性(不被篡改)
    cookie加密解密和保证数据完整性 AES-128-CBC`加密算法 AES-128-CBC是一种分组对称加密算法,即用同一组key进行明文和密文的转换,以128bit为一组,128bit==16B...
    99+
    2023-09-04
    php laravel
软考高级职称资格查询
编程网,编程工程师的家园,是目前国内优秀的开源技术社区之一,形成了由开源软件库、代码分享、资讯、协作翻译、讨论区和博客等几大频道内容,为IT开发者提供了一个发现、使用、并交流开源技术的平台。
  • 官方手机版

  • 微信公众号

  • 商务合作