千家信息网

如何通过AOP环绕通知如何实现事务控制

发表于:2025-01-21 作者:千家信息网编辑
千家信息网最后更新 2025年01月21日,小编给大家分享一下如何通过AOP环绕通知如何实现事务控制,希望大家阅读完这篇文章之后都有所收获,下面让我们一起去探讨吧!通过AOP环绕通知实现事务控制1、导入相关的依赖 org.
千家信息网最后更新 2025年01月21日如何通过AOP环绕通知如何实现事务控制

小编给大家分享一下如何通过AOP环绕通知如何实现事务控制,希望大家阅读完这篇文章之后都有所收获,下面让我们一起去探讨吧!

通过AOP环绕通知实现事务控制

1、导入相关的依赖

            org.springframework        spring-context        5.0.2.RELEASE                 c3p0         c3p0         0.9.1.2                    org.aspectj          aspectjweaver          1.8.7      

2、配置连接池和开启AOP注解

以下采用的是xml配置方式,当然也可以使用纯注解配置

                    

2、创建链接工具类

package com.gzl.utils;import org.springframework.beans.factory.annotation.Autowired;import org.springframework.stereotype.Component;import javax.sql.DataSource;import java.sql.Connection;/** * 连接的工具类,它用于从数据源中获取一个连接,并且实现和线程的绑定 */@Component("connectionUtils")public class ConnectionUtils {    private ThreadLocal tl = new ThreadLocal();    @Autowired    private DataSource dataSource;    /**     * 获取当前线程上的连接     * @return     */    public Connection getThreadConnection() {        try{            //1.先从ThreadLocal上获取            Connection conn = tl.get();            //2.判断当前线程上是否有连接            if (conn == null) {                //3.从数据源中获取一个连接,并且存入ThreadLocal中                conn = dataSource.getConnection();                tl.set(conn);            }            //4.返回当前线程上的连接            return conn;        }catch (Exception e){            throw new RuntimeException(e);        }    }    /**     * 把连接和线程解绑     */    public void removeConnection(){        tl.remove();    }}

3、AOP环绕事务类

package com.gzl.utils;import org.aspectj.lang.ProceedingJoinPoint;import org.aspectj.lang.annotation.*;import org.springframework.beans.factory.annotation.Autowired;import org.springframework.stereotype.Component;/** * 和事务管理相关的工具类,它包含了,开启事务,提交事务,回滚事务和释放连接 */@Component("txManager")@Aspectpublic class TransactionManager {    @Autowired    private ConnectionUtils connectionUtils;  /**     * 需要进行事务控制的类或者方法,EL表达式配置     */    @Pointcut("execution(* com.gzl.service.impl.*.*(..))")    private void pt1(){}    /**     * 开启事务     */    public  void beginTransaction(){        try {            connectionUtils.getThreadConnection().setAutoCommit(false);        }catch (Exception e){            e.printStackTrace();        }    }    /**     * 提交事务     */    public  void commit(){        try {            connectionUtils.getThreadConnection().commit();        }catch (Exception e){            e.printStackTrace();        }    }    /**     * 回滚事务     */    public  void rollback(){        try {            connectionUtils.getThreadConnection().rollback();        }catch (Exception e){            e.printStackTrace();        }    }    /**     * 释放连接     */    public  void release(){        try {            connectionUtils.getThreadConnection().close();//还回连接池中            connectionUtils.removeConnection();        }catch (Exception e){            e.printStackTrace();        }    }    @Around("pt1()")    public Object aroundAdvice(ProceedingJoinPoint pjp){        Object rtValue = null;        try {            //1.获取参数            Object[] args = pjp.getArgs();            //2.开启事务            this.beginTransaction();            //3.执行方法            rtValue = pjp.proceed(args);            //4.提交事务            this.commit();            //返回结果            return  rtValue;        }catch (Throwable e){            //5.回滚事务            this.rollback();            throw new RuntimeException(e);        }finally {            //6.释放资源            this.release();        }    }}

spring AOP 环绕通知的思路

环绕通知Around Advice就是在指定的程序前后均执行相关的服务,设计思路如下:

1、设计一个接口

package com.spring.service;public interface IComponent { public void bussiness1();public void bussiness2();public void bussiness3();}

2、编写这个接口的实现

package com.spring.service;public class Component implements IComponent{ @Override public void bussiness1() {  // TODO Auto-generated method stub  System.out.println("这是业务1"); } @Override public void bussiness2() {  // TODO Auto-generated method stub  System.out.println("这是业务2"); } @Override public void bussiness3() {  // TODO Auto-generated method stub  System.out.println("这是业务3"); }}

3、编写前置通知的逻辑代码

该代码必须实现org.aopalliance.intercept.Method Interceptor接口,需要的服务都写在这里。

4、编写XML配置文件

通过代理来实现AOP的环绕通知,看一下org.aopalliance.intercept.MethodInterceptor接口的源代码。该接口不是Spring内部的接口,而是AOP Alliance标准所指定的,不过Spring对这个接口有一个具体的实现过程,同时该接口相融所有遵守AOP Alliance标准的所有AOP框架。

环绕通知相当于前置通知和后置通知的结合,不同的是在MethodInterceptor的invoke()方法中,可以自由地使用MethodInvocation提供的proceed()方法来执行目标对象的方法,同时proceed()方法将会返回目标方法执行后的返回结果,在invoke方法结束前还可以修改该结果,下面还是以上面的那个例子来示范一下环绕通知的应用。

编写一个环绕通知的类,该类实现MethodInterceptor接口。这里调用了MethodInvocation的proceed()方法,也就是说,调用了目标对象Component中的business1等方法,在这个方法的前后分别增加了验证和通知执行,接着修改一下配置文件,去掉前置通知和后置通知的配置,只需要将这个环绕通知添加进去就可以了,具体代码如下:

这里只需要配置一个环绕通知的Bean,并且将这个Bean配置到interceptorNames中就完成了所有的工作,测试代码与前面的相同,可以看到结果也与前面的相同。

看完了这篇文章,相信你对"如何通过AOP环绕通知如何实现事务控制"有了一定的了解,如果想了解更多相关知识,欢迎关注行业资讯频道,感谢各位的阅读!

0