MySQL中的Redo Log、Undo Log和Binary Log

Redo Log

工作机制
  • 预写日志(WAL) :想象你正在为一本书编写内容。在正式将内容写入书本之前,你会先在一个草稿本上写下你要记录的内容。这样即使突然发生意外(比如墨水洒了),你也可以根据草稿本恢复丢失的内容。Redo Log就像是这个草稿本,在数据真正改变之前,先把即将发生的更改记下来。
    • 具体流程
      • 当一个事务开始执行并修改数据时,InnoDB首先会在内存中做这些修改,并同时把这些变更记录到Redo Log Buffer中(相当于草稿本)。
      • 这些日志随后会被异步刷新到磁盘上的Redo Log文件中(相当于正式的书本)。如果系统崩溃,在重启后,InnoDB会检查Redo Log,并重新应用那些还没来得及写入磁盘的数据更改,确保数据的一致性。
      • 循环使用:Redo Log由一系列固定大小的日志文件组成,当一个日志文件满了之后,会继续写入下一个日志文件,形成循环使用模式。这就像一本用完了就换下一本的日记本。
      • 检查点(Checkpoint):定期将内存中的脏页刷新到磁盘,并更新检查点位置。这有助于缩短数据库恢复时间并释放Redo Log空间。类似于你定期整理你的笔记本,确保所有重要信息都已保存好。
配置与注意事项
  • innodb_log_file_size:决定每本"日记本"的大小。较大的日记本可以减少更换日记本的频率,但可能会增加恢复时间。建议根据实际工作负载调整此值。例如,对于高并发写操作较多的应用,可能需要更大的Redo Log文件以减少日志切换的频率。
  • innodb_flush_log_at_trx_commit:控制什么时候把草稿纸上的内容搬到正式日记本上。
    • 设置为1表示每次完成一个事务就搬;
    • 设置为0表示每隔一段时间批量搬运;
    • 设置为2则是每次完成事务只放到操作系统缓存里,不立即搬到硬盘上。
  • innodb_flush_method:定义如何刷新数据和日志文件到磁盘,不同的设置会影响性能和安全性。例如,O_DIRECT可以绕过操作系统的缓存直接写入磁盘,提高性能但可能增加I/O负担。

Undo Log

工作机制
  • 多版本并发控制(MVCC) :假设你在编辑一篇文章,但是你希望保留每个版本以便随时回退。Undo Log就像是保存文章旧版本的地方。每当你要修改文章时,它会保存当前版本,这样如果需要撤销修改或者其他人想看之前的版本,就可以找到。
    • 快照读取:如果你想要查看文章的历史版本,可以通过Undo Log获取该版本的信息。这对于实现非锁定读非常重要。例如,两个用户同时读取同一张表的不同版本,而不会互相干扰。
    • 回滚段(Rollback Segments):用于存储撤销信息,使得可以回滚未完成的事务。
    • 清理机制:一旦确认没有人再需要某个旧版本的文章了,就可以删除或覆盖这部分Undo Log空间。这有助于防止表空间无限增长。
配置与注意事项
  • innodb_undo_tablespaces:指定Undo表空间的数量,增加数量可以帮助分散Undo Log的压力,就像准备更多的抽屉存放不同版本的文章。从MySQL 5.7开始支持此功能。
  • innodb_undo_log_truncate:启用自动收缩功能来管理Undo表空间的增长,防止其无限制增长,类似于定期清理不再需要的旧版本文章。
  • innodb_purge_rseg_truncate_frequency:控制Undo Log的清理频率,影响系统回收已不再使用的Undo Log页的速度。
  • innodb_max_undo_log_size:设置触发自动收缩的最大Undo Log大小。

Binary Log (Binlog)

工作机制
  • 逻辑日志 :不同于Redo和Undo Log,Binlog更像是一个详细的修改记录簿,记录了所有对数据库的操作(如SQL语句或行变更),而不是具体的物理数据页的变化。
    • 事件驱动:每当有事务执行完毕并提交时,相关的变更信息就会被记录到Binlog中。
    • 格式选择
      • STATEMENT:仅记录做了什么操作;
      • ROW:记录每一行的具体变化;
      • MIXED:根据情况选择STATEMENT或ROW的最佳记录方式。
配置与注意事项
  • 开启Binlog需要在MySQL配置文件中设置log-bin参数。
  • 根据需求选择合适的Binlog格式(STATEMENT, ROW, MIXED)。ROW格式更适合高并发环境,因为它能准确地记录每一行的变化,避免了基于STATEMENT可能存在的不确定性问题。
  • expire_logs_days:设置Binlog文件的过期天数,超过这个时间的日志文件将被自动删除,帮助控制磁盘使用量。
  • sync_binlog:控制Binlog的同步频率,0表示由操作系统决定,N表示每N次事务提交后同步到磁盘。较高的值可以提高性能但降低可靠性。

