JavaWeb_(Spring框架)整合Mybatis加入事务操作数据库
整合Mybatis
a)导包:
i.Spring:基本包、aop、aspects、jdbc、tx、test;
ii.Mybatis:mybatis-3.4.6
iii.整合包:mybatis-spring-1.3.2
iv.三方包:
1.aopalliance
2.aspectj.weaver
3.c3p0-0.9.5.2
4.mchange-commons-java-0.2.11
5.mysql-connector-java-5.1.46-bin
6.ojdbc7
b)创建项目结构(package):bean、service、mapper、test;
c)创建配置文件:sqlMapperConfig、applicaitonContext
2、创建测试用例:使用Mapper扫描开发,转账;
3、在service中加入事务:利用Spring-aop事务解决转账异常问题;
未添加事务前
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
package com.Gary.bean; public class Account { private Integer id; private String name; private Double money; //转账金额 private Double tranferMoney; public Double getTranferMoney() { return tranferMoney; } public void setTranferMoney(Double tranferMoney) { this.tranferMoney = tranferMoney; } public Integer getId() { return id; } public void setId(Integer id) { this.id = id; } public String getName() { return name; } public void setName(String name) { this.name = name; } public Double getMoney() { return money; } public void setMoney(Double money) { this.money = money; } }
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
package com.Gary.mapper; import com.Gary.bean.Account; //账户mapper接口 public interface AccountMapper { //操作数据库扣款和加款 //扣款 void subMoney(Account pay); //加款 void addMoney(Account collect); }
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd"> <mapper namespace="com.Gary.mapper.AccountMapper"> <update id="subMoney" parameterType="Account"> update account set money = money - #{tranferMoney} where id = #{id} </update> <update id="addMoney" parameterType="Account"> update account set money = money + #{tranferMoney} where id = #{id} </update> </mapper>
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
package com.Gary.service; public interface AccountService { //转账方法 void tranferAccount(); }
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
package com.Gary.service; import javax.annotation.Resource; import com.Gary.bean.Account; import com.Gary.mapper.AccountMapper; public class AccountServiceImpl implements AccountService{ @Resource(type = AccountMapper.class) private AccountMapper mapper; @Override public void tranferAccount() { Double tranferMoney = 100d; Account pay = new Account(); pay.setId(1); pay.setTranferMoney(tranferMoney); //先扣款 mapper.subMoney(pay); Account collect = new Account(); collect.setId(2); collect.setTranferMoney(tranferMoney); //加款 mapper.addMoney(collect); } }
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
package com.Gary.test; import javax.annotation.Resource; import org.junit.Test; import org.junit.runner.RunWith; import org.springframework.test.context.ContextConfiguration; import org.springframework.test.context.junit4.SpringJUnit4ClassRunner; import com.Gary.service.AccountService; @RunWith(SpringJUnit4ClassRunner.class) @ContextConfiguration("classpath:applicationContext.xml") public class MapperTest { @Resource(name = "accountService") private AccountService as; @Test public void Test1() { as.tranferAccount(); } }
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
<?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" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-4.3.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-4.3.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-4.3.xsd http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-4.3.xsd"> <!-- 读取配置文件 --> <context:property-placeholder location="db.properties"/> <!-- 配置 dataSource --> <bean name="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource"> <property name="driverClass" value="${jdbc.driverClass}"/> <property name="jdbcUrl" value="${jdbc.jdbcUrl}"/> <property name="user" value="${jdbc.user}"/> <property name="password" value="${jdbc.password}"/> </bean> <!-- mybatis --> <bean name="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean"> <property name="dataSource" ref="dataSource"/> <property name="configLocation" value="classpath:sqlMapConfig.xml"/> </bean> <!-- mapper工厂 --> <bean class="org.mybatis.spring.mapper.MapperScannerConfigurer"> <property name="basePackage" value="com.Gary.mapper"/> </bean> <!-- service --> <bean name="accountService" class="com.Gary.service.AccountServiceImpl"> </bean> </beans>
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
jdbc.driverClass=com.mysql.jdbc.Driver jdbc.jdbcUrl=jdbc:mysql://localhost:3306/ssm_spring jdbc.user=root jdbc.password=123456
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE configuration PUBLIC "-//mybatis.org//DTD Config 3.0//EN" "http://mybatis.org/dtd/mybatis-3-config.dtd"> <configuration> <typeAliases> <package name="com.Gary.bean"/> </typeAliases> </configuration>
Spring中加入事务
a) 配置事务核心管理器: DataSourceTransactionManager;
<!-- 需要事务核心管理器 --> <bean name="transactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager"> <property name="dataSource" ref="dataSource"/> </bean>
b) 配置事务通知 tx:Advice;
<!-- 配置事务通知 --> <tx:advice id="txAdvice" transaction-manager="transactionManager"> <tx:attributes> <tx:method name="update*" isolation="DEFAULT" propagation="REQUIRED" read-only="false"/> </tx:attributes> </tx:advice>
c) 配置aop;
<!-- 配置aop --> <aop:config> <aop:pointcut expression="execution(* com.Gary.service.*ServiceImpl.*(..))" id="txPc"/> <aop:advisor advice-ref="txAdvice" pointcut-ref="txPc"/> </aop:config>
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
<?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" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-4.3.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-4.3.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-4.3.xsd http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-4.3.xsd"> <!-- 读取配置文件 --> <context:property-placeholder location="db.properties"/> <!-- 配置 dataSource --> <bean name="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource"> <property name="driverClass" value="${jdbc.driverClass}"/> <property name="jdbcUrl" value="${jdbc.jdbcUrl}"/> <property name="user" value="${jdbc.user}"/> <property name="password" value="${jdbc.password}"/> </bean> <!-- mybatis --> <bean name="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean"> <property name="dataSource" ref="dataSource"/> <property name="configLocation" value="classpath:sqlMapConfig.xml"/> </bean> <!-- mapper工厂 --> <bean class="org.mybatis.spring.mapper.MapperScannerConfigurer"> <property name="basePackage" value="com.Gary.mapper"/> </bean> <!-- service --> <bean name="accountService" class="com.Gary.service.AccountServiceImpl"> </bean> <!-- 需要事务核心管理器 --> <bean name="transactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager"> <property name="dataSource" ref="dataSource"/> </bean> <!-- 配置事务通知 --> <tx:advice id="txAdvice" transaction-manager="transactionManager"> <tx:attributes> <tx:method name="update*" isolation="DEFAULT" propagation="REQUIRED" read-only="false"/> </tx:attributes> </tx:advice> <!-- 配置aop --> <aop:config> <aop:pointcut expression="execution(* com.Gary.service.*ServiceImpl.*(..))" id="txPc"/> <aop:advisor advice-ref="txAdvice" pointcut-ref="txPc"/> </aop:config> </beans>
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
package com.Gary.bean; public class Account { private Integer id; private String name; private Double money; //转账金额 private Double tranferMoney; public Double getTranferMoney() { return tranferMoney; } public void setTranferMoney(Double tranferMoney) { this.tranferMoney = tranferMoney; } public Integer getId() { return id; } public void setId(Integer id) { this.id = id; } public String getName() { return name; } public void setName(String name) { this.name = name; } public Double getMoney() { return money; } public void setMoney(Double money) { this.money = money; } }
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
package com.Gary.mapper; import com.Gary.bean.Account; //账户mapper接口 public interface AccountMapper { //操作数据库扣款和加款 //扣款 void subMoney(Account pay); //加款 void addMoney(Account collect); }
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd"> <mapper namespace="com.Gary.mapper.AccountMapper"> <update id="subMoney" parameterType="Account"> update account set money = money - #{tranferMoney} where id = #{id} </update> <update id="addMoney" parameterType="Account"> update account set money = money + #{tranferMoney} where id = #{id} </update> </mapper>
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
package com.Gary.service; public interface AccountService { //转账方法 void updateTranferAccount(); }
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
package com.Gary.service; import javax.annotation.Resource; import com.Gary.bean.Account; import com.Gary.mapper.AccountMapper; public class AccountServiceImpl implements AccountService{ @Resource(type = AccountMapper.class) private AccountMapper mapper; @Override public void updateTranferAccount() { Double tranferMoney = 100d; Account pay = new Account(); pay.setId(1); pay.setTranferMoney(tranferMoney); //先扣款 mapper.subMoney(pay); //添加异常 int i=1/0; Account collect = new Account(); collect.setId(2); collect.setTranferMoney(tranferMoney); //加款 mapper.addMoney(collect); } }
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
package com.Gary.test; import javax.annotation.Resource; import org.junit.Test; import org.junit.runner.RunWith; import org.springframework.test.context.ContextConfiguration; import org.springframework.test.context.junit4.SpringJUnit4ClassRunner; import com.Gary.service.AccountService; @RunWith(SpringJUnit4ClassRunner.class) @ContextConfiguration("classpath:applicationContext.xml") public class MapperTest { @Resource(name = "accountService") private AccountService as; @Test public void Test1() { as.updateTranferAccount(); } }
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
<?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" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-4.3.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-4.3.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-4.3.xsd http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-4.3.xsd"> <!-- 读取配置文件 --> <context:property-placeholder location="db.properties"/> <!-- 配置 dataSource --> <bean name="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource"> <property name="driverClass" value="${jdbc.driverClass}"/> <property name="jdbcUrl" value="${jdbc.jdbcUrl}"/> <property name="user" value="${jdbc.user}"/> <property name="password" value="${jdbc.password}"/> </bean> <!-- mybatis --> <bean name="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean"> <property name="dataSource" ref="dataSource"/> <property name="configLocation" value="classpath:sqlMapConfig.xml"/> </bean> <!-- mapper工厂 --> <bean class="org.mybatis.spring.mapper.MapperScannerConfigurer"> <property name="basePackage" value="com.Gary.mapper"/> </bean> <!-- service --> <bean name="accountService" class="com.Gary.service.AccountServiceImpl"> </bean> <!-- 需要事务核心管理器 --> <bean name="transactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager"> <property name="dataSource" ref="dataSource"/> </bean> <!-- 配置事务通知 --> <tx:advice id="txAdvice" transaction-manager="transactionManager"> <tx:attributes> <tx:method name="update*" isolation="DEFAULT" propagation="REQUIRED" read-only="false"/> </tx:attributes> </tx:advice> <!-- 配置aop --> <aop:config> <aop:pointcut expression="execution(* com.Gary.service.*ServiceImpl.*(..))" id="txPc"/> <aop:advisor advice-ref="txAdvice" pointcut-ref="txPc"/> </aop:config> </beans>
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
jdbc.driverClass=com.mysql.jdbc.Driver
jdbc.jdbcUrl=jdbc:mysql://localhost:3306/ssm_spring
jdbc.user=root
jdbc.password=123456
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE configuration PUBLIC "-//mybatis.org//DTD Config 3.0//EN" "http://mybatis.org/dtd/mybatis-3-config.dtd"> <configuration> <typeAliases> <package name="com.Gary.bean"/> </typeAliases> </configuration>
(如需转载学习,请标明出处)