Spring学习(五)OpenSessionInView

来源:互联网 发布:javascript视频网站 编辑:程序博客网 时间:2024/06/08 07:05

首先我们来看一下什么是OpenSessionInView?


    在hibernate中使用load方法时,并未把数据真正获取时就关闭了session,当我们真正想获取数据时会迫使load加载数据,而此时session已关闭,所以就会出现异常。 比较典型的是在MVC模式中,我们在M层调用持久层获取数据时(持久层用的是load方法加载数据),当这一调用结束时,session随之关闭,而我们希望在V层使用这些数据,这时才会迫使load加载数据,我们就希望这时的sessionopen着得,这就是所谓的Open Session In view 。 我们可以用filter来达到此目的。 这段话引至于百度百科,但确实很好的说明了OpenSessionInView这个过滤器的作用。

OpenSessionInViewFilterspring提供的一个针对Hibernate的一个支持类,其主要意思是在发起一个页面请求时打开HibernateSession,一直保持这个Session,直到这个请求结束,具体是通过一个Filter来实现的。  由于Hibernate引入了Lazy Load特性,使得脱离HibernateSession周期的对象如果再想通过getter方法取到其关联对象的值,Hibernate会抛出一个LazyLoadException。所以为了解决这个问题,Spring引入了这个Filter,使得HibernateSession的生命周期变长。  


首先分析一下它的源码,可以发现,它所实现的功能其实比较简单:

    SessionFactory sessionFactory = lookupSessionFactory(request);      Session session = null;      boolean participate = false;            if (isSingleSession()) {          // single session mode          if (TransactionSynchronizationManager.hasResource(sessionFactory)) {          // Do not modify the Session: just set the participate flag.          participate = true;             }    else {          logger.debug("Opening single Hibernate Session in OpenSessionInViewFilter");          session = getSession(sessionFactory);          TransactionSynchronizationManager.bindResource(sessionFactory, new SessionHolder(session));          }      } else {          // deferred close mode          if (SessionFactoryUtils.isDeferredCloseActive(sessionFactory)) {      // Do not modify deferred close: just set the participate flag.          participate = true;          } else {          SessionFactoryUtils.initDeferredClose(sessionFactory);          }      }            try {          filterChain.doFilter(request, response);      } finally {          if (!participate) {                  if (isSingleSession()) {                      // single session mode              TransactionSynchronizationManager.unbindResource(sessionFactory);              logger.debug("Closing single Hibernate Session in OpenSessionInViewFilter");              closeSession(session, sessionFactory);          }else {              // deferred close mode              SessionFactoryUtils.processDeferredClose(sessionFactory);          }      }      }  

在上述代码中,首先获得SessionFactory,然后通过SessionFactory获得一个Session。然后执行真正的Action代码,最后根据情况将HibernateSession进行关闭。整个思路比较清晰。  


下面我们来看一下他的具体配置,其实很简单,直接在web.xmlfilter配置

    <filter>      <filter-name>openSessionInView</filter-name>      <filter-class>org.springframework.orm.hibernate3.support.OpenSessionInViewFilter</filter-class>      <init-param>      <param-name>sessionFactoryBeanName</param-name>      <param-value>sf</param-value>      </init-param>      </filter>      <filter-mapping>      <filter-name>openSessionInView</filter-name>      <url-pattern>/*</url-pattern>      </filter-mapping>  

在上面配置中要注意以下几点:

1、这个filter一定要配置在struts的过滤器的前面,因为过滤器是“先进后出”原则,如果你配置在struts的后面的话,你的openSessionInView过滤器都执行完了,怎么在去在管理action的转向页面啊。

2Opensessioninview也需要sessionfactorybean的注入,他默认的去找beanidsessionfactorybean,如果sessionfactorybeanid不是这个名字的话,要记得给这个过滤器配置一个参数,参数名为sessionfactoryBeanName,把他的value设置为你的sessionfactorybeanid值。

3、在用opensessioninview的时候一定要注意,如果你不配置transaction的话,在用opensessioninview时,他默认的把事务配置为only-read只读,这样的话,如果你进行增删改的时候,他就会报一个在只读事务中不能进行增删改的操作。如果把opensessioninview去掉,他默认的事务的开始边界就锁定在dao层操作上,daohibernatetempt提供了事务的开始和提交

OpenSessionInView的副作用

         了解了上面几个问题之后,那么也就可以大概知道OpenSessionInView的副作用 – 资源占用严重,配置不当,影响系统性能。使用OpenSessionInView后,在request发出和response返回的流程中,如果有任何一步被阻塞,那在这期间connection就会被一直占用而不释放。比如页面较大,显示需要时间 或者 网速太慢,服务器与用户间传输的时间太长,这都会导致资源占用,最直接的表现就是连接池连接不够用,而导致最终服务器无法提供服务
0 0
原创粉丝点击
热门问题 老师的惩罚 人脸识别 我在镇武司摸鱼那些年 重生之率土为王 我在大康的咸鱼生活 盘龙之生命进化 天生仙种 凡人之先天五行 春回大明朝 姑娘不必设防,我是瞎子 当兵的体能太差怎么办 药流第二天出血怎么办 在部队当兵硬了怎么办 窦性心率过缓怎么办 武装突袭3卡顿怎么办 战队副本打完了怎么办 新兵连晚上饿了怎么办 运动后恶心想吐怎么办 运动后反胃想吐怎么办 魔域服务器满了怎么办 魔域忘记哪个区怎么办 魔域快捷键锁了怎么办 宝宝走路o型腿怎么办 走路多了腿疼怎么办 孩子与父母相冲怎么办 压片机冲模锈了怎么办 宝宝腹泻10多天怎么办 10个月宝宝腹泻怎么办 5岁宝宝很叛逆怎么办 6岁了不会写字怎么办 宝宝1岁不爱吃饭怎么办 l岁宝宝不吃饭怎么办 1岁宝宝不肯吃饭怎么办 10岁儿童不吃饭怎么办 2周岁宝宝不吃饭怎么办 9个月小孩不吃饭怎么办 孩子被老师打了怎么办 孩子说老师打她怎么办 孩子的数学太差怎么办 2岁宝宝老要喝水怎么办 分手了还想她怎么办 5岁宝宝不会说话怎么办 2岁半宝宝说话晚怎么办 7岁儿童发烧39度怎么办 感冒发烧怎么办简单的退烧方法 生完孩子没奶水怎么办 梦见让狐狸咬了怎么办 1岁宝宝不吃辅食怎么办 母乳不够宝宝不吃奶粉怎么办 吃母乳的宝宝不吃奶粉怎么办 宝宝吃母乳不吃奶粉怎么办