我们让aaa向bbb转账200,查看结果转账成功。

此时如果我们故意在业务层实现类转账过程当中制造异常,如下所示:


查看结果:

可以看到aaa账户的钱减少了,而bbb账户的钱没有增加。因为现在还没有进行事务管理,所以出现了转出执行了,而转入没有执行这样的情况。而我们所希望的是转入与转出能够同时成功或者同时失败,这时我们就需要进行相应的事务管理了。
PlatformTransactionManager接口
这个接口具体的实现类主要有用SpringJdbc或者Mybatis进行管理的类DataSourceTransactionManager,用Hibernate来进行事务管理的类HibernateTransactionManager
配置SpringJdbc事务管理器
将dataSource连接池注入管理器中,这时因为jdbc进行管理时需要获得连接对象,然后用connection.setAutoCommit(false)使其不自动提交,执行完后要conmmit,有异常的话要rollback。能获取这个连接的就是dataSource连接池,而DataSourceTransactionManager事务管理器是真正进行事务管理的类,而连接池又能获取到连接对象,所以要将其注入。
配置事务管理模板
如果直接用事务管理器来管理的话,代码会很繁琐,Spring为了简化事务管理的代码,提供了一个事务管理模板类org.springframework.transaction.support.TransactionTemplate。而真正进行事务管理的还是transactionManager,所以要将其注入事务管理模板中。
业务层实现类中注入事务管理模板
在编程式事务管理中,需要我们在使用事务的时候,手动的编写代码。也就是哪个类需要进行事务管理,就将模板注入其中。
然后在配置文件中业务层类里注入模板Bean
*利用模板进行转账
??业务类的 transfer方法中的转入和转出此时存在于一个事务中,需要我们用模板的execute方法传入TransactionCallback接口,这里我选择new 一个匿名内部类TransactionCallbackWithoutResult。这个匿名内部类里的一个方法叫做doInTransactionWithoutResult,在里面进行事务的相关操作。

这里要有为注意我划红线的部分,在JDK 1.8以下的版本会报错,也就是必须在方法的局部变量前加上final关键字:

??这是因为匿名内部类访问外部的局部变量时该变量必须是final,加上final之后会导致局部变量提升为一种隐式的成员变量,而在匿名类中需要传递进来final关键字,java希望的是保证内部实现和外在表现的一致性,正因如此,我内部类 操作事务时使用了外部类的out,in和money局部变量,所以必须要加。
??而我使用的是JDK 1.8却没有final也没报错是因为java8中已经没有匿名内部类和局部内部类只能访问final变量的限制了。
测试结果
先将金额都改为1000,然后转账,事务回滚了。也就是达到了一个事务里的操作同时成功或者同时失败。

??在编程式的事务管理中,我们需要手动的去修改业务层的代码,这样对以后的开发是不太友好的。而声明式事务管理是基于AOP技术实现,其主要思想是将事务管理作为一个“切面”代码单独编写,我们只用关心核心业务逻辑代码,然后通过AOP技术将事务管理的“切面”代码织入到业务类中。
配置事务管理器
配置业务层代理
本文来自电脑杂谈,转载请注明本文网址:
http://www.pc-fly.com/a/jisuanjixue/article-86311-2.html
好好翻一下他前前后后的讲话
诺列加并不是毒枭
一年估计只有加多宝赚的钱的零头的十分之一吧