AOP

AOP简介

AOP的底层原理是动态代理。

AOP也就是面向切面,意思是做出一些通用的功能,如打印日志等,应用于所有需要的地方。传统的面向对象,在每个对象里进行打印日志,重复且无意义。

AOP实现的思路,拦截住一些需要使用打印日志功能的方法,使用动态代理,对原本的方法加入了打印日志的操作。

AOP重要概念

  1. 通知(增强,Advice):需要添加的功能叫做通知,比如说打印日志的操作
  2. 连接点(Join point):就是允许使用通知的地方,基本上每个方法前、后、抛异常时都可以是连接点(也就是before、after)
  3. 切点(Poincut):需要添加新功能的地方,比如需要在类A的方法 f() 前后打印日志, f() 就是切点
  4. 切面(Aspect):其实就是通知和切点的结合,通知和切点共同定义了切面的全部内容,它是干什么的,什么时候在哪执行
  5. 引入(Introduction):在无需修改现有类的前提下,让它们具有新的行为和状态。针对方法,而织入重点是实现方式为代理,针对对象。
  6. 目标(target):被通知的对象。也就是需要加入额外代码的对象,也就是真正的业务逻辑被组织织入切面。
  7. 织入(Weaving):把切面加入程序代码的过程。切面在指定的连接点被织入到目标对象中,在目标对象的生命周期里有多个点可以进行织入:编译期(切面在目标类编译时被织入,这种方式需要特殊的编译器)、类加载期(切面在目标类加载到JVM时被织入,这种方式需要特殊的类加载器,它可以在目标类被引入应用之前增强该目标类的字节码)、运行期(切面在应用运行的某个时刻被织入,一般情况下,在织入切面时,AOP容器会为目标对象动态创建一个代理对象,Spring AOP就是以这种方式织入切面的)

AOP具体使用方法

先定义一个切点,也就是需要拦截的地方。
围绕着切点,进行日志打印,共有五种执行日志打印的时机:

  1. before(前置通知): 在方法开始执行前执行
  2. after(后置通知): 在方法执行后执行
  3. around(环绕通知): 在方法执行前和执行后都会执行(优先于before和after)
  4. afterReturning(返回后通知): 在方法返回后执行
  5. afterThrowing(异常通知): 在抛出异常时执行

AOP的具体使用方法见:
传送门

拦截的东西

package com.aili.poem.controller;

import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;

@Controller
public class LoveController {

    @RequestMapping(value = "sayLove")
    @ResponseBody
    /**
     * 这里必须加@ResponseBody,否则会出现白页
     */
    public String sayLove(String name){
        System.out.println("方法运行,参数为:" + name);
        return "求爱";
    }
}

拦截后进行的操作

@Aspect
@Component
public class ControllerAspect {

    //切点
    @Pointcut("execution(* com.aili.poem.controller..*(..))")
    public void pointcut(){
    }

    //开始之前做点事
    @Before("pointcut()")
    public void doSomethingBefore(JoinPoint joinPoint){
        //获取参数
        Object[] args = joinPoint.getArgs();
        System.out.println("开始对" + args[0].toString() + "进行爱");
        System.out.println("Do Some Foreplay");
        System.out.println("Kiss your partner");
        System.out.println("Fingering your partner");
    }

    //结束之后做点事
    @After("pointcut()")
    public void doSomethingAfter(){
        System.out.println("Wipe the white liquid away");
    }

    //前后都做点事(在最前面)
    //这里注意必须返回Object
    @Around("pointcut()")
    public Object doSomethingAround(ProceedingJoinPoint joinPoint) throws Throwable{
        System.out.println("love you,baby");
        //在这条语句之前,相当于@Before,之后则相当于@After
        Object obj = joinPoint.proceed();
        System.out.println("love you,baby");
        return obj;
    }

    //返回结果后做点事
    @AfterReturning(value = "pointcut()", returning = "returnValue")
    public void doSomethingAfterReturn(JoinPoint joinPoint, Object returnValue){
        //获取参数
        Object[] args = joinPoint.getArgs();
        System.out.println("完成对" + args[0].toString() + "的爱");
        System.out.println("对她进行了" + returnValue.toString());
    }

    //出现意外做点事
    @AfterThrowing("pointcut()")
    public void doSomethingAfterThrow(){
        System.out.println("开车失败");
    }
}

最终执行的结果

love you,baby
开始对女神进行爱
Do Some Foreplay
Kiss your partner
Fingering your partner
方法运行,参数为:女神
love you,baby
Wipe the white liquid away
完成对女神的爱
对她进行了求爱
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

weixin_43751710

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值