简单仿写Spring AOP

导语:由于本人是某大学网络中心java组组长,在和学弟学妹们传授完spring的相关知识之后,看到一脸茫然的他们,仿佛看到自己大一的时候,所以为了帮助学弟学妹更好的了解IOC以及 AOP 两大原理,并且帮助自己更加深层次的学习spring,决定自己简单的仿写这两个功能。这篇是AOP,上一篇是IOC

源码已在github开源:Github地址
百度云 提取码:zanx

1.前序

由于上次仿写Spring IOC之后,帮学弟学妹讲了一下,收获赞许,说这样一下就好理解多了,于是乎Spring仿写第二弹来了,仿写Spring AOP。

当然:仿写之前还是需要对AOP的原理、机制有一定的了解,比如说代理模式呀,切点呀,切面呀等前缀知识

2.前缀知识

通知(Advice):主要是用来定义方法增强执行的时机以及如何增强

通知类型:

  • 前置通知(Before):在目标方法执行前,执行通知
  • 后置通知(After):在目标方法执行后,执行通知,此时不关系目标方法返回的结果是什么
  • 返回通知(After-returning):在目标方法执行后,执行通知
  • 异常通知(After-throwing):在目标方法抛出异常后执行通知
  • 环绕通知(Around): 目标方法被通知包裹,通知在目标方法执行前和执行后都被会调用
切点(Pointcut)

切点的作用主要是告诉系统我的那些方法需要增强;

通过匹配规则查找合适的连接点(Joinpoint),AOP 会在这些连接点上织入通知

切面(Aspect)

切面其实算是一个概念,他其实就是切点+通知的组合

3.实现步骤

(1) 确定都有哪些角色

  • 目标对象(被代理对象)
  • 目标对象接口(被代理对象实现的接口)
  • AOP类(通过代理创建代理对象的主战场)
  • 当然还有一些辅助类下面会一一解释

(2)代码实现(所有代码咋EasyAOP包下)

首先:得有一个目标对象实现的接口,这个接口具有需要增强的方法

/**
 * @description: 目标对象实现的接口
 * @author: 
 * @date: 2021/3/12 16:49
**/
public interface Study {
    /**
     * 阅读方法
     */
    void read();
}

然后就是目标对象,也就是被代理对象

/**
 * @description: 目标对象学生类,实现了学习接口
 * @author: 
 * @date: 2021/3/12 16:52
**/
public class Student implements Study{
    @Override
    public void read() {
        System.out.println("具有汉语阅读的能力!");
    }
}

然后我们需要定义一个接口,接口中的方法提供增强逻辑,也就是切面逻辑

/**
 * @description: 切面增强逻辑接口,是一个函数式接口
 * @author: 
 * @date: 2021/3/12 16:55
**/
public interface MethodInvocation {
    void invoke();
}

有了切面逻辑之后,我们就得定义通知接口,这里继承了InvocationHandler接口,因为我们使用的是jdk的动态代理形式

/**
 * @description: 通知接口
 * @author: 
 * @date: 2021/3/12 16:58
**/
public interface Advice extends InvocationHandler {}

然后就是简单定义具体的某种通知类型,这里我定义的是后置通知类型

/**
 * @description: 后置通知类,实现通知接口,其他通知也和这个差不多
 * @author: 
 * @date: 2021/3/12 16:59
**/
public class AfterAdvice implements Advice{
    /**
     * 目标对象
     */
    private Object bean;
    /**
     * 切面逻辑
     */
    private MethodInvocation methodInvocation;

    public AfterAdvice(Object bean,MethodInvocation methodInvocation) {
        this.bean = bean;
        this.methodInvocation = methodInvocation;
    }

    @Override
    public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
        //method.invoke就是代理对象调用目标对象的read方法
        Object result = method.invoke(bean,args);
        //在目标方法之后调用通知
        methodInvocation.invoke();
        return result;

    }
}

最后当然就是我们的主角EasyAop类了

/**
 * @description: AOP类,主要作用是获取代理对象
 * @author: 
 * @date: 2021/3/12 17:09
**/
public class EasyAop {
    public static Object getProxy(Object bean,Advice advice){
        return Proxy.newProxyInstance(EasyAop.class.getClassLoader(),bean.getClass().getInterfaces(),advice);
    }
}

来个小小的单元测试吧

