昨天一同学说在slave上出现Waiting for table metadata lock,metadata lock在5.5版本新加的(http://dev.mysql.com/doc/refman/5.5/en/metadata-locking.html)。metadata lock出现最多情况是一个事务中在t表进行DML时,另外一事务想对t表DDL,这时对t表DDL的事务只能等待,就会出现metadata,就是为了保护表的metadata。
出问题的备库上在跑mysqldump备份数据(参数有–single-transaction),一同学在主库drop table操作,导致备库一直hang住(备库延迟),show processlist就可以看到metadata lock。为什么mysqldump会对表加metadata lock的?
Mysqldump代码(5.5版本,5.1版本有点区别)
1、 if->flush tables成功,do->flush tables with read lock
2、 start transaction
3、 unlock tables
4、 backup(一个表一个表加metadata lock)
模拟mysqldump过程:
Session 1:
Session 2:
session 3:
Session 1:
Session 3:
从上面测试可以知道,mysqldump是备份到哪个表,锁到哪个表。这里有产生一个新的问题:
Session I:
Mysqldump未备份到b表
Session II:
写操作记录到binlog中
drop table b,实际在mysqldump备份集里是没有b表的
当恢复时,因为要apply 写b表的binlog,但备份集恢复后根本就没有b表,所以会报表找不到表,这个在我们线上环境已出现。
总结:因为5.1没有metadata lock,所以出现几率会更大,5.5已改进扫到哪里加锁到哪里。
转自:http://www.dbunix.com/?p=3217