问题是这样的,目前有个应用,平时没有问题,但极少数情况下会抛出数据库死锁的异常,我怀疑有可能是并发操作的时候出现,检查之后定位到这一段执行update的语句,请帮忙看看,有没有可能导致死锁
调用这个方法的是methodA,methodA中先把Autocommit设为false,然后循环调用executeUpdate(String sql),因为可能会有多条sql需要执行,最后commit,再回复Autocommit为true
executeUpdate(String sql)的代码如下
[code="java"]
public int executeUpdate(String sql) throws SQLException {
//LogUtil.getLogger().debug("SQL [" + sql + "]");
stmt = conn.createStatement();
int count = stmt.executeUpdate(sql);
if(stmt != null){
stmt.close();
}
return count;
}
[/code]
有个需要说明的是methodA和executeUpdate都在同一个类中,Connection conn和Statement stmt都是全局的,会不会是stmt创建的时候出的问题,是否需要加上synchronized
我说错了,加上synchronized就可以了
数据库有一个默认的事务级别,像PostGreSQL的默认级别是Read_Committed。像你这样的写法,如果有多条语句同时对行A进行修改:
SQL1:Update A 这时还没有Commit,所有A有行级锁
SQL2:Update A SQL2是无法被修改的,因为A有行级锁
你这种情况加synchronized是没用的。
stmt = conn.createStatement();
int count = stmt.executeUpdate(sql);
if(stmt != null){
stmt.close();
}
你在Commit前不要去执行stmt.close(); 语句。
给你几个解决方法。
1.死锁发生时查询数据库分析死锁具体原因.
2.记录日志知道死锁具体位置.
3.进行数据库操作时设定超时时间,避免等待。
数据库对于这种情况的死锁是能自己发现的,然后退出一个