【MySQL】5.6/5.7并行复制bug导致的故障 ERROR 1755/1756
发表于:2025-02-23 作者:千家信息网编辑
千家信息网最后更新 2025年02月23日,最近做了很多组基于并行复制(MTS)的主从,其中大多数为5.6->5.7的结构,少部分5.6->5.6的并行复制。每组m-s结构配置相近,有一定几率出现如下错误,但不是全部出现:〇 ERROR 175
千家信息网最后更新 2025年02月23日【MySQL】5.6/5.7并行复制bug导致的故障 ERROR 1755/1756最近做了很多组基于并行复制(MTS)的主从,其中大多数为5.6->5.7的结构,少部分5.6->5.6的并行复制。
每组m-s结构配置相近,有一定几率出现如下错误,但不是全部出现:
〇 ERROR 1755:
错误场景:
Master(5.6) -> Slave(5.6/5.7)
相关配置:
Slave开启并行复制:
slave_parallel_workers>=1。
Slave报错信息:(此处是5.7的Slave,5.6也类似,但reason会有不同)
错误提示很明显:
Cannot execute the current event group in the parallel mode
不能在parallel模式下执行目前的这个event组
在5.6作为slave也有可能遇到这个问题。
错误提示和原因显示很明白,关掉并行复制就可以了:
同样是1755报错,目前收集到日志中可能给出的reason有下面三个:
总结一下原因可以是:
在5.6老版本->5.6新版本/5.7的复制结构下,master的event没有记录并行复制的相关信息。
在Slave为5.6和5.7下均有出现的可能,已经被认作是个BUG,可以参考:
https://bugs.mysql.com/bug.php?id=71495
https://bugs.mysql.com/bug.php?id=72537
〇 ERROR 1756
错误场景:
Master(5.6) -> Slave(5.7)
相关配置:
Slave开启并行复制:
slave_parallel_workers>=1。
slave_parallel_type='LOGICAL_CLOCK'。
与1755不同的是,出现1756错误的可能性似乎更多。
Slave报错信息:
Slave的复制分发对象被为"logical_clock",但5.6是仅支持"database"粒度的并行复制。
那么为什么5.7使用基于logical_clock的就会出现这个问题呢?
因为在5.7的binlog event中,新增了"last_committed"和"sequence_number"
前者表示事务提交时,上次提交的事务编号,若事务具有相同的last_committed,则表明这些事务在同一个组内,可以并行进行apply
这两个的出现,也是5.7新增基于logical_clock进行并行复制的基础。
无论在开启GTID还是关闭GTID的情况下,都会有对应信息的产生。
在5.7源码中,MYSQL_BIN_LOG定义了两个Logical_clock的变量:
transaction_counter:记录当前组提交中各事务的logical_clock,即sequence_number。
而5.6所产生的binlog是没有这些记录的,作为slave的5.7自然无法基于logical_clock进行并行复制。
这种情况下,修正该问题就好说了:
不幸的是,1756错误发生不止这一种原因。
更多可以参考:
https://bugs.mysql.com/bug.php?id=69369
https://bugs.mysql.com/bug.php?id=77239
………………
其中一个比较有趣的是,MHA作者Yoshinori Matsunobu也遇到了ERROR 1756:
https://bugs.mysql.com/bug.php?id=68465
其原因是并行复制并不支持"slave_transaction_retries"
他在rpl_slave.cc发现了该描述:
----
/* MTS technical limitation no support of trans retry */
if (mi->rli->opt_slave_parallel_workers != 0 && slave_trans_retries != 0
复现操作:
1.将slave_transaction_retries设置为一个较高的值
2.开启并行复制:slave_parallel_workers>=0
3.在slave上,对t1表持有一个较长时间的InnoDB锁,比如BEGIN; UPDATE t1 SET a=100;
4.在master上执行一个冲突的语句并提交传输到slave上,比如UPDATE t1 SET a=100 WHERE id=1;
这个bug所造成的ERROR 1756已经在5.7.5被修复。
关于ERROR 1755/1756总结一下:
避免跨版本的并行复制。
升级到5.6.x的更高版本,避免使用老版本5.6的并行复制。
升级到5.7.x的更高版本,避免使用老版本5.7。
〇 参考文档
MySQL 5.7并行复制实现原理与调优 by 姜承尧
从MySQL 5.6到5.7复制错误解决 by 佚名
https://bugs.mysql.com/
每组m-s结构配置相近,有一定几率出现如下错误,但不是全部出现:
〇 ERROR 1755:
错误场景:
Master(5.6) -> Slave(5.6/5.7)
相关配置:
Slave开启并行复制:
slave_parallel_workers>=1。
Slave报错信息:(此处是5.7的Slave,5.6也类似,但reason会有不同)
- ……
- Slave_IO_Running: Yes
- Slave_SQL_Running: No
- ……
- Last_Errno: 1755
- Last_Error: Cannot execute the current event group in the parallel mode. Encountered event Gtid, relay-log name {目录}/relaylog/mysql-relay.000002, position 280408 which prevents execution of this event group in parallel mode. Reason: The master event is logically timestamped incorrectly..
- ……
- Last_IO_Errno: 0
- Last_IO_Error:
- Last_SQL_Errno: 1755
- Last_SQL_Error: Cannot execute the current event group in the parallel mode. Encountered event Gtid, relay-log name {目录}/relaylog/mysql-relay.000002, position 280408 which prevents execution of this event group in parallel mode. Reason: The master event is logically timestamped incorrectly..
- Replicate_Ignore_Server_Ids:
- ……
错误提示很明显:
Cannot execute the current event group in the parallel mode
不能在parallel模式下执行目前的这个event组
在5.6作为slave也有可能遇到这个问题。
错误提示和原因显示很明白,关掉并行复制就可以了:
- STOP SLAVE;
- SET GLOBAL slave_parallel_workers=0;
- START SLAVE;
同样是1755报错,目前收集到日志中可能给出的reason有下面三个:
- ① Reason:The master event is logically timestamped incorrectly(这个可能也和在5.7上设置slave_parallel_type="LOGICAL_CLOCK"有关)
- ② Reason: possible malformed group of events from an old master
- ③ Reason:the events is a part of a group that is unsupported in the parallel execution mode.
总结一下原因可以是:
在5.6老版本->5.6新版本/5.7的复制结构下,master的event没有记录并行复制的相关信息。
在Slave为5.6和5.7下均有出现的可能,已经被认作是个BUG,可以参考:
https://bugs.mysql.com/bug.php?id=71495
https://bugs.mysql.com/bug.php?id=72537
〇 ERROR 1756
错误场景:
Master(5.6) -> Slave(5.7)
相关配置:
Slave开启并行复制:
slave_parallel_workers>=1。
slave_parallel_type='LOGICAL_CLOCK'。
与1755不同的是,出现1756错误的可能性似乎更多。
Slave报错信息:
- ……
- Slave_IO_Running: Yes
- Slave_SQL_Running: No
- ……
- Last_Errno: 1756
- Last_Error: … The slave coordinator and worker threads are stopped, possibly leaving data in inconsistent state. A restart should restore consistency automatically, although using non-transactional storage for data or info tables or DDL queries could lead to problems. In such cases you have to examine your data (see documentation for details).
- ……
- Last_SQL_Errno: 1756
- Last_SQL_Error: … The slave coordinator and worker threads are stopped, possibly leaving data in inconsistent state. A restart should restore consistency automatically, although using non-transactional storage for data or info tables or DDL queries could lead to problems. In such cases you have to examine your data (see documentation for details).
- ……
Slave的复制分发对象被为"logical_clock",但5.6是仅支持"database"粒度的并行复制。
那么为什么5.7使用基于logical_clock的就会出现这个问题呢?
因为在5.7的binlog event中,新增了"last_committed"和"sequence_number"
前者表示事务提交时,上次提交的事务编号,若事务具有相同的last_committed,则表明这些事务在同一个组内,可以并行进行apply
这两个的出现,也是5.7新增基于logical_clock进行并行复制的基础。
无论在开启GTID还是关闭GTID的情况下,都会有对应信息的产生。
在5.7源码中,MYSQL_BIN_LOG定义了两个Logical_clock的变量:
- class MYSQL_BIN_LOG: public TC_LOG
- {
- ...
- public:
- /* Committed transactions timestamp */
- Logical_clock max_committed_transaction;
- /* "Prepared" transactions timestamp */
- Logical_clock transaction_counter;
- ...
transaction_counter:记录当前组提交中各事务的logical_clock,即sequence_number。
而5.6所产生的binlog是没有这些记录的,作为slave的5.7自然无法基于logical_clock进行并行复制。
这种情况下,修正该问题就好说了:
- STOP SLAVE;
- SET GLOBAL slave_parallel_type="DATABASE";
- START SLAVE;
不幸的是,1756错误发生不止这一种原因。
更多可以参考:
https://bugs.mysql.com/bug.php?id=69369
https://bugs.mysql.com/bug.php?id=77239
………………
其中一个比较有趣的是,MHA作者Yoshinori Matsunobu也遇到了ERROR 1756:
https://bugs.mysql.com/bug.php?id=68465
其原因是并行复制并不支持"slave_transaction_retries"
他在rpl_slave.cc发现了该描述:
----
/* MTS technical limitation no support of trans retry */
if (mi->rli->opt_slave_parallel_workers != 0 && slave_trans_retries != 0
复现操作:
1.将slave_transaction_retries设置为一个较高的值
2.开启并行复制:slave_parallel_workers>=0
3.在slave上,对t1表持有一个较长时间的InnoDB锁,比如BEGIN; UPDATE t1 SET a=100;
4.在master上执行一个冲突的语句并提交传输到slave上,比如UPDATE t1 SET a=100 WHERE id=1;
这个bug所造成的ERROR 1756已经在5.7.5被修复。
关于ERROR 1755/1756总结一下:
避免跨版本的并行复制。
升级到5.6.x的更高版本,避免使用老版本5.6的并行复制。
升级到5.7.x的更高版本,避免使用老版本5.7。
〇 参考文档
MySQL 5.7并行复制实现原理与调优 by 姜承尧
从MySQL 5.6到5.7复制错误解决 by 佚名
https://bugs.mysql.com/
错误
事务
版本
原因
信息
结构
问题
参考
配置
不同
两个
场景
情况
更多
目录
升级
提示
支持
好说
明显
数据库的安全要保护哪些东西
数据库安全各自的含义是什么
生产安全数据库录入
数据库的安全性及管理
数据库安全策略包含哪些
海淀数据库安全审计系统
建立农村房屋安全信息数据库
易用的数据库客户端支持安全管理
连接数据库失败ssl安全错误
数据库的锁怎样保障安全
查询把数据库宕机
阿里云 读数据库超载
中国白银交易软件开发
麒麟服务器 单用户
打电话提示服务器被锁定
服务器安全狗漏洞失败
服务器安全防御教程
软件开发学校湖南
软件开发哪个阶段最耗时间
神舟十二号软件开发
增城电力系统软件开发
北京市网络安全总队电话
虚拟专用网络技术的工作原理
网络安全警察工作忙
欧盟5g网络安全问题
学软件开发一般面向哪些企业
数据库批号id
最好用的手机软件开发
数据库无法读取内存
鸿蒙软件开发难度
国家网络安全周主题班会教案
自建设服务器安全吗
睿达互联网科技公司
网络安全风险责任书
软件开发实验总结范文
网络安全建议的答复网信办
健康码演示软件开发者
网络安全警察工作忙
医学数据库基础知识
阿里云rds数据库开放端口