Spring学习笔记:声明式事务管理增删改查业务

一、关于是事务

  以方法为单位,进行事务控制;抛出异常,事务回滚。

  最小的执行单位为方法。决定执行成败是通过是否抛出异常来判断的,抛出异常即执行失败

 

二、声明式事务:

声明式事务(declarative transaction management)是Spring提供的对程序事务管理的方式之一。
Spring的声明式事务顾名思义就是采用声明的方式来处理事务。这里所说的声明,就是指在配置文件中声明。用在Spring配置文件中声明式的处理事务来代替代码式的处理事务。这样的好处是,事务管理不侵入开发的组件,具体来说,业务逻辑对象就不会意识到正在事务管理之中,事实上也应该如此,因为事务管理是属于系统层面的服务,而不是业务逻辑的一部分,如果想要改变事务管理策划的话,也只需要在定义文件中重新配置即可;在不需要事务管理的时候,只要在设定文件上修改一下,即可移去事务管理服务,无需改变代码重新编译,这样维护起来极其方便。
Spring使用AOP来完成声明式的事务管理,因而声明式事务是以方法为单位,Spring的事务属性自然就在于描述事务应用至方法上的策略,在Spring中事务属性有以下四个参数:
1.传播行为
3.只读提示
4.事务超时期间

 

三、案例:编程实现购买股票的业务

  

  1.编写实体类

  2.编写dao层接口和实现

  3.编写service层接口和实现

public class StockServiceImpl implements IStockService{
    private IStockDao stockDao;
    private IAccountDao accountDao;

    public void setStockDao(IStockDao stockDao) {
        this.stockDao = stockDao;
    }

    public void setAccountDao(IAccountDao accountDao) {
        this.accountDao = accountDao;
    }

    @Override
    public void buyStock(int sid, double scount, int aid, double abalance) {
        boolean isBuy = true;
        stockDao.updateStock(sid,scount,isBuy);
        accountDao.updateAccount(aid,abalance,isBuy);
    }
    @Override
    public void sellStock(int sid, double scount, int aid, double abalance) {
        boolean isBuy = false;
        stockDao.updateStock(sid,scount,isBuy);
        accountDao.updateAccount(aid,abalance,isBuy);
    }
}

  4.编写applicationContext.xml引入架包

    (1)没有加入事务的xml文件

<bean class="org.springframework.beans.factory.config.PropertyPlaceholderConfigurer">
        <property name="location" value="database.properties"/>
    </bean>
    <!--配置jdbc数据源-->
    <bean id="dataSource" class="org.springframework.jdbc.datasource.DriverManagerDataSource">
        <property name="url" value="${jdbc.url}"></property>
        <property name="driverClassName" value="${jdbc.driver}"></property>
        <property name="username" value="${jdbc.username}"></property>
        <property name="password" value="${jdbc.password}"></property>
    </bean>
    <!--注册jdbcTemplate-->
    <bean id="jbdcTemplate" class="org.springframework.jdbc.core.JdbcTemplate">
        <property name="dataSource" ref="dataSource"/>
    </bean>
    <!--注册dao实现-->
    <bean id="accountDao" class="cn.bank.dao.impl.AccountDaoImpl">
        <property name="jdbcTemplate" ref="jbdcTemplate"/>
    </bean>
    <bean id="stockDao" class="cn.bank.dao.impl.StockDaoImpl">
        <property name="jdbcTemplate" ref="jbdcTemplate"/>
    </bean>
    <!--注册service实现-->
    <bean id="stockService" class="cn.bank.service.impl.StockServiceImpl">
        <property name="accountDao" ref="accountDao"/>
        <property name="stockDao" ref="stockDao"/>
    </bean>

    功能测试:

@Test
    public void buyStock(){
        ApplicationContext context = new ClassPathXmlApplicationContext("applicationContext.xml");
        IStockService stockService = (IStockService) context.getBean("stockService");
        stockService.buyStock(1001,1000,1204,10000);
    }

(此处没有关联股票价格)

   (2)加入异常测试

@Override
public void buyStock(int sid, double scount, int aid, double abalance) {
boolean isBuy = true;
stockDao.updateStock(sid,scount,isBuy);
if (1==1) {
int i = 5 / 0;
}
accountDao.updateAccount(aid,abalance,isBuy);
}

  报错:

  处理结果:

 

  在执行一次:

 

  现在我们可以看到,在增加股票和减少余额中间产生异常之后,股票增加而余额没有减少,这种现在肯定是错误的。

  (3)添加事务管理

 

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xsi:schemaLocation="http://www.springframework.org/schema/beans
       http://www.springframework.org/schema/beans/spring-beans.xsd">
    <!--通过bean元素生命需要Spring创建的实例。该实例的类型通过class属性指定,
    并通过id属性为该实例制定一个名称,以便于访问-->
    <!--引入数据库配置文件-->
    <bean class="org.springframework.beans.factory.config.PropertyPlaceholderConfigurer">
        <property name="location" value="database.properties"/>
    </bean>
    <!--配置jdbc数据源-->
    <bean id="dataSource" class="org.springframework.jdbc.datasource.DriverManagerDataSource">
        <property name="url" value="${jdbc.url}"></property>
        <property name="driverClassName" value="${jdbc.driver}"></property>
        <property name="username" value="${jdbc.username}"></property>
        <property name="password" value="${jdbc.password}"></property>
    </bean>
    <!--注册jdbcTemplate-->
    <bean id="jbdcTemplate" class="org.springframework.jdbc.core.JdbcTemplate">
        <property name="dataSource" ref="dataSource"/>
    </bean>
    <!--注册dao实现-->
    <bean id="accountDao" class="cn.bank.dao.impl.AccountDaoImpl">
        <property name="jdbcTemplate" ref="jbdcTemplate"/>
    </bean>
    <bean id="stockDao" class="cn.bank.dao.impl.StockDaoImpl">
        <property name="jdbcTemplate" ref="jbdcTemplate"/>
    </bean>
    <!--注册service实现-->
    <bean id="stockService" class="cn.bank.service.impl.StockServiceImpl">
        <property name="accountDao" ref="accountDao"/>
        <property name="stockDao" ref="stockDao"/>
    </bean>
    <!--引入事务平台管理器-->
    <bean id="transactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
        <property name="dataSource" ref="dataSource"/>
    </bean>
    <!--事务拦截处理:使用代理工厂-->
    <bean id="serviceProxy" class="org.springframework.transaction.interceptor.TransactionProxyFactoryBean">
        <property name="target" ref="stockService"/>
        <property name="transactionManager" ref="transactionManager"/>
        <!--事务参数的设定-->
        <property name="transactionAttributes">
            <props>
                <prop key="buyStock">ISOLATION_DEFAULT,PROPAGATION_REQUIRED</prop>
            </props>
        </property>
    </bean>
</beans>

  测试(修改getBean()方法的参数):

@Test
    public void buyStockTest(){
        ApplicationContext context = new ClassPathXmlApplicationContext("applicationContext.xml");
        IStockService stockService = (IStockService) context.getBean("serviceProxy");
        stockService.buyStock(1001,1000,1204,10000);
    }

  异常发生,数据没有改变(是我们预期的结果,也是业务需要的):

    最后,去掉异常,保证事务管理下业务功能正常:

四:业务实现正常

 

posted @ 2017-10-20 11:41  滕秋宇  阅读(1058)  评论(0编辑  收藏  举报