问题描述
最近做了一个项目框架是Spring+Hibernate+Webwork,数据库是MySQL。用到了Quartz。这个job继承QuartzJobBean,直接使用DAO层。 项目每10分钟运行一次,中间有个for循环,循环内部有个DAO的Update操作。 结果发现有个很严重的问题,job正常运行一段时间后,Update操作多次后,某个循环中,程序运到Update操作就不动了,像假死一样。 请求指点,谢谢。JOB中的部分的代码protected void executeInternal(JobExecutionContext arg0) throws JobExecutionException { for (int i = 0; i < 1000; i++) { abcDAO.update("update table set a=1"); }}DAO中的代码public class AbcDAO extends HibernateDaoSupport { public void update(String hql) { Session session = null; try { session = (Session) getSession(); if (session.isOpen()) { System.out.println("session is Open"); } if (session.isConnected()) { System.out.println("session is Connected"); } session.createQuery(hql).executeUpdate(); } catch (Exception e) { logger.error("sql操作失败 : " + e.getMessage()); } finally { releaseSession(session); } }}上面代码测试的过程中,在DAO代码第12行处假死的,但是假死之前session is Open和session is Connected。请大家指点,谢谢!问题补充:回答jones:下面是show processlist的结果Id User Host db Command Time State Info 97 root localhost:3803 information_schema Query 0 <NULL> show processlist 99 root localhost:3810 collection Sleep 329 <NULL> 100 root localhost:3817 collection Sleep 170 <NULL> 101 root localhost:3823 collection Sleep 86 <NULL> DEBUG日志看了之后,没有发现什么特别的异常。请问你能帮忙看看是什么原因吗?谢谢你
解决方案
1.假死后用show processlist命令观察mysql情况2.log4j日志级别DEBUG后看hibernate日志停到哪里
解决方案二:
很想看看releaseSession做了哪些事情。貌似没有flush,to jones终结函数是指Object类的finlize方法,不是finally块,finally块不管try块还是catch块有异常抛出来,都会被执行。
解决方案三:
顺便说句,DAO写法有问题,不建议直接操作session,如果必须,最好放到Callback中,在finally中释放session也不建议,见《Effective java》中对finally的论述:“终结函数并不能保证会被及时的执行,从一个对象变得不可到达开始,到终结函数被执行,这段时间的长度是任意的、不确定的”