TransactionProxyFactoryObject的TransactionAttributes属性是用来配置的传播行为,并规定了7种类型的事务传播行为,它们规定了事务方法和事务方法发生嵌套调用时事务如何进行传播:
PROPAGATION_REQUIRED | 支持当前事务,如果当前没有事务,就新建一个事务。这是最常见的选择。 |
PROPAGATION_SUPPORTS | 支持当前事务,如果当前没有事务,就以非事务方式执行。 |
PROPAGATION_MANDATORY | 支持当前事务,如果当前没有事务,就抛出异常。 |
PROPAGATION_REQUIRES_NEW | 新建事务,如果当前存在事务,把当前事务挂起。 |
PROPAGATION_NOT_SUPPORTED | 以非事务方式执行操作,如果当前存在事务,就把当前事务挂起。 |
PROPAGATION_NEVER | 以非事务方式执行,如果当前存在事务,则抛出异常。 |
PROPAGATION_NESTED | 如果当前存在事务,则在嵌套事务内执行。如果当前没有事务,则进行与PROPAGATION_REQUIRED类似的操作。 |
PROPAGATION_REQUIRED和PROPAGATION_SUPPORTS我用的比较多,其它的很少使用。特别是PROPAGATION_REQUIRED,我绝大多数情况都使用这个行为(如,在创建,删除,修改的时候),我会在查询(获取)数据的时候设置为:PROPAGATION_REQUIRED,readOnly,声明为一个只读事务,这样有助于性能的提高。
TransactionProxyFactoryObject的Target属性是我们要拦截的对象,一般我们设置为业务层的对象。
实现代码:
App.config
<?xml version="1.0" encoding="utf-8" ?>
<objects xmlns="http://www.springframework.net"
xmlns:db="http://www.springframework.net/database">
<db:provider id="DbProvider"
provider="SqlServer-1.1"
connectionString="Server=(local);Database=SpringLesson16;Uid=sa;Pwd=;Trusted_Connection=False"/>
<object id="userDao" type="Dao.UserDao, Dao">
<property name="AdoTemplate" ref="adoTemplate"/>
</object>
<object id="accountDao" type="Dao.AccountDao, Dao">
<property name="AdoTemplate" ref="adoTemplate"/>
</object>
<object id="userService" parent="txProxyTemplate">
<property name="Target">
<object type="Service.UserService, Service">
<property name="UserDao" ref="userDao"/>
<property name="AccountDao" ref="accountDao"/>
</object>
</property>
</object>
<object id="adoTemplate" type="Spring.Data.Core.AdoTemplate, Spring.Data">
<property name="DbProvider" ref="DbProvider"/>
<property name="DataReaderWrapperType" value="Spring.Data.Support.NullMappingDataReader, Spring.Data"/>
</object>
<!--事务管理器-->
<object id="transactionManager"
type="Spring.Data.Core.AdoPlatformTransactionManager, Spring.Data">
<property name="DbProvider" ref="DbProvider"/>
</object>
<object id="txProxyTemplate" abstract="true"
type="Spring.Transaction.Interceptor.TransactionProxyFactoryObject, Spring.Data">
<property name="PlatformTransactionManager" ref="transactionManager"/>
<property name="TransactionAttributes">
<name-values>
<add key="Save*" value="PROPAGATION_REQUIRED"/>
<add key="Delete*" value="PROPAGATION_REQUIRED"/>
<add key="Get*" value="PROPAGATION_REQUIRED,readOnly"/>
</name-values>
</property>
</object>
</objects>
在name-value节点下,key属性为Save*,意思是拦截所有以Save开头的方法,在拦截到的方法上增加PROPAGATION_REQUIRED的事务传播行为。