[Spring框架]Spring AOP基础入门总结二:Spring基于AspectJ的AOP的开发.

前言:  在上一篇中: [Spring框架]Spring AOP基础入门总结一. 中 我们已经知道了一个Spring AOP程序是如何开发的, 在这里呢我们将基于AspectJ来进行AOP 的总结和学习. 一, AspectJ的概述:

AspectJ是一个面向切面的框架,它扩展了Java语言。AspectJ定义了AOP语法所以它有一个专门的编译器用来生成遵守Java字节编码规范的Class文件。

Spring为了简化自身的AOP的开发,将AspectJ拿过来作为Spring自身一个AOP的开发. 二, Spring AspectJ开发实例 2.1 开发所需jar包

2.2 AspectJ 注解开发规范

2.2.1 @AspectJ提供不同的通知类型

@Before 前置通知,相当于BeforeAdvice 在执行目标方法之前完成一个操作,获得到切入点信息. @AfterReturning 后置通知,相当于AfterReturningAdvice

1 在目标方法执行之后完成一个操作,获得方法的返回值.
2 
3 @AfterReturning(value="execution(* cn.augmentum.aspectj.demo1.CustomerService+.update(..))",returning="result")
4 public void afterReturing(Object result){
5     System.out.println("后置通知============"+result);
6 }

@Around 环绕通知,相当于MethodInterceptor

1 在目标方法执行的前和执行后完成一个操作,阻止目标方法执行.
2 
3 @Around(value="execution(* cn.augmentum.aspectj.demo1.CustomerService+.delete(..))")
4 public Object around(ProceedingJoinPoint joinPoint) throws Throwable{
5     System.out.println("环绕前通知==========");
6     Object obj = joinPoint.proceed();
7     System.out.println("环绕后通知==========");
8     return obj;
9 }

@AfterThrowing抛出通知,相当于ThrowAdvice

1 在目标方法出现异常的时候,完成一个操作.获得异常信息.
2 
3 @AfterThrowing(value="execution(* cn.itcast.aspectj.demo1.CustomerService+.find(..))",throwing="e")
4 public void afterThrowing(Throwable e){
5     System.out.println("异常抛出通知========="+e.getMessage());
6 }

@After 最终final通知,不管是否异常,该通知都会执行

1 在目标方法任何情况下都会执行的操作.相当于finally中的代码.
2 
3 @After(value="execution(* cn.itcast.aspectj.demo1.CustomerService+.find(..))")
4 public void after(){
5     System.out.println("最终通知===========");
6 }

2.2.2 通过配置启用@AspectJ切面

 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
 6     http://www.springframework.org/schema/beans/spring-beans.xsd
 7     http://www.springframework.org/schema/aop
 8     http://www.springframework.org/schema/aop/spring-aop.xsd">
 9     <!-- 开启AspectJ自动代理-->    
10     <aop:aspectj-autoproxy />
11 </beans>

2.2.3 在通知中通过value属性定义切点

通过execution函数,可以定义切点的方法切入 语法: execution(<访问修饰符>?<返回类型><方法名>(<参数>)<异常>) 例如   匹配所有类public方法 execution(public * *(..))   匹配指定包下所有类方法 execution(* cn.itcast.dao.*(..)) 不包含子包   execution(* cn.itcast.dao..*(..)) ..*表示包、子孙包下所有类   匹配指定类所有方法 execution(* cn.itcast.service.UserService.*(..))   匹配实现特定接口所有类方法 execution(* cn.itcast.dao.GenericDAO+.*(..))   匹配所有save开头的方法 execution(* save*(..))

2.2.4 AspectJ的切入点:

1 统一管理切入点的表达式.
2 @Pointcut(value="execution(* cn.itcast.aspectj.demo1.CustomerService+.find(..))")
3 private void myPointcut1(){} //这个类没有实际用途, 只是为了@Pointcut 注解

2.2.6 Aspect和Advisor的区别:

Advisor :传统的切面.传统切面一般都是由一个切入点和一个通知的组合. Aspect :真正意义上的切面.由多个切入点和多个通知的组合.

2.3 Spring AspctJ 基于注解模式的开发 CustomerService.java:

1 public interface CustomerService {
2 
3     public void save();
4     public Integer update();
5     public void delete();
6     public void find();
7 }

