Spring 源码学习(4) —— 动态AOP使用示例

在实际工作中, 此bean可能是满足业务需要的核心逻辑, 例如test()方法中可能会封装着某个核心业务, 如果在test()方法前后加入日志来跟踪调试, 直接修改源码并不符合面向对象的设计模式, 而随意改动源码也会造成一定的风险。不用怕, Spring为此提供了解决方案。

1.创建用于拦截的bean

 1 /**
 2  * @filename: AopBean.java
 3  * @desc AopBean 测试类
 4  * @author: Wang Chinda
 5  * @blog http://www.cnblogs.com/goodcheap
 6  * @date: 2018-05-25 11:32
 7  * @version: v1.0
 8  * @copyright: Copyright © 2018 ༄ྂ祸ྂྂ害ོ༘苍ྂྂ生ོ༘࿐ྂ 版权所有
 9  * @modify_history: -
10  * 20180525   Wang Chinda   create
11  * 20180525   Wang Chinda   modify   method()
12  */
13 package com.itdoc.learn.source.aop.demo;
14 
15 /**
16  * @desc AopBean 测试类
17  * @author Wang Chinda
18  * @create 2018-05-25 11:32
19  */
20 public class AopBean {
21 
22     public void testMethod() {
23         System.out.println("this is aop test method!");
24     }
25 }

2.创建Advisor

Spring中摒弃了最原始的繁杂配置方式而采用@Aspect注解对POJO进行标注, 使AOP的工作大大简化, 但是要注意, 使用@Aspect注解需要导入第三方依赖aspectjweaver。

 1 /**
 2  * @filename: AspectJTest.java
 3  * @desc aop切面控制
 4  * @author: Wang Chinda
 5  * @blog http://www.cnblogs.com/goodcheap
 6  * @date: 2018-05-25 11:33
 7  * @version: v1.0
 8  * @copyright: Copyright © 2018 ༄ྂ祸ྂྂ害ོ༘苍ྂྂ生ོ༘࿐ྂ 版权所有
 9  * @modify_history: -
10  * 20180525   Wang Chinda   create
11  * 20180525   Wang Chinda   modify   method()
12  */
13 package com.itdoc.learn.source.aop.demo;
14 
15 
16 import org.aspectj.lang.ProceedingJoinPoint;
17 import org.aspectj.lang.annotation.*;
18 
19 /**
20  * @desc aop切面控制, 创建Advisor
21  * @author Wang Chinda
22  * @create 2018-05-25 11:33
23  */
24 @Aspect
25 public class AspectJTest {
26 
27     @Pointcut("execution(* *.*(..))")
28     public void test() {
29     }
30 
31     @Before("test()")
32     public void beforeTest() {
33         System.out.println("beforeTest");
34     }
35 
36     @After("test()")
37     public void afterTest() {
38         System.out.println("afterTest");
39     }
40 
41     @Around("test()")
42     public Object aroundTest(ProceedingJoinPoint point) {
43         Object obj = null;
44         try {
45             System.out.println("前置通知");
46             obj = point.proceed();
47             System.out.println("返回通知");
48         } catch (Throwable throwable) {
49             throwable.printStackTrace();
50             System.out.println("异常通知");
51         } finally {
52             System.out.println("后置通知");
53         }
54         return obj;
55     }
56 
57 }

3.引入第三方依赖:

  1 <?xml version="1.0" encoding="UTF-8"?>
  2 
  3 <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  4          xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
  5     <modelVersion>4.0.0</modelVersion>
  6 
  7     <groupId>com.itdoc.learn.source</groupId>
  8     <artifactId>spring-01</artifactId>
  9     <version>1.0-SNAPSHOT</version>
 10 
 11     <name>spring-01</name>
 12 
 13 
 14     <properties>
 15         <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
 16         <maven.compiler.source>1.7</maven.compiler.source>
 17         <maven.compiler.target>1.7</maven.compiler.target>
 18     </properties>
 19 
 20     <dependencies>
 21 
 22         <!-- https://mvnrepository.com/artifact/org.springframework/spring-web -->
 23         <dependency>
 24             <groupId>org.springframework</groupId>
 25             <artifactId>spring-web</artifactId>
 26             <version>3.2.3.RELEASE</version>
 27         </dependency>
 28 
 29         <!-- https://mvnrepository.com/artifact/org.apache.commons/commons-lang3 -->
 30         <dependency>
 31             <groupId>org.apache.commons</groupId>
 32             <artifactId>commons-lang3</artifactId>
 33             <version>3.4</version>
 34         </dependency>
 35 
 36         <!-- https://mvnrepository.com/artifact/org.aspectj/aspectjweaver -->
 37         <!-- aop功能 @Aspect 注解依赖包 -->
 38         <dependency>
 39             <groupId>org.aspectj</groupId>
 40             <artifactId>aspectjweaver</artifactId>
 41             <version>1.8.10</version>
 42         </dependency>
 43 
 44         <!-- https://mvnrepository.com/artifact/aopalliance/aopalliance -->
 45         <!--<dependency>-->
 46             <!--<groupId>aopalliance</groupId>-->
 47             <!--<artifactId>aopalliance</artifactId>-->
 48             <!--<version>1.0</version>-->
 49         <!--</dependency>-->
 50 
 51 
 52         <!-- https://mvnrepository.com/artifact/org.aspectj/aspectjrt -->
 53         <!--<dependency>-->
 54             <!--<groupId>org.aspectj</groupId>-->
 55             <!--<artifactId>aspectjrt</artifactId>-->
 56             <!--<version>1.8.9</version>-->
 57         <!--</dependency>-->
 58 
 59 
 60 
 61         <!-- https://mvnrepository.com/artifact/javax.inject/javax.inject -->
 62         <dependency>
 63             <groupId>javax.inject</groupId>
 64             <artifactId>javax.inject</artifactId>
 65             <version>1</version>
 66         </dependency>
 67 
 68         <dependency>
 69             <groupId>junit</groupId>
 70             <artifactId>junit</artifactId>
 71             <version>RELEASE</version>
 72         </dependency>
 73     </dependencies>
 74 
 75     <build>
 76         <pluginManagement><!-- lock down plugins versions to avoid using Maven defaults (may be moved to parent pom) -->
 77             <plugins>
 78                 <plugin>
 79                     <artifactId>maven-clean-plugin</artifactId>
 80                     <version>3.0.0</version>
 81                 </plugin>
 82                 <!-- see http://maven.apache.org/ref/current/maven-core/default-bindings.html#Plugin_bindings_for_jar_packaging -->
 83                 <plugin>
 84                     <artifactId>maven-resources-plugin</artifactId>
 85                     <version>3.0.2</version>
 86                 </plugin>
 87                 <plugin>
 88                     <artifactId>maven-compiler-plugin</artifactId>
 89                     <version>3.7.0</version>
 90                 </plugin>
 91                 <plugin>
 92                     <artifactId>maven-surefire-plugin</artifactId>
 93                     <version>2.20.1</version>
 94                 </plugin>
 95                 <plugin>
 96                     <artifactId>maven-jar-plugin</artifactId>
 97                     <version>3.0.2</version>
 98                 </plugin>
 99                 <plugin>
