1、依赖
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-aop</artifactId>
<version>2.5.6</version>
</dependency>
2、添加注解类
package com.tianqi.annotion;
import java.lang.annotation.*;
@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.METHOD})
public @interface TestAnnotion {
}
注解说明:
@Retention 修饰注解,用来表示注解的生命周期
RetentionPolicy.SOURCE 表示注解只保留在源文件,当java文件编译成class文件,就会消失 RetentionPolicy.CLASS 注解被保留到class文件,但jvm加载class文件时候被遗弃,这是默认的生命周期
RetentionPolicy.RUNTIME 注解不仅被保存到class文件中,jvm加载class文件之后,仍然存在
@Target 用来表示注解作用范围,超过这个作用范围,编译的时候就会报错。@Target(ElementType.TYPE)——接口、类、枚举、注解
@Target(ElementType.FIELD)——字段、枚举的常量
@Target(ElementType.METHOD)——方法
@Target(ElementType.PARAMETER)——方法参数
@Target(ElementType.CONSTRUCTOR) ——构造函数
@Target(ElementType.LOCAL_VARIABLE)——局部变量
@Target(ElementType.ANNOTATION_TYPE)——注解
@Target(ElementType.PACKAGE)——包,用于记录java文件的package信息
3、添加切面类
package com.tianqi.aop;
import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.annotation.*;
import org.aspectj.lang.reflect.MethodSignature;
import org.springframework.stereotype.Component;
import java.lang.reflect.Method;
@Component
@Aspect
public class TestAnnotionAop {
@Pointcut(value = "@annotation(com.tianqi.annotion.TestAnnotion)")
private void testAn(){
}
@Before("testAn()")
public void testMain(JoinPoint point){
System.out.println("test方法前置执行了···");
MethodSignature ms = (MethodSignature) point.getSignature();
//获取方法名
Method method = ms.getMethod();
//获取参数
Object[] params = point.getArgs();
System.out.println("使用注解的方法名:" + method.getName());//该方法名为使用该注解的方法名
System.out.println("使用注解方法的最后一个参数:" + params[params.length-1]);
}
}
注解说明:
@Component 实现bean的注入。
@Aspect: 该注解是把此类声明为一个切面类。
@Before: 该注解是声明此方法为前置通知 (目标方法执行之前就会先执行被此注解标注的方法)
@After: 该注解是声明此方法为后置通知 (目标方法执行完之后就会执行被此注解标注的方法) @AfterReturning: 该注解是声明此方法为返回通知 (目标方法正常执行返回后就会执行被此注解标注的方法)
@AfterThrowing: 该注解是声明此方法为异常通知 (目标方法在执行出现异常时就会执行被此注解标注的方法)
@Around: 该注解是环绕通知是动态的,可以在前后都设置执行
@PointCut: 该注解是声明一个公用的切入点表达式(通知行为的注解的都可以直接拿来复用)
4、业务类使用,直接在方法上添加注解即可.
package com.tianqi.controller;
import com.tianqi.annotion.TestAnnotion;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
@RestController
@RequestMapping("/test")
public class TestController {
@GetMapping("/test")
@TestAnnotion
public String test(String name) {
System.out.println("test方法执行···");
return "SUCCESS";
}
}
5、执行结果
可以看到,在test方法执行之前 成功执行。