文章目录
binlog(二进制日志文件)用于记录数据库执行的写入性操作(不包括查询select,展示show)信息,以二进制的形式保存在磁盘中
。【逻辑日志】
binlog
是通过追加的方式进行写入的,可以通过max_binlog_size
参数设置每个binlog
文件的大小,当文件大小达到给定值之后,会生成新的文件来保存日志。
1. binlog
使用场景
- 主从复制:在
Master
端开启binlog
,然后将binlog
发送到各个Slave
端,Slave
端接受binlog
从而达到主从数据一致。 - 数据恢复:通过使用
mysqlbinlog
工具来恢复数据(用于数据库的基于时间点的还原)。
2. binlog
日志记录的内容和产生释放时机
binlog
日志记录的内容:逻辑格式的日志,可以简单的认为是执行过的事务中的sql
语句。但又不完全是sql
语句这么简单,而是包括了执行的sql
语句(增删改)反向的信息,也就意味着delete
对应着delete
本身和其反向的insert
;update
对应着update
执行前后的版本的信息;insert
对应着delete
和insert
本身的信息。
什么时候产生:
事务提交的时候,一次性将事务中的sql
语句(一个事物可能对应多个sql语句)按照一定的格式记录到binlog
中。
什么时候释放:
binlog
的默认保持时间由参数expire_logs_days
配置,也就是说对于非活动的日志文件,在生成时间超过expire_logs_days
配置的天数之后,会被自动删除。
3. binlog
日志格式
mysql> delete from t where a>=4 and t_modified <= '2018-11-10' limit 1;
-
STATMENT
:基于SQL
语句的复制(statement-based replication,SBR
),每一条会修改数据的sql
语句会记录到binlog
中。binlog 里面记录的就是 SQL 语句的原文
优点:不需要记录每一行的变化,减少了
binlog
日志量,节约了IO
, 从而提高了性能;
缺点:在某些情况下会导致主从数据不一致,比如执行sysdate()、sleep()
等。 -
ROW
:基于行的复制(row-based replication, RBR
),不记录每条sql
语句的上下文信息,仅需记录哪条数据被修改了。binlog 里面记录了真实删除行的主键 id
图中没有办法看到详细信息,还需要借助mysqlbinlog
,这个事务的binlog
是从 8900
这个位置开始的,所以可以用start-position
参数来指定从这个位置的日志开始解析。
mysqlbinlog -vv data/master.000001 --start-position=8900;
优点:不会出现某些特定情况下的存储过程、或
function
、或trigger
的调用和触发无法被正确复制的问题;
缺点:会产生大量的日志,尤其是alter table
的时候会让日志暴涨
MIXED
:基于STATMENT
和ROW
两种模式的混合复制(mixed-based replication, MBR
),一般的复制使用STATEMENT
模式保存binlog
,对于STATEMENT
模式无法复制的操作使用ROW
模式保存binlog
在
MySQL 5.7.7
之前,默认的格式是STATEMENT
,MySQL 5.7.7
之后,默认值是ROW
。日志格式通过binlog-format
指定。
3.1 为什么会有 mixed
格式的 binlog
?
因为有些 statement
格式的 binlog
可能会导致主备不一致,所以要使用 row
格式。
但 row
格式的缺点是,很占空间。比如你用一个 delete
语句删掉 10 万行数据,用
statement
的话就是一个 SQL
语句被记录到 binlog
中,占用几十个字节的空间。但如
果用 row
格式的 binlog
,就要把这 10 万条记录都写到 binlog
中。这样做,不仅会占
用更大的空间,同时写 binlog
也要耗费 IO 资源,影响执行速度。
所以,MySQL
就取了个折中方案,也就是有了 mixed
格式的 binlog
。mixed
格式的意
思是,MySQL
自己会判断这条 SQL
语句是否可能引起主备不一致,如果有可能,就用
row
格式,否则就用 statement
格式
4. binlog
的写入机制(sync_binlog
)
binlog
的写入逻辑:
事务执行过程中,先把日志写到 binlog cache
,事务提交的时候,再把 binlog cache
写到 binlog
文件中。
一个事务的 binlog
是不能被拆开的,因此不论这个事务多大,也要确保一次性写入。这就涉及到了 binlog cache
的保存问题。
系统给 binlog cache
分配了一片内存,每个线程一个,参数 binlog_cache_size
用于控制单个线程内 binlog cache
所占内存的大小。如果超过了这个参数规定的大小,就要暂存到磁盘。
事务提交的时候,执行器把 binlog cache
里的完整事务写入到 binlog
中,并清空 binlog cache
。
每个线程有自己 binlog cache
,但是共用同一份 binlog
文件。
binlog
提交的过程包含了 write
和 fsync
两个步骤:
write
:指的就是指把日志写入到文件系统的page cache
,并没有把数据持久化到磁盘,所以速度比较快。
fsync
:是将数据持久化到磁盘的操作。一般情况下,我们认为fsync
才占磁盘的IOPS
。
write
和 fsync
的时机,是由参数 sync_binlog
控制的:
sync_binlog=0
的时候,表示每次提交事务都只write
,不fsync
;sync_binlog=1
的时候,表示每次提交事务都会执行fsync
;sync_binlog=N(N>1)
的时候,表示每次提交事务都write
,但累积N
个事务后才fsync
。(如果主机发生异常重启,会丢失最近N
个事务的binlog
日志。)
来源地址:https://blog.csdn.net/weixin_45683550/article/details/128763401