spring——AOP面向切面编程——基于XML的AspectJ AOP开发(转载)
我们可以在 Spring 项目中通过 XML 配置,对切面(Aspect 或 Advisor)、切点(PointCut)以及通知(Advice)进行定义和管理,以实现基于 AspectJ 的 AOP 开发。
Spring 提供了基于 XML 的 AOP 支持,并提供了一个名为“aop”的命名空间,该命名空间提供了一个 <aop:config> 元素。
- 在 Spring 配置中,所有的切面信息(切面、切点、通知)都必须定义在 <aop:config> 元素中;
- 在 Spring 配置中,可以使用多个 <aop:config>。
- 每一个 <aop:config> 元素内可以包含 3 个子元素: pointcut、advisor 和 aspect ,这些子元素必须按照这个顺序进行声明。
引入 aop 命名空间
首先,我们需要在 XML 配置文件中导入 Spring aop 命名空间的约束,如下所示。
示例
下面我们通过一个示例来演示下 Spring 集成 AspectJ 基于 XML 实现 AOP 开发。
1. 新建一个名为 my-spring-asepctj-demo 的 Java 项目,并将以下依赖 Jar 包导入到该项目中。
- commons-logging-1.2.jar
- spring-aop-5.3.13.jar
- spring-aspects-5.3.13.jar
- spring-beans-5.3.13.jar
- spring-context-5.3.13.jar
- spring-core-5.3.13.jar
- spring-expression-5.3.13.jar
- aspectjweaver-1.9.7.jar
2. 在 net.biancheng.c.dao 包下,创建一个名为 OrderDao 的接口,代码如下。
3. 在 net.biancheng.c.dao.impl 包下,创建 OrderDao 的实现类 OrderDaoImpl,代码如下。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
|
package net.biancheng.c.dao.impl; import net.biancheng.c.dao.OrderDao; public class OrderDaoImpl implements OrderDao { @Override public void add() { System.out.println( "正在执行 OrderDao 中的 add() 方法" ); } @Override public void delete() { System.out.println( "正在执行 OrderDao 中的 delete() 方法" ); } @Override public int modify() { System.out.println( "正在执行 OrderDao 中的 modify() 方法" ); return 1 ; } @Override public void get() { //异常 int a = 10 / 0 ; System.out.println( "正在执行 OrderDao 中的 get() 方法" ); } } |
4. 在 net.biancheng.c 包下,创建一个名为 MyOrderAspect 的类,代码如下。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
|
package net.biancheng.c; import org.aspectj.lang.ProceedingJoinPoint; public class MyOrderAspect { public void before() { System.out.println( "前置增强……" ); } public void after() { System.out.println( "最终增强……" ); } public void around(ProceedingJoinPoint proceedingJoinPoint) throws Throwable { System.out.println( "环绕增强---前……" ); proceedingJoinPoint.proceed(); System.out.println( "环绕增强---后……" ); } public void afterThrow(Throwable exception) { System.out.println( "异常增强…… 异常信息为:" + exception.getMessage()); } public void afterReturning(Object returnValue) { System.out.println( "后置返回增强…… 方法返回值为:" + returnValue); } } |
5. 在 src 目录下创建一个 Spring 配置文件 Beans2.xml,配置内容如下。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
|
<?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:context= "http://www.springframework.org/schema/context" xmlns:aop= "http://www.springframework.org/schema/aop" xsi:schemaLocation="http: //www.springframework.org/schema/beans http: //www.springframework.org/schema/beans/spring-beans.xsd http: //www.springframework.org/schema/context http: //www.springframework.org/schema/context/spring-context.xsd http: //www.springframework.org/schema/aop http: //www.springframework.org/schema/aop/spring-aop.xsd"> <!--定义 Bean--> <bean id= "orderDao" class = "net.biancheng.c.dao.impl.OrderDaoImpl" ></bean> <!--定义切面--> <bean id= "myOrderAspect" class = "net.biancheng.c.MyOrderAspect" ></bean> <aop:config> <aop:pointcut id= "beforePointCut" expression= "execution(* net.biancheng.c.dao.OrderDao.add(..))" /> <aop:pointcut id= "throwPointCut" expression= "execution(* net.biancheng.c.dao.OrderDao.get(..))" /> <aop:pointcut id= "afterReturnPointCut" expression= "execution(* net.biancheng.c.dao.OrderDao.modify(..))" /> <aop:pointcut id= "afterPointCut" expression= "execution(* net.biancheng.c.dao.OrderDao.*(..))" /> <aop:aspect ref= "myOrderAspect" > <!--前置增强--> <aop:before method= "before" pointcut-ref= "beforePointCut" ></aop:before> <!--后置返回增强--> <aop:after-returning method= "afterReturning" pointcut-ref= "afterReturnPointCut" returning= "returnValue" ></aop:after-returning> <!--异常通知--> <aop:after-throwing method= "afterThrow" pointcut-ref= "throwPointCut" throwing= "exception" ></aop:after-throwing> <!--最终通知--> <aop:after method= "after" pointcut-ref= "afterPointCut" ></aop:after> <!--环绕通知--> <aop:around method= "around" pointcut-ref= "beforePointCut" ></aop:around> </aop:aspect> </aop:config> </beans> |