我想解决的基本问题是运行一个在MySQL中生成几个临时表的任务,这些表需要保持足够长的时间以便在创建Java后从Java中获取结果.由于涉及的数据大小,任务必须分批完成.每个批处理都是对通过JDBC调用的存储过程的调用.对于大型数据集,整个过程可能需要半小时或更长时间.
为了确保访问临时表,我在一个带有TransactionCallbackWithoutResult的Spring事务中运行整个任务,从头到尾完成.否则,我可以得到一个不能访问临时表的不同连接(这会在我将事务包装在事务中之前偶尔发生).
这在我的开发环境中运行良好.但是,在生产中我遇到以下异常:
java.sql.SQLException: Lock wait timeout exceeded; try restarting transaction
Run Code Online (Sandbox Code Playgroud)
当一个不同的任务试图在执行长时间运行的事务期间访问某些相同的表时,就会发生这种情况.令我困惑的是长时间运行的事务只插入或更新到临时表中.对非临时表的所有访问都是仅选择.从我可以找到的文档中,默认的Spring事务隔离级别不应该导致MySQL在这种情况下阻塞.
所以我的第一个问题是,这是正确的方法吗?我是否可以确保在没有长时间运行的事务的情况下通过Hibernate模板重复获得相同的连接?
如果长时间运行的事务方法是正确的,那么我应该检查隔离级别?我的理解是正确的,Spring/MySQL事务中的默认隔离级别不应该锁定只能通过选择访问的表吗?我该怎么做才能调试哪些表导致冲突,并防止这些表被事务锁定?