以转账为例,数据库如下:
首先先要写其service层和dao层,如下所示:
在dao中进行jdbc连接,要继承JdbcDaoSupport,查看其源码可知,只需要进行模板注入或者是连接池(有了连接池之后会进行模板的创建)。
public class TransDaoImpl extends JdbcDaoSupport implements TransDao{
/**
* 转出
* @param out
* @param money
*/
@Override
public void outMoney(String out, Double money)
{
String sql="update trans set money=money-? where name=?";
this.getJdbcTemplate().update(sql,money,out);
}
/**
* 转入
* @param in
* @param money
*/
@Override
public void inMoney(String in, Double money)
{
String sql="update trans set money=money+? where name=?";
this.getJdbcTemplate().update(sql,money,in);
}
}
public class AccountServiceImpl implements AccountService {
/**
* 注入dao层中的
*/
private TransDao transDao;
public void setTransDao(TransDao transDao) {
this.transDao = transDao;
}
//注入事务管理的模板
private TransactionTemplate transactionTemplate;
public void setTransactionTemplate(TransactionTemplate transactionTemplate) {
this.transactionTemplate = transactionTemplate;
}
/**
* @param out:转出账号
* @param in:传入账号
* @param money:交易金额
*/
@Override
public void trans(final String out, final String in,final Double money)
{
//对于编程式事务管理 会进行service层代码的改动,所以通常不用编程式事务管理
/*
//进行调用
transDao.inMoney(in,money);
transDao.outMoney(out,money);
//这两个事务应该是要么都做 ,要么都不做 transactionTemplate事物管理模板
*/
transactionTemplate.execute(new TransactionCallbackWithoutResult() {
//使用匿名内部类
@Override
protected void doInTransactionWithoutResult(TransactionStatus transactionStatus)
{
//进行对事物的相应操作
//匿名内部类使用外部变量的时候 需要将变量变为final
transDao.inMoney(in,money);
transDao.outMoney(out,money);
}
});
}
}
再配置其xml文件如下所示:
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
xmlns:aop="http://www.springframework.org/schema/aop"
xmlns:tx="http://www.springframework.org/schema/tx"
xmlns:p="http://www.springframework.org/schema/p"
xmlns:jee="http://www.springframework.org/schema/jee"
xsi:schemaLocation=" http://www.springframework.org/schema/aop
http://www.springframework.org/schema/aop/spring-aop-4.0.xsd
http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-4.0.xsd
http://www.springframework.org/schema/context
http://www.springframework.org/schema/context/spring-context-4.0.xsd
http://www.springframework.org/schema/jee
http://www.springframework.org/schema/jee/spring-jee-4.0.xsd
http://www.springframework.org/schema/tx
http://www.springframework.org/schema/tx/spring-tx-4.0.xsd">
<!--引入外部的属性文件-->
<context:property-placeholder location="classpath:jdbc.properties"/>
<!--配置c3p0连接池-->
<bean id="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource">
<property name="driverClass" value="${jdbc.driverClass}"/>
<property name="jdbcUrl" value="${jdbc.url}"/>
<property name="user" value="${jdbc.username}"/>
<property name="password" value="${jdbc.password}"/>
</bean>
<!--配置业务层-->
<bean id="accountService" class="per.hss.trans.AccountServiceImpl">
<property name="transDao" ref="transDao"/>
<!--注入事务管理,编程式事物管理需要手动进行事务管理的注入-->
<property name="transactionTemplate" ref="transactionTemplate"/>
</bean>
<!--配置Dao层-->
<!--这个是将连接池直接进行注入,创建jdbc模板,就不用再dao层进行注入了-->
<bean id="transDao" class="per.hss.trans.TransDaoImpl">
<property name="dataSource" ref="dataSource"/>
</bean>
<!--配置事物管理器 ,使用jdbc进行提交的时候connection.setAutoCommit(false)-->
<bean id="transactionManager"
class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
<!--连接池获得具体连接对象-->
<property name="dataSource" ref="dataSource"></property>
</bean>
<!--配置事物管理模板 spring为了简化事务管理的代码提供的类-->
<bean id="transactionTemplate"
class="org.springframework.transaction.support.TransactionTemplate">
<!--将真正进行事物管理的注入-->
<property name="transactionManager" ref="transactionManager"/>
</bean>
</beans>
在测试类中进行测试
public class Demo01
{
public static void main(String[] args)
{
ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml");
AccountService accountService1=(AccountService) applicationContext.getBean("accountService");
accountService1.trans("aaa","bbb",50d);
}
}
用Junit进行测试
@RunWith(SpringJUnit4ClassRunner.class)//配置测试环境
@ContextConfiguration(locations={"classpath:applicationContext.xml"})//引入xml文件
public class Demo01 {
//测试业务层类,将业务层进行注入
@Resource(name="accountService")
private AccountService accountService;
@Test
public void demo1()
{
accountService.trans("aaa","bbb",50d);
}
}
如果需要测试spring是否进行事务管理,那么就需要在AccountAerviceImpl中作如下改变
transDao.inMoney(in,money);
int i=1/0;
transDao.outMoney(out,money);
对于spring4.2.4需要的是Junit 4.9或以上的版本,否则很可能因为版本冲突导致无法进行测试。
关于编程式事务管理,编程式事务管理需要在每个service层进行改动,所以在一般的开发中不进行使用这种方法。