/**
 * @description: Aop单元测试类
 * @author: 
 * @date: 2021/3/12 17:14
**/
public class EasyAopTest {
    @Test
    public void getProxy(){
        //目标对象
        Student student = new Student();
        //切面逻辑对象,
        MethodInvocation strentMethod = () -> {
            //在这里书写增强逻辑,因为MethodInvocation是函数式接口,所以用来lambda表达式
            System.out.println("阅读之后,具有理解的能力");
        };
        //后置通知对象
        AfterAdvice afterAdvice = new AfterAdvice(student, strentMethod);
        //生成代理对象
        Study proxy = (Study) EasyAop.getProxy(student, afterAdvice);
        proxy.read();
    }
}

来看看结果
在这里插入图片描述

4.小结

看看上面的结果,perfect! 这次AOP的仿写也是实现的比较简单,当然其中的思路还是对的,在动手之前需要先去了解代理模式,然后手动写写JDK的动态代理,再来实现AOP就会简单很多。哈哈,又是一次勇敢的尝试,嗯。。。好像还有点小上瘾,下次该仿写哪个小玩意呢?[坏笑]

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
### 回答1: Spring AOP是一种面向切面编程(AOP)框架,它是Spring框架的一部分,允许您将切面(通常是横切关注点)织入到代码中,以实现横切逻辑和功能,例如:事务管理,安全,日志跟踪等。它使用代理来实现AOP,因此它可以拦截方法调用,以执行相应的逻辑。 ### 回答2: Spring AOP(Aspect-Oriented Programming)是一个面向切面编程的框架,它通过将横切关注点(Cross-Cutting Concerns)与业务逻辑代码分离,实现了对代码的解耦和复用。横切关注点,也就是在应用程序中多处重复出现的功能或行为,如日志记录、性能监测、事务管理等。 在Spring AOP中,通过定义切面(Aspect)来封装横切关注点,切面是一组相互关联的通知(Advice)和切点(Pointcut)的集合。通知定义了在什么时候、在哪个切点处执行何种操作,常见的通知类型有前置通知(Before)、后置通知(After)、返回通知(AfterReturning)、异常通知(AfterThrowing)和环绕通知(Around)。切点用来确定在哪些连接点上应用通知,可以使用切点表达式或者注解来定义。 使用Spring AOP的过程为: 1. 定义一个切面类,通过注解或者XML配置定义相应的通知和切点。 2. 将切面类声明为一个Bean,让Spring容器来管理它。 3. 在应用程序中,通过AOP代理来将通知织入到目标对象的连接点上。 总体来说,Spring AOP提供了一种轻量级、便捷的方式,帮助开发者通过配置来实现横切关注点的解耦和复用。相对于传统的面向对象编程,它使得软件系统更加模块化、可维护,并且可以提升代码的可读性和可测试性。不过需要注意的是,Spring AOP只能针对Spring管理的Bean进行代理,对于非Spring管理的对象无法实现代理。同时,切面的织入也会带来一定的运行时开销,因此在使用过程中需要权衡利弊。 ### 回答3: Spring AOP(Aspect-Oriented Programming)是Spring框架提供的一种面向切面编程的方式。它能够在程序的运行期间动态地将横切关注点(即与业务逻辑无关的重复代码)插入到目标对象的方法中。 在传统的面向对象编程中,我们把应用程序抽象成不同的类和对象。但是随着业务的复杂度增加,我们会发现,在不同的类和对象中有一些共同的行为,比如日志记录、事务处理、安全控制等。这些共同的行为称为横切关注点。使用传统的编程方式,我们会在每个需要添加横切关注点的方法中编写相应的代码,这样会导致大量的代码重复。 而Spring AOP通过在编译期或运行期动态地将横切关注点插入到目标对象的方法中,从而实现对横切关注点的统一管理。它基于代理模式实现,在目标对象的方法执行前、执行后或抛出异常时,将额外的逻辑(切面)插入到方法中。 通过使用Spring AOP,我们可以将横切关注点的代码单独封装到一个切面中,然后在配置文件中定义切面的逻辑,指定需要被切入的目标对象和方法。当程序运行时,Spring框架会根据配置自动生成代理对象,并动态地将切面逻辑织入到代理对象的方法中。这样就不需要手动编写大量的重复代码,提高了代码的维护性和可重用性。 总的来说,Spring AOP是一种实现横切关注点的机制,通过动态的代理技术实现将横切关注点插入到目标对象的方法中。它使得应用程序更加模块化,减少了重复代码的编写,提高了代码的可维护性和可重用性。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值