最近为了提升日志入库的速度,把入库的代码改为并发的。发现部分日志入库的时候mysql报错:mysql
Error 1213: Deadlock found when trying to get lock; try restarting transaction.
字面意思可见是有死锁了。sql
出现死锁,首先查询状态日志,mysql执行:并发
SHOW ENGINE INNODB STATUS
查询LATEST DETECTED DEADLOCK标签下的日志,可见最近一次发生死锁的语句。再加上对比正常执行的sql语句,问题定位在使用replace into上。rest
innodb是行级锁,而我是并发且批量去使用replace into去更新表,很容易形成同时两条语句去更新一行数据。replace的时候会给要更新的行加上排他锁(X锁),这就是形成死锁的缘由。(有惟一索引的表在insert的时候,若是发生了惟一索引冲突,会加上读锁(S锁),理论上在并发处理的时候不会死锁?待证明)。日志