Spring学习笔记-AOP(注解)
AOP配置
myAdvice的bean在注解中用 @Component
将AopAdvice类配置成切面,就将@Aspect放在AopAdvice类上
关于切入点的配置使用注解@Pointcut("表达式") ,写一个空方法pt(),用来标记切入点!
再使用@Before("pt()")注解,标记相应的方法。
问:为什么要使用一个空方法呢?不能标记变量来表示切入点吗?
如果使用变量来标记切入点,存在内存空间的浪费,而使用空的方法,综合考虑对于内存的开销是最小的。
最后,在XML使用<aop:aspectj-autoproxy>开启注解驱动的支持,换而言之,就是在XML中写了这句话,@Aspect、@Pointcut、@Before才可以正常使用。
所以到最后就变成了下图:
注解开发AOP制作步骤
在XML格式基础上
-
导入坐标(伴随spring-context坐标导入已经依赖导入完成)
-
开启AOP注解支持(容易忘记)
-
配置切面@Aspect
-
定义专用的切入点方法,并配置切入点@Pointcut
-
为通知方法配置通知类型及对应切入点@Before
案例代码
applicationContext.xml文件
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:aop="http://www.springframework.org/schema/aop"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="http://www.springframework.org/schema/beans
https://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/aop
https://www.springframework.org/schema/aop/spring-aop.xsd http://www.springframework.org/schema/context https://www.springframework.org/schema/context/spring-context.xsd">
<context:component-scan base-package="com.Harmony"/>
<!-- 开启AOP注解支持-->
<aop:aspectj-autoproxy/>
</beans>
UserServiceImpl实现类
@Service("userService")
public class UserServiceImpl implements UserService {
public int save(int i, int m) {
System.out.println("user service running..." + " " + i + " " + m);
return 100;
}
}
UserApp
public class UserApp {
public static void main(String[] args) {
ApplicationContext ctx = new ClassPathXmlApplicationContext("applicationContext.xml");
UserService userService = (UserService) ctx.getBean("userService");
int ret = userService.save(666,888);
System.out.println("应用程序调用执行结果..." + ret);
}
}
AOPAdvice
@Component
@Aspect
public class AOPAdvice {
@Pointcut("execution(* *(..))")
public void pt() {}
@Before("pt()")
public void before() {
System.out.println("before");
}
@After("pt()")
public void after() {
System.out.println("after");
}
@AfterReturning("pt()")
public void afterReturning() {
System.out.println("afterReturning");
}
@AfterThrowing("pt()")
public void afterThrowing() {
System.out.println("afterThrowing");
}
@Around("pt()")
public Object around(ProceedingJoinPoint pjp) throws Throwable {
System.out.println("around before");
//对原始方法的调用
Object ret = pjp.proceed();
System.out.println("around after");
return ret;
}
}
注解开发AOP注意事项
1.切入点最终体现为一个方法,无参无返回值,无实 际方法体内容,但不能是抽象方法
2.引用切入点时必须使用方法调用名称,方法后面的()不能省略
3.切面类中定义的切入点只能在当前类中使用,如果想引用其他类中定义的切入点使用“类名.方法名()”引用 (可以抽出一个类来配置所有的切入点)
4.可以在通知类型注解后添加参数,实现XML配置中的属性,例如after-returning后的returning属性
AOP注解开发通知执行顺序控制
1.AOP使用XML配置情况下,通知的执行顺序由配置顺序决定,在注解情况下由于不存在配置顺序的概念的概念,参照通知所配置的方法名字符串对应的编码值顺序,可以简单理解为字母排序
-
同一个通知类中,相同通知类型以方法名排序为准
-
不同通知类中,以类名排序为准
-
使用@Order注解通过变更bean的加载顺序改变通知的加载顺序
2.企业开发经验
-
通知方法名由3部分组成,分别是前缀、顺序编码、功能描述
-
前缀为固定字符串,例如baidu、itheima等,无实际意义
-
顺序编码为6位以内的整数,通常3位即可,不足位补0
-
功能描述为该方法对应的实际通知功能,例如exception、strLenCheck
-
制通知执行顺序使用顺序编码控制,使用时做一定空间预留
-
003使用,006使用,预留001、002、004、005、007、008
-
使用时从中段开始使用,方便后期做前置追加或后置追加
-
最终顺序以运行顺序为准,以测试结果为准,不以设定规则为准
-
AOP注解驱动
-
名称:@EnableAspectJAutoProxy
-
类型:注解
-
位置:Spring注解配置类定义上方
-
作用:设置当前类开启AOP注解驱动的支持,加载AOP注解
-
格式:
@Configuration
@ComponentScan("com.itheima")
@EnableAspectJAutoProxy
public class SpringConfig {
}
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 全程不用写代码,我用AI程序员写了一个飞机大战
· DeepSeek 开源周回顾「GitHub 热点速览」
· 记一次.NET内存居高不下排查解决与启示
· MongoDB 8.0这个新功能碉堡了,比商业数据库还牛
· .NET10 - 预览版1新功能体验(一)