我理解为死锁,也许并不准确,因为我在spring和hibernate中间又加了jpa!
之前使用了OpenSessionInView模式,在网上看到一篇帖子说使用该模式会造成死锁,果断去掉,还是不行!
但是问题应该已经改善了!(控制台信息提示不同了)
http://blog.sina.com.cn/s/blog_53923f940100g6as.html
后来发现:
<prop key="hibernate.connection.release_mode">after_statement</prop>
唉!不懂是此属性值默认是on_close,就是session.close();时关闭连接,但我在调用这查询时,使用手动session.close();
果断使用,发现直接报异常!
怀疑是jpa的原因,果断去掉,还是报错!
继续百度:
先看看SessionFactory.getCurrentSession与openSession的区别
1. 如果使用的是getCurrentSession来创建session的话,在commit后,session就自动被关闭了,
也就是不用再session.close()了。但是如果使用的是openSession方法创建的session的话,
那么必须显示的关闭session,也就是调用session.close()方法。这样commit后,session并没有关闭
/*2. getCurrentSession的使用可以参见hibernate\hibernate-3.2\doc\tutorial\src项目
3. 使用SessionFactory.getCurrentSession()需要在hibernate.cfg.xml中如下配置:
* 如果采用jdbc独立引用程序配置如下:
<property name="hibernate.current_session_context_class">thread</property>
* 如果采用了JTA事务配置如下
<property name="hibernate.current_session_context_class">jta</property>*/
开始用的:
Session session = this.getHibernateTemplate().getSessionFactory().getCurrentSession();
Transaction tran=session.beginTransaction();
好多文章里都说只需在Spring配置<bean id="sessionFactory"...---><property name="hibernateProperties"> 中加入 <prop key="hibernate.current_session_context_class">thread</prop>就可以解决,试了没用.
修改后的:
Session session = this.getHibernateTemplate().getSessionFactory().openSession();
Transaction tran=session.beginTransaction();
......
finally
{
session.close();
}
-----------------------------------------------
他的问题解决,我得问题变了:org.hibernate.event.internal.AbstractFlushingEventListener - Post flush
继续百度:
这个是hibernate与spring整合开发,让DAO继承了spring的HibernateDaoSupport,这样的确能够提高开发效率 ,但是不够灵活,而且使DAO层依赖于spring的api,增加了耦合。但是不考虑复用的话还可以。
下面一个一个的分析: this.getsession实际上是调用了父类中的方法获得session。使用spring管理hibernate的SessionFactory的时候,这个方法会从session池中拿出一session.这样做有可能有问题,就是超session池连接数的时候,spring无法自动的关闭session。 不推荐使用
this.getHibernateTemplate().getSessionFactory().getCurrentSession()从spring管理的sessionFactory中创建一个绑定线程的session.spring会根据该线程的执行情况来自动判断是关闭session还是延迟关闭。这样做可以避免手动的管理实务,同时一个线程最多开启和关闭一次session又可以提高程序的性能。 极力推荐使用这种方法
this.getHibernateTemplate().getSessionFactory().OpenSession。这种方法从spring管理的sessionFactory中创建一个session,此session不是线程绑定的。当执行完一个实务的时候自动关闭session.这种方法不用手动管理实务,但是同一个线程多次的开启和关闭session,浪费系统资源和影响执行效率,正常情况下还是不要用了。
更换成this.getHibernateTemplate().getSessionFactory().getCurrentSession()这种方式的,但是我直接改成:
@Service("pgisDao")
public class PgisDaoImpl extends HibernateDaoSupport implements PgisDao{
@Override
public void insertPgis(Pgis pgis) {
super.getHibernateTemplate().save(pgis);
}
}
<bean id="pgisDao" class="com.clb.pgis.dao.impl.PgisDaoImpl">
<property name="sessionFactory" ref="sessionFactory"></property>
</bean>
去掉了基础dao,将sessionFactory显示的注入到了pgisDao中,发现不好使,仔细一看貌似底层还是老一套,怒了自己写了下:
@Override
public void insertPgis(Pgis pgis) {
Session session = super.getHibernateTemplate().getSessionFactory().getCurrentSession();
session.save(pgis);
}
终于好使了!
----------------------------------
其实并没有好使,好大喜功了!
各种研究就是不行,最后都换了BoneCP还是不好使,跑个2-3分钟就假死了,
临下班急眼了,把myeclipse关了,直接tomcat starup试试,竟然不假死了,万恶的myeclipse啊,其实还是自己经验不足,早该想到myeclipse有自己的运行参数,以为在里面启动tomcat会用tomcat的参数,是不可能在这出问题的!