如何编写一个AOP实例demo

之前对Spring的AOP一直处于一种大概知道他的意思但是完全不知道该怎么用,面试的时候也被面试官说是“背课本”,一直觉得很难(当然深入了解后可能确实会很难),想学习无处下手,对着公司的系统看相关的配置,一直也理不清楚头绪。前几天在处理一个事务的问题时,上网查资料,感觉有点头绪,就趁热打铁学习了一下并记录下来。

这篇文章只是学习过程中的记录【 编写一个简单的demo】,并没有太多的高深的理解,但是会对以后做深入理解做一些入门的启发。

相关知识点:

AOP是一种面向切面编程的思想,在程序开发中主要用来解决一些系统层面上的问题。

      切面:通常是一个类,里面可以定义切入点和通知

      连接点:程序执行过程中明确的点,一般是方法的调用

      通知:AOP在特定的切入点上执行的增强处理,有before,after,afterReturning,afterThrowing,around

      切入点:就是带有通知的连接点,在程序中主要体现为书写切入点表达式

AOP应用场景:日志 、 缓存、权限(登陆)控制、事务管理 、监控性能(运行时间)

上面的一些概念在没有实际进行aop的编写时可能有些难以理解,不妨先看看demo在回头理解这些名词。

1.准备工作

      1.maven依赖jar包

<!-- aspectjweaver.jar这是Spring AOP所要用到的包 -->
<dependency>
    <groupId>org.aspectj</groupId>
    <artifactId>aspectjweaver</artifactId>
    <version>1.8.9</version>
</dependency>

      2.配置文件导入aop(约束)命名空间

2.编写通知类

package com.common;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Aspect;
import org.springframework.stereotype.Component;

/**
 * <p>Title: MyAdviceAop.java</p>
 * <p>Description:aop相关 </p>
 * @author Daniel
 * @date   2018年9月14日
 *
 */

//使用注解的方式可以省略xml中配置bean,保证能扫描到就行
@Aspect
@Component("myAdviceAop")
public class MyAdviceAop {
 
	//前置通知(在配置文件中通过aop:before来指定)
	public void sayHello(){
		System.out.println("Hello welcome AOP , 这句话出现在你调用的方法之前");
	}
	public void afterReturning(){
		System.out.println("这是后置通知(如果出现异常不会调用)");
	}
	public Object around(ProceedingJoinPoint pjp) throws Throwable {
		System.out.println("这是环绕通知之前的部分");
		Object proceed = pjp.proceed();//调用目标方法
		System.out.println("这是环绕通知之后的部分");
		return proceed;
	}
	public void afterException(){
		System.out.println("出事啦!出现异常了");
	}
	public void after(){
		System.out.println("这是后置通知(出现异常也会调用)");
	}
}

3.配置spring.xml文件

<!-- 使用AOP注解 -->
<aop:aspectj-autoproxy />
	
<!-- 1.配置目标对象(哪些类需要使用aop) -->
<!-- <bean name="userService" class="test.service.UserServiceImpl" ></bean> -->
<!-- 2.配置通知对象(aop调用哪些切面上的功能)-->
<!-- 两种方式:1.写下面的bean标签 ;2.在类上写@Aspect @Component("myAdviceAop")注解-->
<!-- <bean name="myAdviceAop" class="com.common.MyAdviceAop" ></bean> -->
<!-- 我是用的扫描注解的方式,所以就不配置bean了-->


<!-- 3.配置将通知织入目标对象 -->
	<aop:config>
		<!-- 配置切入点,即UserServiceImpl的所有方法,通配符的具体含义在下面的代码段里有 -->
		<aop:pointcut expression="(execution(* com..UserServiceImpl.*(..)))" id="pc"/>
		<aop:aspect ref="myAdviceAop" >
			<!-- aop:before 指定名为sayHello方法作为前置通知,以下同理 -->
			<aop:before method="sayHello" pointcut-ref="pc" />
			<!-- 后置 -->
			<aop:after-returning method="afterReturning" pointcut-ref="pc" />
			<!-- 环绕通知 -->
			<aop:around method="around" pointcut-ref="pc" />
			<!-- 异常拦截通知 -->
			<aop:after-throwing method="afterException" pointcut-ref="pc"/>
			<!-- 后置 -->
			<aop:after method="after" pointcut-ref="pc"/>
		</aop:aspect>
	</aop:config>

其中关于< aop:aspect>和< aop:advisor>两个标签的区别,暂时了解的如下:

<aop:config>
        <!-- aop标签:aop:pointcut指定核心业务,expression指定满足该条件时调用(指定切入点) -->
        <!-- 第一个*代表所有的返回值类型;第二个*代表所有的类;第三个*代表类所有方法;..代表子或者孙子包;最后一个..代表所有的参数 -->
        <aop:pointcut id="transactionPointcut" expression="(execution(* com..*Impl.*(..)))" />
    
        <!-- 在进行事务管理时,我们会使用< aop:advisor>【定义通知器(通知器跟切面一样,也包括通知和切点)】 -->
        <!-- pointcut-ref指向aop:pointcut标签,advice-ref指向tx:advice标签 -->
        <aop:advisor pointcut-ref="transactionPointcut" advice-ref="transactionAdvice" />
        
        <!-- 面向切面编程时,我们会使用< aop:aspect>【定义切面(切面包括通知和切点)】-->
        <!-- 具体事例看spring.xml -->
    </aop:config>

4.调用UserServiceImpl里的方法

在上面的例子中,当系统调用UserServiceImpl里面的方法的时候,会根据配置,依次调用MyAdviceAop里面的方法,即切面上的方法。结果如下图:

5.总结:

(就我目前的水平与理解来看)AOP就是配置在哪些方法上取执行一系列相关但是不是很重要(非业务逻辑)的方法。文章可能有不正确的地方,欢迎指正。

 

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值