为事务编写代码的正确方法是什么?

时间:2014-12-13 20:50:29

标签: java mysql multithreading transactions deadlock

当从多个线程或进程执行到同一数据库和表的事务时,它是自定义的,以期望出现类型错误:

  

超过锁定等待超时;尝试重新启动交易

来自MySQL?
我的理解是,这并不表示因为昂贵的操作而导致阻塞的情况也会出现僵局 在我的例子中,我注意到代码结构如下:

BEGIN  
DELETE FROM TableA where pk = X  
DELETE FROM TableC where colA = X  
DELETE FROM TableD where colA = X  
DELETE FROM TableE where colA = X  
DELETE FROM TableF where colA = X  
COMMIT  

对于更多上下文,我想从这些表中删除,以便更快地通过分配批量PK而不是通过单个线程顺序执行来分离多个线程中的删除。 所以基本上我可以告诉他们没有死锁(如果我错了请纠正我) 所以我认为这个问题是其中一个线程被阻止了太长时间试图删除 似乎(根据错误消息)我会在应用程序级别中处理这种情况 所以我的问题是:当编写执行事务的代码时,通常需要预期这样的错误,例如等待几秒钟并重试事务几次然后可能放弃?
我不确定这是否是人们通常如何编写交易代码 (注意:我正在标记为Java,虽然它不是Java问题,因为它是我的首选语言)。

1 个答案:

答案 0 :(得分:1)

你是正确的 - 这与死锁不是一回事。

请参阅http://dev.mysql.com/doc/refman/5.6/en/innodb-parameters.html#sysvar_innodb_lock_wait_timeout

innodb_lock_wait_timeout系统变量决定InnoDB在放弃之前等待获取行锁的时间。

您的多个线程很可能不得不相互等待,因此在这种情况下,您可能会重新考虑多线程是否是您尝试完成的有用方法。

通常情况下,这些错误是应用程序中出现问题的迹象,因为如果行被锁定这么长时间通常会出现问题 - 交易操作中的最佳做法是进入,完成工作,以及尽快再次出去(提交或回滚)。显然,当对大量行进行操作时,这是不可能的,因此锁等待变得更有可能,因为需要相同的独占行或索引锁的其他事务必须等待。