最近两天晚上,手机老收到报警信息,mysql从库断了,不知道什么原因,主库没问题,从库断了,从库上我们也没做任何修改操作。最后通过日志和询问同时,发现从库中有条这样的sql,insert into b.b1 select from a.a1,这条语句刚开我也以为对从库同步没啥影响,因为只是查询么,但是感觉确实再没其它问题了,通过发帖以及询问公司同事,终于明白了,记录一下
insert into b.b1 as select * from a.a1 会锁住 a1 表,阻塞 a1 表上的写操作,如果 slave sql 线程等待锁的时间超过 innodb_lock_wait_timeout 的话,就会报 Error_code: 1205 错误,并重启事务。
如果重启事务的次数超过了 slave_transaction_retries,复制就中断了。
也可以尝试加大 slave_transaction_retries 的值,或者在 insert into b.b1 as select * from a.a1 前 stop slave,等insert 完成以后再 start slave。
具体原因主要是为了mysql为了保证binlog的一致性,
在 binlog_format = ‘MIXED‘ 或者 ‘STATEMENT‘ 的时候,binlog 里面保存的是 sql 语句,按事务的提交顺序排列。
如果 insert into b.b1 as select * from a.a1 的时候不锁住 a1 表,但同时执行了 update a1 的操作并在 insert 之前提交的话,在 binlog 里 update 就会在 insert 之前,slave 或者数据库恢复的时候使用了这样的 binlog 就会产生和实际不一致的结果。