深入MySQL(一)—— 深入理解binlog

2,080 阅读5分钟

概述


binlog(binary log)顾名思义是一组二进制日志文件,其中包含了对MySQL服务器实例的数据修改信息。它也包含了一些其它的元数据

  • 有关正确再现语句所需的服务状态信息
  • 错误码
  • 维护二进制日志本身所需的元数据(例如, 轮换事件 ,详见下文)

binlog是运行期服务状态改变的追踪,它所包含的 Events 描述了状态的改变。更确切的说,binlog中的 Events 描述了那些能够用来再现服务状态改变的行为。

用途


binlog有两种用途

  • 主从复制(结合Slave的relay log来实现)
  • 备份恢复

总之,都是通过binlog上的 events 信息来再现服务的状态

  • events 记录的是 SQL语句 就执行SQL语句
  • 如果记录的是 数据更改 直接保存数据更改后的状态

查看binary log文件列表


两种方式,

  1. SQL语句 SHOW BINARY LOGS 在这里插入图片描述
  2. 查看HOSTNAME.index文件(下文介绍)在这里插入图片描述

查看当前source服务的binlog状态


  1. SQL语句SHOW MASTER STATUS 在这里插入图片描述

注意:该操作需要系统权限,而且当 GTID mode 启用时Executed_Gtid_Set才会存在,表示二进制日志中写入的一组全局事务ID。

格式


binlog支持三种格式,

  • statement-based 此时events包含了所有产生数据变更的 SQL语句 —— DDL(修改表结构,创建表库等),DML(增删改)。 如果使用statement作为日志格式,在某些情况下做数据恢复和备份会产生问题,比如服务引擎设置不一致、UUID()、自定义函数、存储过程或触发器等,都会导致replica数据状态与source数据状态无法达成一直。
  • row-based【 defalut 】 此时events分别描述了对单个行的 更改 某些情况下row-based也会自动选择记录 SQL语句 而并非 数据更改,比如一系列DDL……
  • mixed-based Mixed-baed默认使用 statement-based 格式记录日志但必要条件下会自动转换成 row-based 格式来记录。

注意:

  • Row-based and Mixed-based 在 MySQL 5.1.* 之后可用。
  • 三种类型格式各有优缺点,至于如何选择,可以根据 业务数据特征存储引擎集群模式 来判断。

设置格式


  • 启动时设置,两种方式
    1. 传入启动参数 --binlog-format=format
    2. 读取配置文件 etc/my.cnfbinlog-format=format
  • 运行时设置,两种作用域(要求权限)
    1. SET GLOBAL binlog_format = ‘format’
    2. SET SESSION binlog_format = 'format'

优先级:

session > global > 启动参数 > 配置文件

结构与内容


binlog是一组日志文件,包含了对一个MySQL服务实例的数据修改信息。

  • 日志文件包括 一组binary log 文件(默认是HOSTNAME-bin.NNNNNN),再加上一个 index 文件(默认HOSTNAME.index,index文件是一个包含了当前binary log文件名列表的文本文件)。
  • 每个日志文件的开头包含一个4byte的魔数,紧随其后的是描述数据修改的一系列events
  • 魔数字节是 0xfe 0x62 0x69 0x6e = “þbin”
    • 每个 Event 包含 header字节数组跟在后面的data字节数组 两部分:
      1. header bytes 部分提供了一些信息,比如Event生成时间 timestamp (单位:s)、服务身份标识 server_id 等其他信息。
      2. data bytes 部分提供特定于event类型的信息,例如特定的数据修改。
    • 第一个event被称为 descriptor event (描述符事件,START_EVENT_V3FORMAT_DESCRIPTION_EVENT 统称为描述符事件)—— 用来描述binlog文件格式版本(用来写events到日志文件的格式)。
    • 随后的一系列events需要依照 descriptor event 提供的 format version 来解析。
    • 最后的event是 ROTATE_EVENT (日志轮转事件, 当MySQL服务切换到一个新的日志文件时发生,由server重启、flush logs 或日志大小到达阈值触发,用来指定下一个binlog的文件名。)

查看binlog文件内容


由于binlog的文件内容是二进制的,如果直接通过文本工具去查看,那是很费力的,MySQL提供了binlog解析工具 mysqlbinlog , 参考链接:dev.mysql.com/doc/refman/…

尤其注意,当 binlog-format 是 Row-based时,events的data bytes部分被使用base-64编码,你可以通过增加参数--base64-output=DECODE-ROWS 来解码查看(其实是告诉server引擎不使用BINLOG语句来编码)

binlog的核心其实就是记录在日志文件中的,各种各样的events,所以我们也可以使用SQL语句 —— SHOW BINLOG EVENTS IN 'filename' ,直接查看binary log文件中的events列表 在这里插入图片描述 SHOW BINLOG EVENTS 在日志文件中的每个event都展示出如下几个字段:

  • Log_name —— 文件名
  • Pos —— event 起始位置
  • Event_type —— 事件类型描述,参考链接:
  • Server_id —— 事件发生的MySQL server实例标识
  • End_log_pos —— event 结束位置,等于Pos + event bytes length
  • Info —— 关于event type 的更多详细信息,信息的格式取决于event type

对于压缩的事务负载,Transaction_payload_event 首先被单独打印出来,然后解压并一一打印负载中的每个event。

下一篇:《深入MySQL(二)—— 深入理解binlog event 与解析原理》

关注作者公众号,随时了解更多干货!


在这里插入图片描述

往期推荐