CustomerServiceImpl.java:

 1 public class CustomerServiceImpl implements CustomerService {
 2 
 3     @Override
 4     public void save() {
 5         System.out.println("保存客户...");
 6     }
 7 
 8     @Override
 9     public Integer update() {
10         System.out.println("修改客户...");
11         return 100;
12     }
13 
14     @Override
15     public void delete() {
16         System.out.println("删除客户...");
17     }
18 
19     @Override
20     public void find() {
21         System.out.println("查询客户...");
22         int d = 1 / 0;
23     }
24 
25 }

MyAspectAnno.java:

 1 /**
 2  * 自定义切面类:
 3  *
 4  */
 5 @Aspect
 6 public class MyAspectAnno {
 7 
 8     @Before(value="execution(* cn.augmentum.aspectj.demo1.CustomerService+.save(..))")
 9     public void before(JoinPoint joinPoint){
10         System.out.println("前置通知============"+joinPoint);
11     }
12     
13     @AfterReturning(value="execution(* cn.augmentum.aspectj.demo1.CustomerService+.update(..))",returning="result")
14     public void afterReturing(Object result){
15         System.out.println("后置通知============"+result);
16     }
17     
18     @Around(value="execution(* cn.augmentum.aspectj.demo1.CustomerService+.delete(..))")
19     public Object around(ProceedingJoinPoint joinPoint) throws Throwable{
20         System.out.println("环绕前通知==========");
21         Object obj = joinPoint.proceed();
22         System.out.println("环绕后通知==========");
23         return obj;
24     }
25     
26     @AfterThrowing(value="MyAspectAnno.myPointcut1()",throwing="e")
27     public void afterThrowing(Throwable e){
28         System.out.println("异常抛出通知========="+e.getMessage());
29     }
30     
31     @After(value="MyAspectAnno.myPointcut1()")
32     public void after(){
33         System.out.println("最终通知===========");
34     }
35     
36     @Pointcut(value="execution(* cn.augmentum.aspectj.demo1.CustomerService+.find(..))")
37     private void myPointcut1(){}
38 }

SpringDemo.java 测试类:

 1 @RunWith(SpringJUnit4ClassRunner.class)
 2 @ContextConfiguration("classpath:applicationContext.xml")
 3 public class SpringDemo1 {
 4 
 5     @Resource(name = "customerService")
 6     private CustomerService customerService;
 7 
 8     @Test
 9     public void demo1() {
10         customerService.save();
11         customerService.update();
12         customerService.delete();
13         customerService.find();
14     }
15 }

applicationContext.xml 配置文件:

 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="
 6 http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
 7 http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd">
 8     
 9     <!-- 使用注解完成AOP的开发 -->
10     <aop:aspectj-autoproxy/>
11     
12     <!-- 目标对象 -->
13     <bean id="customerService" class="cn.augmentum.aspectj.demo1.CustomerServiceImpl"/>
14 
15     <!-- 配置切面 -->
16     <bean id="myAspectAnno" class="cn.augmentum.aspectj.demo1.MyAspectAnno"/>
17 </beans>

2.4 Spring AspctJ 基于xml模式的开发

OrderService.java:

 1 public class OrderService {
 2     public void save(){
 3         System.out.println("保存订单...");
 4     }
 5     public Integer update(){
 6         System.out.println("修改订单...");
 7         return 200;
 8     }
 9     public void delete(){
10         System.out.println("删除订单...");
11     }
12     public void find(){
13         System.out.println("查询订单...");
14         //int d = 1/ 0;
15     }
16 }

MyAspectXml.java:

 1 public class MyAspectXml {
 2 
 3     public void before(){
 4         System.out.println("前置通知===========");
 5     }
 6     
 7     public void afterReturing(Object result){
 8         System.out.println("后置通知==========="+result);
 9     }
10     
11     public Object around(ProceedingJoinPoint joinPoint) throws Throwable{
12         System.out.println("环绕前通知==========");
13         Object obj = joinPoint.proceed();
14         System.out.println("环绕后通知==========");
15         return obj;
16     }
17     
18     public void afterThrowing(Throwable e){
19         System.out.println("异常抛出通知========"+e.getMessage());
20     }
21     
22     public void after(){
23         System.out.println("最终通知==========");
24     }
25 }

SpringDemo.java 测试类:

 1 @RunWith(SpringJUnit4ClassRunner.class)
 2 @ContextConfiguration("classpath:applicationContext.xml")
 3 public class SpringDemo2 {
 4 
 5     @Resource(name="orderService")
 6     private OrderService orderService;
 7     
 8     @Test
 9     public void demo1(){
10         orderService.save();
11         orderService.update();
12         orderService.delete();
13         orderService.find();
14     }
15 }