区别详解

目的
  • Redo Log:像一个保险箱,确保即使系统崩溃也能找回未保存的数据。
  • Undo Log:像是一个时光机,允许你撤销未完成的修改或者查看历史版本的数据。
  • Binlog:则是一个记录员,记录所有的数据库操作,用于数据恢复、复制和迁移。
内容形式
  • Redo Log:关注于如何重建数据页,记录的是数据页的物理变化。
  • Undo Log:保存的是数据的旧版本,用于回滚事务和支持MVCC。
  • Binlog:记录的是用户执行的所有操作,描述了事务的具体操作。
生命周期管理
  • Redo Log:随检查点推进而覆盖,周期性地将日志条目应用到数据页,并释放相应的日志空间。
  • Undo Log:依赖于事务状态及其对应的MVCC视图,当没有事务再需要某个Undo Log记录时,它会被标记为可重用。
  • Binlog:需手动或按策略清理,通常通过设置过期时间或手动命令来管理Binlog文件。

示例说明

假设你在一家公司负责文档管理系统,以下是每个日志类型在实际操作中的作用:

  • Redo Log:当你正在编辑一份重要的报告时,系统会先将你做的每一个改动记录下来。如果突然停电,你可以根据这些记录恢复未保存的工作。这就像是你在编辑Word文档时,Office软件会自动保存临时文件,以防意外丢失。

  • Undo Log:当你在编辑文档时,系统会保存每个版本,让你可以轻松撤销任何你不满意的修改,或者查看以前的版本。这就像是Word中的"撤销"功能,可以回退到任意步骤。

  • Binlog:当你需要备份整个文档库或将文档库迁移到另一个服务器时,系统会记录所有操作,确保你可以完全复制或恢复文档库的状态。这就像是你将整个项目文件夹复制到外部硬盘以备不时之需。

更详细的配置示例

Redo Log 配置
bash 复制代码
[mysqld]
innodb_log_file_size = 512M
innodb_log_files_in_group = 3
innodb_flush_log_at_trx_commit = 1
innodb_flush_method = O_DIRECT
  • innodb_log_file_size=512M:设置每个Redo Log文件大小为512MB,适用于高并发场景。
  • innodb_log_files_in_group=3:设置Redo Log组中有3个文件,提供冗余和更高的吞吐量。
  • innodb_flush_log_at_trx_commit=1:确保每个事务提交时都会将日志刷到磁盘,保证数据安全。
  • innodb_flush_method=O_DIRECT:绕过操作系统缓存,直接写入磁盘,提高性能。
Undo Log 配置
bash 复制代码
[mysqld]
innodb_undo_tablespaces = 4
innodb_undo_log_truncate = ON
innodb_max_undo_log_size = 1G
  • innodb_undo_tablespaces=4:设置4个Undo表空间,分散Undo Log压力。
  • innodb_undo_log_truncate=ON:开启自动收缩功能,防止Undo Log无限增长。
  • innodb_max_undo_log_size=1G:设置触发自动收缩的最大Undo Log大小为1GB。
Binary Log 配置
bash 复制代码
[mysqld]
log-bin = mysql-bin
binlog_format = ROW
expire_logs_days = 7
sync_binlog = 1
  • log-bin=mysql-bin:开启Binlog,并设置前缀为mysql-bin。
  • binlog_format=ROW:选择Row格式记录Binlog,适合高并发环境。
  • expire_logs_days=7:设置Binlog文件过期时间为7天。
  • sync_binlog=1:确保每个事务提交时都将Binlog刷到磁盘,保证数据一致性。
相关推荐
赴前尘几秒前
chromem-go + ollama + bge-m3 进行文档向量嵌入和查询
开发语言·数据库·golang
Austindatabases26 分钟前
数据库界的“申公豹”,带云DBA走出--救生筏困境!
数据库·dba
努力也学不会java30 分钟前
【MyBatis】MyBatis 操作数据库
java·数据库·spring boot·spring·java-ee·intellij-idea·mybatis
博睿谷IT99_34 分钟前
数据库DBA认证,选哪个认证合适?
数据库·mysql·postgresql·dba·oracle ocp
计算机学姐43 分钟前
基于SpringBoot的足球俱乐部管理系统
java·vue.js·spring boot·后端·mysql·java-ee·intellij-idea
真的睡不醒ovo1 小时前
nacos 外置mysql数据库操作(docker 环境)
数据库·mysql·spring cloud
JIU_WW1 小时前
Redis大key问题
数据库·redis
weixin_391336901 小时前
gdb 调试mysql
android·mysql·adb
大桶矿泉水1 小时前
qt之使用redis与其他程序(python)交互同通信
数据库·redis·缓存·银河麒麟redis·linux redis