在面对级联关联(one-to-many......)查询的时候,你是怎么解决hibernate session关闭的?我是这样做的。

来源:互联网 发布:4钻淘宝店铺转让价格 编辑:程序博客网 时间:2024/04/30 20:48

For management of hibernate session,there are two solution that are added openSessionInViewFilter in webapp, or add intercepter in Spring framework,I don't think the openSessionInViewFilter is a best way.
By HibernateDAOSupport supplied from Spring, when user try to get the sub Object from father-object,it always happen a error shown that the Session has been closed yet in current Operation.For this case happen so freqeentyl. I think that the best way is write the code in our service tier without any hibernate smart feature anymore.

 

hibernate的session问题,我发现当使用了对象里的高级特性,比如说one-to-many, many-to-one,当使用lazy=true的时候,在尝试去get主表里的collection的时候,告诉session已经关闭。从网上看来,很多人遇到这样的问题,一般的解决方案是在web层增加一个Filter,管理session的周期,一般的做法是拉长周期,是一次处理期间session一直open,而不是spring所默认的那种,当线程离开service层就关闭。但是这样也会带来很多问题。是single的一个session还是多个?假如是多个,web复杂环境情况,在处理并发的时候,会遇到速度慢的问题。

假如使用多个session--即singleSession =false,那样的话,并发量大的时候,session可能占用太多。不太安全。当然我认为这个配置比singleSession =true那种在性能上要好很多。

 

后来发现三个办法:

一个是最低端的做法,抛弃hibernate的关联配置---即 one-to-many, many-to-one等。自己在dao里写hql或者sql来查询,那样的数据不会又任何问题。但是这样的话,查询会麻烦,多了很多代码,不认识是一种高效率的解决之道,而且放弃了hibernate比较高级的特性,有点暴敛天物的了。

还有一种解决办法是,也是最偷懒的做法,就是把lazy从true该成false,让查询的时候,查询出所有关联的数据。这样其实也是我们所采用的办法,发现做了分页查询,性能还算可以接受。但是发现这样的做法,在一些比较复杂处理操作的时候还是有些问题,比如说batch job。当然这应该算是另外一个问题,具体请看使用hibernate,在面对复杂业务处理的时候,你时候很顺手,由Exception-found shared references to a collection说开去

第三种做法是,使用一个spring的一个intercepter拦截器来处理,即在service层增加一个拦截器。后来我担心这样会破坏spring的事务管理机制---有点杞人忧天。