1.@Transactional声明式事物也是基于aop实现的,public方法加了@Transactional注解后,已经成功的创建了事务,但是当前方法仍在方法拦截器中
2.业务方法发生异常之后的处理
判断回滚条件:
如果自定义了RollbackRuleAttribute列表,如果当前异常匹配到,则回滚(RollbackRuleAttribute默认是RuntimeException),其他异常不会回滚。
满足回滚条件,那么当前事务执行回滚操作
未满足回滚操作,那么当前事务可能被回滚,可能被提交。例如当前事务的rollbackOnly为true,依然执行回滚操作。当然如果未能满足回滚条件的话,即使该事务抛出异常,依然会被提交。
例如:A类的service层的某个方法中调用B类service层的对象方法,B类中方法被A类中的方法调用后,B类方法的事务已经提交,但是spring却把B类方法的事务标记为rollback-only,A类方法的外层事务管理器再commit时就会抛此异常。(可以设置globalRollbackOnParticipationFailure=false解决,该配置默认是true)。
B.既然声明式事务也是aop,所以当@Transactional跟其他切面(如@Asyn或其他拦截器MethodIntercepter)同时使用时,需要考虑@Order属性【切面设置,没有设置取默认值】,,是按照切面的Order顺序来执行的:Order值越小,那么切面越先执行(越后结束).【如果Order相同,则是按照切面字母的顺序(自然排序)来执行切面】
假设都使用默认值(@Transactional的Order值是Integer.MAX_VALUE(拦截器不指定时的默认值).@Aysn的值是OrderInteger.MIN_VALUE,如果Order一样,按照字母顺序排序【排序越后的越后执行,越先执行完】,另外SpringAop会先扫描事务拦截器,(自定义拦截器在事务拦截器后面)所以自定义拦截器不会影响事务【事务拦截开始-自定义拦截开始-自定义拦截结束-自定义拦截结束】)
所以不考虑Order的情况下(自定义切面不设置order),自定义aop对本地事务的影响
1.@Before 不会,因为还没执行到service的业务逻辑
2.@After 报错会影响事务回滚
3.@AfterReturning 报错会影响事务回滚
4.@Around 以Object o=pjp.proceed()为界,之前的代码不会影响事务回滚,之后的代码会影响事务回滚.
切面
@PointCut() 连接点
@Before() 前置通知
@Around() 环绕通知
@After() 最终通知
@AfterReturn() 后置通知
@AfterThrow() 异常通知
无异常情况下执行顺序为:
环绕通知开始->前置通知->环绕通知.proceed()->环绕通知结束->最终通知->后置通知