posts - 35,  comments - 7,  trackbacks - 0


事务不应该由dao管理,而应该由service管理

最重要的是如下四个类
DataSource :数据库的Connection连接工厂
DataSourceUtils:
参与同一个事务的多个dao实际上应该是共享同一个conn的。
DataSourceUtils.getConnection(dataSource)取得当前ThreadLocal的conn,如果没有从dataSource创建一个。
DataSourceUtils.releaseConnection(conn, dataSource)未必真正关闭连接。
DataSourceTransactionManager
TransactionProxyFactoryBean;拦截具体业务对象方法调用,中间根据DataSourceTransactionManager设置进行事务管理

文笔不行,说不明白,举个例子:

 dao1{
   method(){
     conn= DataSourceUtils.getConnection(dataSource);
      ...........
     DataSourceUtils.releaseConnection(conn, dataSource);
   }
 }
 
 dao2{
   method(){
     conn= DataSourceUtils.getConnection(dataSource);
      ...........
     DataSourceUtils.releaseConnection(conn, dataSource);
   }
 }
 
 service{   method();  }
 
 serviceImp{
   method(){
      dao1.method();
      dao2.method();
   }
 }
 
 
 <bean id="dataSource"
       class="org.apache.commons.dbcp.BasicDataSource"
       destroy-method="close">
 </bean>     
 <bean id="transactionManager"
       class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
     <property name="dataSource">
           <ref local="dataSource" />
     </property>
  </bean> 
  <bean id="service"
          class="org.springframework.transaction.interceptor.TransactionProxyFactoryBean">
       <property name="transactionManager">
          <ref bean="transactionManager" />
       </property>
       <property name="target">
          <ref local="serviceImp" />
       </property>
       <property name="transactionAttributes">
          <props>
            <prop key="*">PROPAGATION_REQUIRED</prop>
          </props>
       </property>
  </bean> 

分析:
当调用service.method()时,开始TransactionProxyFactoryBean拦截此方法指定当前线程需要事务,然后调用dao1.method(),
调用conn= DataSourceUtils.getConnection(dataSource)
判断当前线程还没有conn则创建一个,因为此时线程需要事务所以conn.setAutoCommit(false),执行数据库作,
然后DataSourceUtils.releaseConnection(conn, dataSource),判断当前线程需要事务所以不真正关闭连接继续,dao1.method()返回。
调用dao2.method(),调用conn= DataSourceUtils.getConnection(dataSource)判断当前线程有一个conn就返回这个conn,(此时dao1.method()和dao2.method()已经共用了这个conn),执行数据库操作,然后DataSourceUtils.releaseConnection(conn, dataSource),判断当前线程需要事务
所以不真正关闭连接继续,dao2.method()返回。service.method()返回,TransactionProxyFactoryBean拦截取得当前线程连接提交事务,关闭清除连接。这样两个dao就参与到了一个事务当中。如果service.method()抛出异常,则TransactionProxyFactoryBean在service.method()返回时拦截取得当前线程连接回滚事务,关闭清除连接。

不知道猜得对不对

posted on 2005-11-26 11:13 java小记 阅读(1199) 评论(1)  编辑  收藏

FeedBack:
# re: 关于spring的事务管理(单数据库):纯属猜测。
2008-12-07 19:57 | 桂丰大厦
cx  回复  更多评论
  

只有注册用户登录后才能发表评论。


网站导航:
 

<2005年11月>
303112345
6789101112
13141516171819
20212223242526
27282930123
45678910

常用链接

留言簿(1)

随笔分类

随笔档案

搜索

  •  

最新评论

阅读排行榜

评论排行榜