Write operations are not allowed in read-only mode

使用Spring提供的Open Session In View而引發Write operations are not allowed in read-only mode (FlushMode.NEVER) 錯誤解決: web

       在沒有使用Spring提供的Open Session In View狀況下,因須要在service(or Dao)層裏把session關閉,因此lazy loading 爲true的話,要在應用層內把關係集合都初始化,如 company.getEmployees(),不然Hibernate拋session already closed Exception;    Open Session In View提供了一種簡便的方法,較好地解決了lazy loading問題. spring

它有兩種配置方式OpenSessionInViewInterceptor和OpenSessionInViewFilter(具體參看SpringSide),功能相同,只是一個在web.xml配置,另外一個在application.xml配置而已。 session

Open Session In View在request把session綁定到當前thread期間一直保持hibernate session在open狀態,使session在request的整個期間均可以使用,如在View層裏PO也能夠lazy loading數據,如 ${ company.employees }。當View 層邏輯完成後,纔會經過Filter的doFilter方法或Interceptor的postHandle方法自動關閉session。 app

 

解決方案: ide

《一》我實踐過,這個filter寫在最前面 保險 post

在 web.xml配置裏添加 
<filter> 
   <filter-name>OpenSessionInViewFilter</filter-name> 
   <filter-class> 
    org.springframework.orm.hibernate3.support.OpenSessionInViewFilter 
   </filter-class> 
   <init-param> 
    <param-name>sessionFactoryBeanName</param-name> 
    <param-value>sessionFactory</param-value> 
   </init-param> 
   <init-param> 
            <param-name>singleSession</param-name> 
            <param-value>true</param-value>            
        </init-param> 
        <init-param> 
        <param-name> flushMode </param-name> 
   <param-value>AUTO </param-value>         
        </init-param> 
</filter> 
     。。。。 


<filter-mapping> 
   <filter-name>OpenSessionInViewFilter</filter-name> 
   <url-pattern>/*</url-pattern> 
</filter-mapping>  url

 

《二》 spa

般這個錯誤是事務引發的,若是肯定事務沒有問題,仍是有這個錯,能夠重寫OpenSessionInViewFilter的2個方法 hibernate

在myfaces的wiki裏提供了OpenSessionInViewFilter的一個子類以下:
public class OpenSessionInViewFilter extends org.springframework.orm.hibernate3.support.OpenSessionInViewFilter {
      
        /**
         * we do a different flushmode than in the codebase
         * here
         */
        protected Session getSession(SessionFactory sessionFactory) throws DataAccessResourceFailureException {
                Session session = SessionFactoryUtils.getSession(sessionFactory, true);
                session.setFlushMode(FlushMode.COMMIT);
                return session;
        }
        /**
         * we do an explicit flush here just in case
         * we do not have an automated flush
         */
        protected void closeSession(Session session, SessionFactory factory) {
                session.flush();
                super.closeSession(session, factory);
        }
} code

相關文章
相關標籤/搜索