`
raymond2006k
  • 浏览: 295565 次
  • 性别: Icon_minigender_1
  • 来自: 杭州
社区版块
存档分类
最新评论

Spring 事务配置的几种方式及应用举例

阅读更多

我以前在项目中的实践选择过程,最终选择第三种方案,几种都写出来与大家分享。 大家有其他好的方式,也欢迎分享。

环境:JDK 1.4.x , Hibernate 3.1, Spring 2.0.6, 开发模式: Service + DAO

1. 代理工厂Bean事务管理( *ProxyFactoryBean) + Service + DAO配置

    我刚开始看Spring时用的书是林信良的《Spring技术手册》,书中对声明式事务主要采用 TransactionProxyFactoryBean,业务Bean如 Service或BO类继承它来进行事务控制。代理工厂Bean( *ProxyFactoryBean)这一类Spring提供的工厂类,可将一个 bean 进行委托代理,从而达到控制方法行为的目的。

   此类事务配置一般如下(因为我们未采用这种方式,就以书上的JDBC datasource举例说明。不同公司采用的格式可能有所不同):

<!-- 前面的 dataSource等配置略 ........ -->

<!-- 事务管理器 -->
<bean id="transactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
<property name="dataSource">
<ref local="dataSource" />
</property>
</bean>

<!-- 事务模板 -->
<bean id="baseTransactionProxy"
class="org.springframework.transaction.interceptor.TransactionProxyFactoryBean"
abstract="true">
<property name="transactionManager" ref="transactionManager" />
<property name="transactionAttributes">
<props>
<prop key="*">PROPAGATION_REQUIRED</prop>   <!-- 本文仅简单用一种方式说明。所有方法起事务,可以修改以精细和区别性控制事务 -->
</props>
</property>
</bean>


<!-- 业务对象 -->
<bean id="authService" parent="baseTransactionProxy">
<property name="target">
<bean class="com.xxxx.cms.service.AuthorityService">
<property name="authDao" ref="authDao" />
</bean>
</property>
</bean>
<bean id="departmentService" parent="baseTransactionProxy">
<property name="target">
<bean class="com.xxxx.cms.service.pojo.DepartmentService">
<property name="departmentDao" ref="departmentDao" />
</bean>
</property>
</bean>
<!-- 数据访问对象 -->
<bean id="authDao" class="com.xxxx.cms.dao.jdbc.AuthorityDao">
<property name="dataSource" ref="dataSource" />
</bean>
<bean id="departmentDao" class="com.xxxx.cms.dao.jdbc.DepartmentDao">
<property name="dataSource" ref="dataSource" />
</bean>


  这种代理工厂Bean的事务管理一般都要求将 Service 的 bean 配置为 class="org.springframework.transaction.interceptor.TransactionProxyFactoryBean" , 上面的例子使用了 parent="baseTransactionProxy" 继承机制简化了原书中的配置。

   代码中通过以下方式使用:
 

  

AuthService authService = (AuthService) context.getBean("authService"); 
    boolean b = authService.hasPermission("TOKEN_XXXXX"); 

 

2. 自动代理事务(*AutoProxyCreator) + Service + DAO配置

    *AutoProxyCreator这一类东东,能够自动为Spring容器中的bean进行 AOP 代理,配置起来能适当简化。一般需要用 BeanNameAutoProxyCreator 来配置对那些类进行自动代理, MethodPointcutAdvisor 来配置对哪些方法进行代理。

    这种声明式事务配置采用拦截器(Interceptor)或通知器(Advisor) 进行事务控制,这里使用了Spring提供的 TransactionInterceptor 来管理事务。 (本质上 ProxyFactoryBean 也要生成被代理对象的字节码,不过每个类型的ProxyFactoryBean 只能固定处理一个 Aspect,不算真正的AOP)。

    以下配置对 *Service 的所有方法进行事务控制。   

<bean id="transactionManager" class="org.springframework.orm.hibernate3.HibernateTransactionManager">
  <property name="sessionFactory">
   <ref local="sessionFactory" />
  </property>
 </bean> 


 

<!-- 事务管理拦截器 --> 
<bean id="transactionInterceptor" class="org.springframework.transaction.interceptor.TransactionInterceptor"> 
<property name="transactionManager"> 
<ref local="transactionManager"/> 
</property> 
<property name="transactionAttributes"> 
<props> 
<prop key="*">PROPAGATION_REQUIRED</prop> <!-- 本文仅简单用一种方式说明。所有方法起事务,还可以精细控制事务 --> 
</props> 
</property> 
</bean> 

<!-- 配置要拦截哪些方法 --> 
<bean id="trasactionMethodPointcutAdvisor" class="org.springframework.aop.support.NameMatchMethodPointcutAdvisor"> 
<property name="mappedNames"> 
<list> 
<value>*</value> <!-- 所有方法 --> 
</list> 
</property> 
<property name="advice"> 
<ref local="transactionInterceptor" /> 
</property> 
</bean> 

<!-- 配置要拦截哪些类,并使用那些拦截器 --> 
<bean id="ServiceAutoProxyCreator" class="org.springframework.aop.framework.autoproxy.BeanNameAutoProxyCreator"> 
<property name="proxyTargetClass" value="true"></property> 
<property name="beanNames"> 
<list> 
<value>*Service</value> 
</list> 
</property> 
<property name="interceptorNames"> 
<list>  
<!-- 头三个是我们项目中用的其他 Advisor,这里展示了添加拦截器进行aspect控制的灵活性。省略他们的配置 --> 
<value>monitorMethodPointcutAdvisor</value> 
<value>asynmonitorMethodPointcutAdvisor</value> 
<value>businessLogMethodPointcutAdvisor</value> 
<value>trasactionMethodPointcutAdvisor</value> <!-- 事务拦截器, 直接配成 transactionInterceptor 去掉 trasactionMethodPointcutAdvisor bean 也可以, --> 
</list> 
</property> 
</bean> 

 
Service,DAO的配置方式稍微改变一下, Service不再作为ProxyFactoryBean的 target属性,而是一个顶级 bean,这样 Service bean看起来就更单纯一些。 

<!-- 业务对象 --> 
<bean class="com.xxxx.cms.service.AuthorityService"> 
<property name="authDao" ref="authDao" /> 
</bean> 
<bean class="com.xxxx.cms.service.pojo.DepartmentService"> 
<property name="departmentDao" ref="departmentDao" /> 
</bean> 

<!-- 数据访问对象 --> 
<bean id="authDao" class="com.xxxx.cms.dao.jdbc.AuthorityDao"> 
<property name="dataSource" ref="dataSource" /> 
</bean> 
<bean id="departmentDao" class="com.xxxx.cms.dao.jdbc.DepartmentDao"> 
<property name="dataSource" ref="dataSource" /> 
</bean> 

 
    代码中的使用方式不变,同 1 小节。

3.  自动代理 +  Service DAO零配置

    这种是我们项目中运用的方式,transactionInterceptor,trasactionMethodPointcutAdvisor ,ServiceAutoProxyCreator 三个 bean的配置不变。
    Service,DAO 无需配置, 其原理参见我另一篇文章:

我的开发经验分享(一)-Spring业务bean零配置


    代码中的使用方式不同,使用 ServiceFactory 直接创建bean,代码如下: 
    

   

AuthService authService = (AuthService)ServiceFactory.createBean(AuthService.class); 
    boolean b = authService.hasPermission("TOKEN_XXXXX"); 

 
    ServiceFactory 内部会自动注册未注册的 bean, 并和Spring 容器和已配置的拦截器关联。
 

4. Annotation 声明事务

    如果是 JDK 1.5下,Spring 也支持 注释声明式事务,类似于如下代码(附部分片段):

@Transactional 
public class PersonServiceImpl implements PersonService 
{ private EntityManager em; 

   @PersistenceContext 
  public void setEntityManager(EntityManager em) 
  { this.em = em; } 

 
   结合 <tx:annotation-driven/>配置。


它实际是将 xml 中的

<property name="transactionAttributes"> 
<props> 
<prop key="*">PROPAGATION_REQUIRED</prop> <!-- 所有方法起事务,还可以精细控制事务 --> 
</props> 
</property> 

 
转移到了Java代码中,本质上是一样的,两种方式都能进行精细事务管理。不过个人不太偏好这种方式,因为xml更便于集中管理,修改后无需编译。

 

1.5下Spring还用哪种更简化的事务管理方式,鄙人不是太熟,欢迎大家分享。

 

分享到:
评论
1 楼 raymond2006k 2008-09-26  
沙发自己坐,哈哈。

相关推荐

    spring声明式事务配置

    根据提供的信息,我们可以深入探讨Spring框架中的声明式事务配置及其多种实现方式。声明式事务管理是一种简化事务管理的方式,它允许开发人员通过配置而非编程来指定事务边界,从而减少了代码的复杂性并提高了可维护...

    Spring基于XML方式配置事务

    在Spring框架中,事务管理是核心功能之一,它允许开发者以声明式或编程式的方式处理应用程序的事务。这里我们主要探讨的是"Spring基于XML方式配置事务",这涉及到Spring的事务管理器、事务属性以及如何在XML配置文件...

    spring事务操作试验

    在Spring事务中,有几种常见的隔离级别可供选择,包括读未提交(READ UNCOMMITTED)、读已提交(READ COMMITTED)、可重复读(REPEATABLE READ)和串行化(SERIALIZABLE)。每种隔离级别都有其特定的并发控制策略,...

    spring 事务代理配置

    ### Spring事务管理——声明式事务配置详解 #### 引言 在现代的Java企业级应用开发中,事务处理是确保数据一致性和完整性的重要机制。Spring框架提供了强大的事务管理功能,支持编程式和声明式两种事务管理方式。...

    Spring事务管理配置

    在深入探讨Spring事务管理配置之前,我们先简要回顾一下Spring框架的核心概念。Spring是一个开源的Java平台,它提供了一套全面的编程和配置模型,旨在简化企业级应用的开发。其中,事务管理是Spring框架中的一个重要...

    spring 应用aop 实例

    在Spring框架中,AOP(面向切面编程)是一种强大的设计模式,它允许开发者将关注点从核心业务逻辑中分离出来,比如日志记录、事务管理、权限控制等。本实例将深入探讨如何在Spring 4.0版本中实现AOP。 首先,AOP的...

    Spring 实例化Bean的三种方式

    ### Spring 实例化Bean的三种方式详解 在Java企业级应用开发中,Spring框架因其强大的功能和灵活性,成为了处理依赖注入、事务管理等任务的首选工具。其中,Bean的实例化是Spring框架的核心功能之一,它支持多种...

    Spring+Hibernate+MySql的应用实例

    **Spring+Hibernate+MySql应用实例详解** 在Java Web开发领域,Spring、Hibernate和MySQL是三个非常关键的技术组件。Spring作为一个全面的框架,提供了一种轻量级的控制反转(IoC)和面向切面编程(AOP)的解决方案...

    Spring及AOP应用(事务与集成)

    #### 六、Spring事务管理 Spring框架提供了强大的事务管理机制,可以在不侵入业务逻辑的情况下实现事务控制。 - **声明式事务**:通过配置元数据(XML或注解)来管理事务边界。 - **编程式事务**:通过编程的方式...

    mybatis整合spring 实例

    6. **事务管理**:Spring提供了一种声明式事务管理方式,只需在需要事务的方法上添加`@Transactional`注解,Spring会自动进行事务的开启、提交或回滚。 通过以上步骤,我们可以看到MyBatis和Spring的整合简化了数据...

    Spring XML 的配置实例

    3. **属性注入**:Spring 提供了几种方式注入 Bean 的属性,如属性值注入、构造函数注入和工厂方法注入。例如: ```xml ``` 在这里,`name` 属性对应 Bean 类的属性名,`value` 或 `ref` 属性则提供了注入...

    整合Spring与Struts的几种方法

    整合Spring和Struts可以提升应用的可维护性和灵活性,同时也允许开发人员充分利用Spring的强大功能,如事务管理、数据访问抽象、AOP等。然而,随着技术的发展,现在许多项目已经转向使用Spring Boot或Spring MVC,...

    spring视频教程种子

    2. **IoC容器**:详述Spring的核心——IoC容器,包括Bean的生命周期管理、Bean的定义与实例化、Bean的装配方式(XML、注解和Java配置)。 3. **依赖注入**:深入解析依赖注入的概念,如何通过构造器注入、设值注入...

    spring_hibernate整合实例

    然而,随着Spring Data JPA的出现,现在更多地推荐使用JPA,它提供了一种基于标准的、与ORM供应商无关的方式来处理数据持久化。 4. **事务管理**:Spring提供了声明式事务管理,允许开发者在XML配置或注解中定义...

    spring_tx编程式事务代码

    总结来说,`Spring_tx编程式事务代码`主要涉及Spring的`TransactionTemplate`类,它是Spring事务管理的一种便捷工具,可以帮助开发者以编程的方式更加方便地控制事务的生命周期,同时保持代码的简洁和可维护性。...

    Spring Boot多数据源(JdbcTemplate)配置与使用

    配置多数据源在Spring Boot中主要涉及以下几个步骤: 1. 引入依赖:在`pom.xml`或`build.gradle`文件中添加Spring Boot的JDBC和数据源相关依赖。例如,如果你使用的是MySQL,可以添加如下Maven依赖: ```xml ...

    Redis+Spring实例

    Redis+Spring实例是一个结合了两种流行技术的项目,旨在演示如何在Java应用中集成和使用Redis作为缓存系统。Redis是一种高性能的键值数据存储,常用于缓存、消息代理和分布式数据结构服务。而Spring框架是Java企业级...

    spring_day04

    总结起来,`PlatformTransactionManager`是Spring事务管理的关键接口,它提供了一种抽象层,使得我们可以轻松地在不同事务管理策略间切换,同时简化了事务管理的复杂性。了解并正确使用`PlatformTransactionManager`...

    spring+hibernate

    至于"配置事务",在Spring中,我们可以通过以下几种方式配置事务: 1. XML配置:在配置文件中定义事务管理器和事务属性。 2. 注解配置:在Service层的方法上使用@Transactional注解。 3. Java配置:使用@...

    Spring事务管理的方法

    ### Spring事务管理的方法 #### 一、引言 在企业级应用开发中,事务管理是一项至关重要的技术。Spring框架作为Java领域中一个非常流行的轻量级框架,为开发者提供了多种方式来实现事务管理,其中主要分为编程式...

Global site tag (gtag.js) - Google Analytics