1. AOP概念
1.1 概述
AOP(Aspect Oriented Programming)是一种设计思想,是软件设计领域中的面向切面编程,它是面向对象编程的一种补充和完善,它以通过预编译方式和运行期动态代理方式实现,在不修改源代码的情况下,给程序动态统一添加额外功能的一种技术。利用AOP可以对业务逻辑的各个部分进行隔离,从而使得业务逻辑各部分之间的耦合度降低,提高程序的可重用性,同时提高了开发的效率。
1.2 相关术语
①横切关注点
分散在每个各个模块中解决同一样的问题,如用户验证、日志管理、事务处理、数据缓存都属于横切关注点。
从每个方法中抽取出来的同一类非核心业务。在同一个项目中,我们可以使用多个横切关注点对相关方法进行多个不同方面的增强。
这个概念不是语法层面的,而是根据附加功能的逻辑上的需要:有十个附加功能,就有十个横切关注点。
②通知(增强)
增强,通俗说,就是你想要增强的功能,比如 安全,事务,日志等。
每一个横切关注点上要做的事情都需要写一个方法来实现,这样的方法就叫通知方法。
- 前置通知:在被代理的目标方法前执行
- 返回通知:在被代理的目标方法成功结束后执行
- 异常通知:在被代理的目标方法异常结束后执行
- 后置通知:在被代理的目标方法最终结束后执行
- 环绕通知:使用try…catch…finally结构围绕整个被代理的目标方法,包括上面四种通知对应的所有位置
③切面
封装通知方法的类。
④目标
被代理的目标对象。
⑤代理
向目标对象应用通知之后创建的代理对象。
⑥连接点
通俗说,就是spring允许使用通知的地方
⑦切入点
定位连接点的方式。
每个类的方法中都包含多个连接点,所以连接点是类中客观存在的事物(从逻辑上来说)。
如果把连接点看作数据库中的记录,那么切入点就是查询记录的 SQL 语句。
Spring 的 AOP 技术可以通过切入点定位到特定的连接点。要实际去增强的方法切入点通过 org.springframework.aop.Pointcut 接口进行描述,它使用类和方法作为连接点的查询条件。
2. 切入点表达式语法
2.1 语法格式
execution(权限修饰符 方法返回值 方法所在类的全类名 方法名(参数列表))
如果我们想覆盖test类中的所有方法,那么切入点表达式如下所示:
execution(* org.kkk.spring.test.*(…))
解释:
- 第一个*代表对方法权限和返回类型不限
- org.kkk.spring.test是该方法的全类名
- 第二个*代表任意方法名
- (…)代表任意参数
2.2 语法细节
-
用*号代替“权限修饰符”和“返回值”部分表示“权限修饰符”和“返回值”不限
-
在包名的部分,一个“*”号只能代表包的层次结构中的一层,表示这一层是任意的。
- 例如:*.Hello匹配com.Hello,不匹配org.kkk.Hello
-
在包名的部分,使用“*…”表示包名任意、包的层次深度任意
-
在类名的部分,类名部分整体用*号代替,表示类名任意
-
在类名的部分,可以使用*号代替类名的一部分
- 例如:*Service匹配所有名称以Service结尾的类或接口
-
在方法名部分,可以使用*号表示方法名任意
-
在方法名部分,可以使用*号代替方法名的一部分
- 例如:*Operation匹配所有方法名以Operation结尾的方法
-
在方法参数列表部分,使用(…)表示参数列表任意
-
在方法参数列表部分,使用(int,…)表示参数列表以一个int类型的参数开头
-
在方法参数列表部分,基本数据类型和对应的包装类型是不一样的
- 切入点表达式中使用 int 和实际方法中 Integer 是不匹配的
-
在方法返回值部分,如果想要明确指定一个返回值类型,那么必须同时写明权限修饰符
- 例如:execution(public int …Service.(…, int)) 正确
例如:execution( int *…Service.(…, int)) 错误
- 例如:execution(public int …Service.(…, int)) 正确