applicationContext.xml 配置文件:

 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="
 6 http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
 7 http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd">
 8     
 9     <!-- 配置目标类 -->
10     <bean id="orderService" class="cn.augmentum.aspectj.demo2.OrderService"></bean>
11 
12     <!-- 配置切面 -->
13     <bean id="myAspectXml" class="cn.augmentum.aspectj.demo2.MyAspectXml"></bean>
14 
15     <!-- AOP的配置 -->
16     <aop:config>
17         <aop:pointcut expression="execution(* cn.augmentum.aspectj.demo2.OrderService.save(..))" id="pointcut1"/>
18         <aop:pointcut expression="execution(* cn.augmentum.aspectj.demo2.OrderService.update(..))" id="pointcut2"/>
19         <aop:pointcut expression="execution(* cn.augmentum.aspectj.demo2.OrderService.delete(..))" id="pointcut3"/>
20         <aop:pointcut expression="execution(* cn.augmentum.aspectj.demo2.OrderService.find(..))" id="pointcut4"/>
21         <aop:aspect ref="myAspectXml">
22             <aop:before method="before" pointcut-ref="pointcut1"/>
23             <aop:after-returning method="afterReturing" pointcut-ref="pointcut2" returning="result"/>
24             <aop:around method="around" pointcut-ref="pointcut3"/>
25             <aop:after-throwing method="afterThrowing" pointcut-ref="pointcut4" throwing="e"/>
26             <aop:after method="after" pointcut-ref="pointcut4"/>
27         </aop:aspect>
28     </aop:config>
29 </beans>

OK. 到了这里Spring 基于AOP的开发也总结完了, 学习之路漫漫, 谨以此记录成长的过程! 

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

发表于

我来说两句

0 条评论
登录 后参与评论

相关文章

来自专栏C#

C#操作XML的通用方法总结

    在.net的项目开发中,经常会对XML文件进行操作,由于XML文件可以实现跨平台传输,较多的应用在数据传输中,特总结以下几种常用的XML操作方法: ...

3319
来自专栏coolblog.xyz技术专栏

Spring AOP 源码分析 - 筛选合适的通知器

从本篇文章开始,我将会对 Spring AOP 部分的源码进行分析。本文是 Spring AOP 源码分析系列文章的第二篇,本文主要分析 Spring AOP ...

1154
来自专栏xingoo, 一个梦想做发明家的程序员

【Spring实战】—— 9 AOP环绕通知

假如有这么一个场景,需要统计某个方法执行的时间,如何做呢?   典型的会想到在方法执行前记录时间,方法执行后再次记录,得出运行的时间。 如果采用Sp...

2305
来自专栏javathings

Spring 中 AOP 的实现

AOP 称为面向切面编程,在程序开发中,AOP 技术可以在不改变原有方法代码的情况下,把逻辑直接插入到方法上。Spring AOP 的大致原理主要依靠的是动态代...

1084
来自专栏xingoo, 一个梦想做发明家的程序员

【Spring实战】—— 13 AspectJ注解切面

前面了解了典型的AOP基于配置的使用方法,下面介绍下如何依赖于注解来实现AOP。 基于注解降低了配置文件的复杂程度,但是引入了程序间的耦合,其中的优劣待用户...

2345
来自专栏一英里广度一英寸深度的学习

Spring 基础

interface声明接口,接口中的函数不用public/private,但是要匹配参数和异常。

961
来自专栏Java帮帮-微信公众号-技术文章全总结

Spring-AOP

AOP引介 AOP(Aspect Oriented Programing)面向切面编程采用横向抽取机制,以取代传统的纵向继承体系的重复性代码(如性能监控/事务管...

3608
来自专栏Hongten

spring开发_Annotation_AOP_Before增强处理

http://www.cnblogs.com/hongten/gallery/image/112691.html

942
来自专栏java达人

Spring-AOP之aspectj注解方式

一、简介 1、AOP用在哪些方面:AOP能够将那些与业务无关,却为业务模块所共同调用的逻辑或责任,例如事务处理、日志管理、权限控制,异常处理等,封装起来,便于...

3778
来自专栏cs

spring aop概念以及jdk的动态代理

AOP(Aspect-Oriented Programming),又称为面向切面编程。作为一种编程思想,AOP是 OOP(Object-Oriented Pro...

1034

扫码关注云+社区

领取腾讯云代金券