Thinking in sky

          --老賀的BLOG

            BlogJava :: 首頁 :: 新隨筆 :: 聯(lián)系 :: 聚合  :: 管理 ::
            21 隨筆 :: 0 文章 :: 35 評論 :: 0 Trackbacks
          先看一段代碼:
          1Connection conn = Conn.getConnection();
          2    conn.setAutoCommit(false);
          3    ……..
          4    ……
          5    conn.rollback();
          6    conn.commit(); 
          7
          數(shù)據(jù)庫的事務(wù)是針對 Connection 的。

             
          接著再看一段代碼:( spring 中事務(wù)的一段學(xué)習(xí)代碼,這段代碼是把 spring hibernate 結(jié)合在一起的,增加了理解上的難度,因為我的出發(fā)點一開始不要 hibernate ,就光用 jdbc 來進行數(shù)據(jù)庫事務(wù),但是沒有其他好的代碼,就這樣吧)
           1public Long addLineItem(Long orderId, LineItem lineItem)
           2
           3       log("OrderListDAOHibernate.addLineItem : Start"); 
           4
           5       OrderList orderList = (OrderList) getHibernateTemplate().load(OrderList.class, orderId); 
           6
           7       lineItem.setOrderList(orderList); 
           8
           9       getHibernateTemplate().saveOrUpdate(lineItem); 
          10
          11       getHibernateTemplate().saveOrUpdate(orderList); 
          12
          13       log("OrderListDAOHibernate.addLineItem : Ending"); 
          14
          15       return lineItem.getId(); 
          16
          17    }

          18
          19

          在這個代碼的配置文件中,把 addLineItem 做為一個切入點,進行事務(wù),也就是說,在 addLineItem 的外面,再包上一層事務(wù)的外殼。

             
          但是這個時候,問題出來了,事務(wù)是針對 Connection 的,而上面的兩個連續(xù)的 HibernateTemplate 執(zhí)行的 saveOrUpdate 中的 Connection 必須是一致才能用事務(wù), spring 怎么做到這一點的呢?(這個問題也就是在找 spring 的事務(wù)例子前,我想的 spring 中用 jdbc 來進行事務(wù),怎么樣讓 Connection 保持一致呢?但是沒有 jdbc 的例子,只有整合 hibernate 或者 ibatis 的例子,但是,我想,原理是一樣的吧。)

           

              解決問題的思路: HibernateTemplate 中的 Connection 必定一致。那么就從 HibernateTemplate 入手。

              spring 的源代碼,既然是 Hibernate ,那么,就沒有 Connection 給你看,只有 Session ,由 Session 來管理 Connection ,那么用事務(wù)來控制的話,這個 Session 必定在所有該事務(wù)中是一致的。于是在 HibernateTemplate 中找到:

           1protected Session getSession() 
           2
           3       if (isAlwaysUseNewSession()) 
           4
           5return SessionFactoryUtils.getNewSession(getSessionFactory(), getEntityInterceptor()); 
           6
           7       }
           
           8
           9       else if (!isAllowCreate()) 
          10
          11return SessionFactoryUtils.getSession(getSessionFactory(), false); 
          12
          13       }
           
          14
          15       else 
          16
          17return SessionFactoryUtils.getSession( 
          18
          19                  getSessionFactory(), getEntityInterceptor(), getJdbcExceptionTranslator()); 
          20
          21       }
           
          22
          23    }
           
          24
          25

          看來在 SessionFactoryUtils 里面,接著在 SessionFactoryUtils.getSession 中找:

           

          這個方法太長了,太復(fù)雜了,從簡,發(fā)現(xiàn)了非常關(guān)鍵的一點:

          1SessionHolder sessionHolder = (SessionHolder) TransactionSynchronizationManager.getResource(sessionFactory); 
          2
          3

          假如 sessionHolder 不等于空,說明,在事務(wù)中有這樣一個還沒有 commit session ,那么就返回這個 session ,假如等于空,新建一個 session ,并且在事務(wù)里加入這個 session 。這段代碼的意思大概是這樣,太繁雜了,只能猜,也肯定是如此。

           

          再看 getHibernateTemplate() 方法來自繼承 HibernateDaoSupport ,看了電子書《 spring-reference 》的第九章“ Dao 支持”, Dao 的支持類可以有好多,如: JdbcDaoSupport , HibernateDaoSupport , JdoDaoSupport 等等。

           

          既然前面一開始就是從 jdbc spring 事務(wù)控制引起的,那么看到了同樣的 HibernateDaoSupport---JdbcDaoSupport ,那么 JdbcDaoSupport 也應(yīng)該有 getJdbcTemplate() 這個方法,并且返回 JdbcTemplate 這個類。

           

          果然如此。

           

          于是剖析 JdbcTemplate 是不是和 HibernateTemplate 一樣。果然一樣。

           

          注意到:

          Connection con = DataSourceUtils.getConnection(getDataSource()); 

          Connection 是從 DataSourceUtils.getConnection() 來的,繼續(xù)跟蹤 DataSourceUtils.getConnection() 。

           

          找到:

          ConnectionHolder conHolder = (ConnectionHolder) TransactionSynchronizationManager.getResource(dataSource);

           

          Hibernate 中的一模一樣,因為沒有了 session 的封裝,條理在 jdbc 中更加清晰了。

           

          至此, spring 的事務(wù)控制 已經(jīng)全部搞定。

          posted on 2007-05-11 17:42 老賀 閱讀(403) 評論(0)  編輯  收藏

          只有注冊用戶登錄后才能發(fā)表評論。


          網(wǎng)站導(dǎo)航:
           
          主站蜘蛛池模板: 宜黄县| 聊城市| 民县| 修水县| 阿拉尔市| 平定县| 扎囊县| 乌拉特后旗| 玉树县| 嘉定区| 苍梧县| 康定县| 镇原县| 南部县| 福泉市| 永州市| 荆州市| 洛宁县| 桓台县| 巢湖市| 徐汇区| 淳化县| 宁国市| 山东| 永福县| 阿拉善左旗| 高台县| 连江县| 赤水市| 朝阳市| 建始县| 龙胜| 沁源县| 建湖县| 尉氏县| 增城市| 镇安县| 荔波县| 亚东县| 万源市| 易门县|