道歉的愚蠢的标题,但问题是一个真正的人,即使它不是一个新的事情。模式的升级在Galera不是一个普通的操作。为主题,底线是:在默认值总订单隔离(钢铁洪流)方法。”集群复制模式改变查询语句之前执行”。这意味着在实践中是一个DDL发布在一个节点复制到集群中的其他节点之前,甚至在源节点执行,更不用说成功完成。
结果,它在一个节点可能会失败,是成功的另一个,这在不提高大声警告或停止节点来防止数据不一致。这不是错误本身,而是一种妥协的设计。在MySQL和新变化最近支持原子ddl添加在version 8.0中,我们可以看到在这方面改善随着时间的推移Galera。目前,警告应该维护:在Galera ddl不是原子操作,即使在8.0。
这是多大的问题?
公平地说,这是罕见的,我们不经常看到这种情况的发生。
问题体现在实践中如何?给我们一个例子!
我们最近调查了DBA发布情况截断表声明一个节点,采取一些时间来完成。他当时的反应Ctrl + C在会话的DDL。会话似乎挂,所以他最终打开一个新会话和发布一个完整的删除在相同的表。它也需要花费大量时间来完成,然而这一次,他更有耐心。问题是:一旦声明完成后,他注意到另外两个节点从集群中消失了。在仔细检查日志,两个节点集群驱逐前报告以下错误:
|
1
|
(
错误
]
奴隶
SQL
:
可以
不
执行
Delete_rows
事件
在
表
mydb
.target
;
可以
“t找到记录”
目标”,
Error_code
:
1032年
;
处理程序
错误
HA_ERR_KEY_NOT_FOUND
;
的
事件”年代
主
日志
第一个
,
end_log_pos
1073年
,
Error_code
:
1032年
|
的删除是成功的源节点,但未能完成另外两个节点上。为什么?因为目标表已经空:前面截断表在这些节点有效执行。
不是截断表也成功的在源节点上?原来不是。事实上,截断慢速查询日志的记录源节点是这样的:
|
1
2
3
4
5
6
7
8
9
10
|
#时间:(…)
#用户(…)
#模式:构建Last_errno: 1317人死亡:0
145.753247 # Query_time: Lock_time: 0.000000 Rows_sent: 0 Rows_examined: 0 Rows_affected: 0
# Bytes_sent: 44 Tmp_tables: 0 Tmp_disk_tables: 0 Tmp_table_sizes: 0
# QC_Hit:没有Full_scan: Full_join:没有Tmp_table:没有Tmp_table_on_disk:没有
# Filesort:没有Filesort_on_disk: Merge_passes: 0
#没有InnoDB统计查询
集
时间戳=(
。
。
。
)
截断
目标
;
|
注意Last_errno上面显示:
|
1
2
|
美元
perror
1317年
MySQL
错误
代码
1317年
(
ER_QUERY_INTERRUPTED
)
:
查询
执行
是
打断了
|
我们的同事Przemek复制一个类似的问题,他所描述的错误pxc - 3536:修改/查询处理不允许线程被杀,如果线程在钢铁洪流。Perc雷竞技下载官网ona工程团队已经固定的堕胎问题,离开后注意bug追踪器:
固定在5.7(.33 - 31.49)和8.0 (22 - 13.1)。任何试图杀死查询或连接在钢铁洪流将失败。注意,由于时间的原因,“杀死查询”有时可能会返回成功,但操作仍然会成功。
在我们调查中,MySQL源节点有答案的错误日志;有一些其他高优先级事务已经到位,节点上,阻止它执行截断:
|
1
|
(
请注意
]
WSREP
:
MDL
冲突
db=mydb
表=目标
票=MDL_SHARED_WRITE
解决了
通过
中止
|
澄清一下,这个集群从多个节点接收写道,和高优先级事务被复制线程应用,通常优先于当地当检测到冲突事件。
你可能会怀疑,截断不存在的二进制日志源节点;自声明没有完成,这不是记录。只有后续删除声明。
至于其他两个节点的二进制日志,他们包括了截断以及删除覆盖的所有行目标表。行这些不再有其他节点,因此无法删除后的数据不一致造成的。