100                     <artifactId>maven-install-plugin</artifactId>
101                     <version>2.5.2</version>
102                 </plugin>
103                 <plugin>
104                     <artifactId>maven-deploy-plugin</artifactId>
105                     <version>2.8.2</version>
106                 </plugin>
107             </plugins>
108         </pluginManagement>
109     </build>
110 </project>

4.配置aop:在xml中开启aop功能

 1 <?xml version="1.0" encoding="UTF-8"?>
 2 <beans xmlns="http://www.springframework.org/schema/beans"
 3        xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
 4        xmlns:aop="http://www.springframework.org/schema/aop"
 5        xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
 6        http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd">
 7 
 8     <!-- 使 AspectJ 注解起作用, 自动为匹配的类生成代理对象 -->
 9     <aop:aspectj-autoproxy/>
10 
11     <bean id="test" class="com.itdoc.learn.source.aop.demo.AopBean"/>
12     <bean class="com.itdoc.learn.source.aop.demo.AspectJTest"/>
13 </beans>

5.测试

 1 /**
 2  * @filename: AopDemoClient.java
 3  * @desc
 4  * @author: Wang Chinda
 5  * @blog http://www.cnblogs.com/goodcheap
 6  * @date: 2018-05-25 12:00
 7  * @version: v1.0
 8  * @copyright: Copyright © 2018 ༄ྂ祸ྂྂ害ོ༘苍ྂྂ生ོ༘࿐ྂ 版权所有
 9  * @modify_history: -
10  * 20180525   Wang Chinda   create
11  * 20180525   Wang Chinda   modify   method()
12  */
13 package com.itdoc.learn.source.aop.demo;
14 
15 import org.springframework.context.ApplicationContext;
16 import org.springframework.context.support.ClassPathXmlApplicationContext;
17 
18 /**
19  * @desc
20  * @author Wang Chinda
21  * @create 2018-05-25 12:00
22  */
23 public class AopDemoClient {
24     public static void main(String[] args) {
25         ApplicationContext app = new ClassPathXmlApplicationContext("test/aopDemo.xml");
26         AopBean aopBean = (AopBean) app.getBean("test");
27         aopBean.testMethod();
28     }
29 }

控制台输出:

五月 25, 2018 3:07:21 下午 org.springframework.context.support.AbstractApplicationContext prepareRefresh
信息: Refreshing org.springframework.context.support.ClassPathXmlApplicationContext@1e67b872: startup date [Fri May 25 15:07:21 CST 2018]; root of context hierarchy
五月 25, 2018 3:07:21 下午 org.springframework.beans.factory.xml.XmlBeanDefinitionReader loadBeanDefinitions
信息: Loading XML bean definitions from class path resource [test/aopDemo.xml]
五月 25, 2018 3:07:22 下午 org.springframework.beans.factory.support.DefaultListableBeanFactory preInstantiateSingletons
信息: Pre-instantiating singletons in org.springframework.beans.factory.support.DefaultListableBeanFactory@5c30a9b0: defining beans [org.springframework.aop.config.internalAutoProxyCreator,test,com.itdoc.learn.source.aop.demo.AspectJTest#0]; root of factory hierarchy
前置通知
beforeTest
this is aop test method!
返回通知
后置通知
afterTest

 GitHub源码:https://github.com/wcd19901010/spring-01



原文地址:https://www.cnblogs.com/chinda/p/9088764.html