一. AOP操作术语
二. AOP准备工作
1、Spring 框架一般都是基于 AspectJ 实现 AOP 操作
AspectJ 不是 Spring 组成部分,独立 AOP 框架,一般把 AspectJ 和 Spirng 框架一起使 用,进行 AOP操作
2、基于 AspectJ 实现 AOP 操作
(1)基于 xml 配置文件实现
(2)基于注解方式实现(使用)
3 在项目工程里面引入 AOP 相关依赖
4、切入点表达式
(1)切入点表达式作用:
知道对哪个类里面的哪个方法进行增强
(2)语法结构:
execution([权限修饰符] [返回类型] [类全路径] [方法名称]([参数列表]))
[权限修饰符]:public,private,*
[返回类型] 可以不写
[类全路径]
[方法名称]([参数列表])
举例 1:
对 com.atguigu.dao.BookDao 类里面的 add进行增强
execution(* com.atguigu.dao.BookDao.add(..))
举例 2:
对 com.atguigu.dao.BookDao 类里面的所有的方法进行增强
execution(* com.atguigu.dao.BookDao.* (..))
举例 3:
对 com.atguigu.dao包里面所有类,类里面所有方法进行增强
execution(* com.atguigu.dao.*.* (..))
三. AspectJ注解实现AOP操作
1.创建类
2.创建增强类(编写增强逻辑)
package com.LinXiaoDe.spring5.aopanno;
//增强的类
public class UserProxy {
//前置通知
public void before(){
System.out.println("before");
}
}
3.进行通知的配置
(1)开启注解扫描,有两种方式,
一种是通过配置文件开启注解扫描,另一种是通过新建配置类来开启注解扫描
①通过配置文件开启注解扫描
扫描二维码关注公众号,回复:
11856157 查看本文章
- 引入名称空间,开启注解扫描:
②通过新建配置类开启注解扫描
@Configuration @ComponentScan(basePackages = {
"com.atguigu"}) @EnableAspectJAutoProxy(proxyTargetClass = true)
public class ConfigAop {
}
(2)使用注解来创建User和UserProxy对象
(3)在增强类上面添加注解@Aspect
(4)在Spring配置文件中开启生成代理对象
(5)配置不同类型的通知
在增强类的里面,在作为通知方法上面添加通知类型注解,使用切入点表达式配置
execution([权限修饰符] [返回类型] [类全路径] [方法名称]([参数列表]))
package com.LinXiaoDe.spring5.aopanno;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.*;
import org.springframework.stereotype.Component;
//增强的类
@Component
@Aspect //要生成代理对象
public class UserProxy {
//@Before表示前置通知
@Before(value="execution(* com.LinXiaoDe.spring5.aopanno.User.add())")
public void before(){
System.out.println("Before 前置通知");
}
//后置通知(返回通知)
@AfterReturning(value="execution(* com.LinXiaoDe.spring5.aopanno.User.add())")
public void afterReturning(){
System.out.println("afterReturning后置通知");
}
//@After表示最终通知
@After(value="execution(* com.LinXiaoDe.spring5.aopanno.User.add())")
public void after(){
System.out.println("after最终通知");
}
//AfterThrowing表示异常通知
@AfterThrowing(value="execution(* com.LinXiaoDe.spring5.aopanno.User.add())")
public void afterThrowing(){
System.out.println("afterThrowing");
}
//环绕通知
@Around(value="execution(* com.LinXiaoDe.spring5.aopanno.User.add())")
public void around(ProceedingJoinPoint proceedingJoinPoint) throws Throwable{
System.out.println("环绕之前");
//被增强的方法
proceedingJoinPoint.proceed();
System.out.println("环绕之后");
}
}
四. 对相同切入点进行抽取
用@Pointcut对相同的切入点进行抽取(字符串保存也是可以的)
package com.LinXiaoDe.spring5.aopanno;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.*;
import org.springframework.stereotype.Component;
//增强的类
@Component
@Aspect //要生成代理对象
public class UserProxy {
//对相同的切入点进行抽取
@Pointcut(value = "execution(* com.LinXiaoDe.spring5.aopanno.User.add())")
public void pointdemo(){
}
//@Before表示前置通知
@Before(value="pointdemo()")
public void before(){
System.out.println("Before 前置通知");
}
//后置通知(返回通知)
@AfterReturning(value="pointdemo()")
public void afterReturning(){
System.out.println("afterReturning后置通知");
}
}
五. 有多个增强类多同一个方法进行增强,设置增强类优先级
- 在增强类上面添加注解 @Order(数字类型值),数字类型值越小优先级越高
@Component
@Aspect
@Order(1)//优先级
public class PersonProxy {
}