1.我对Aop的理解是在不改变源代码的基础上,扩展新的功能。
2.概念解释:
public class User { /** * 连接点:类里面可以被增强的方法 * 切入点:类里面已经被增强的方法 * 通知/增强:扩展的功能(逻辑) * ①前置通知:在方法之前执行 * ②后置通知:在方法之后执行(出现异常也会执行) * ③异常通知:方法出现异常时候执行 * ④返回通知:在后置之前执行(出现异常不会执行,方法成功返回后执行) * ⑤环绕通知:在方法之前和之后执行(包住方法) * 切面:把增强用到方法的过程叫增强(注意是一个过程) */ public void show(){//这个show方法叫 连接点 System.out.print("我是AopUser"); } }
3.spring使用aspectj来做aop
①aspectj不是spring的一部分
②spring2.0新增了对aspectj的支持
4.实现aop有2种方式
①xml方式
②注解方式
5.导入jar包
在导入spring核心包的基础上,还需要导入aop相关的jar包
spring-aspects-5.0.5.RELEASE.jar
spring-aop-5.0.5.RELEASE.jar
aopalliance.jar
aspectjweaver-1.8.7.jar
6.常用表达式
execution(<访问修饰符>?<返回类型><方法名>(<参数>)<异常>)
(1) execution(* test3.AopUser.show1(..))
(2) execution(* test3.AopUser.*(..))
(3) execution(* *.*(..))
(4)execution(* show*(..))匹配所有show开头的方法
7.xml方式
①创建User类
@Component public class User { public void show(){ //int i=1/0;异常通知的时候用 System.out.println("我是User的show方法"); } }
②创建增强类:
public class AopMethod { public void before(){ System.out.println("我是前置通知"); } public void after(){ System.out.println("我是后置通知"); } public void last(){ System.out.println("我是最终通知"); } public void exception(){ System.out.println("我是异常通知"); } public void around(ProceedingJoinPoint proceedingJoinPoint) throws Throwable{ System.out.println("环绕通知开始"); proceedingJoinPoint.proceed(); System.out.println("环绕通知结束"); } }
③applicationContext.xml文件
<?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"> <context:component-scan base-package="test3"></context:component-scan> <bean id="AopMethod" class="test3.AopMethod"></bean> <aop:config> <aop:pointcut id="userShow" expression="execution(* test3.User.show(..))"></aop:pointcut> <aop:aspect ref="AopMethod"> <!--<aop:before method="before" pointcut-ref="userShow"></aop:before>--> <!--<aop:after method="after" pointcut-ref="userShow"></aop:after>--> <!--<aop:around method="around" pointcut-ref="userShow"></aop:around>--> <!-- <aop:after-throwing method="exception" pointcut-ref="userShow"></aop:after-throwing>--> <!--<aop:after-returning method="last" pointcut-ref="userShow"></aop:after-returning>--> </aop:aspect> </aop:config> </beans>
④测试类MainTest
public class MainTest { public static void main(String[] args){ //1.加载xml文件 ApplicationContext context=new ClassPathXmlApplicationContext("applicationContext.xml"); //2.拿到user对象,这里user是bean里面的id User user = (User)context.getBean("user"); user.show(); } }
⑤运行结果...
8.注解方式
@Before前置通知
@AfterReturning返回通知
@Around环绕通知
@AfterThrowing异常通知
@After(后置通知)最终通知(最终final通知,不管是否异常,该通知都会执行)
①在applicationContext.xml中加入
<!--开启aop操作--> <aop:aspectj-autoproxy></aop:aspectj-autoproxy>
**************************************************************************************************************************
applicationContext.xml文件:
<?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"> <context:component-scan base-package="test3"></context:component-scan> <!--开启aop操作--> <aop:aspectj-autoproxy></aop:aspectj-autoproxy> </beans>
②User类:
@Component public class User { public void show(){ //int i=1/0;//异常通知的时候用 System.out.println("我是User的show方法"); } }
③AopMethod类:
@Component @Aspect public class AopMethod { @Before(value = "execution(* test3.User.show(..))") public void before(){ System.out.println("我是前置通知"); } @AfterReturning(value = "execution(* test3.User.show(..))") public void after(){ System.out.println("我是返回通知"); } @After(value = "execution(* test3.User.show(..))") public void last(){ System.out.println("我是后置通知"); } @AfterThrowing(value = "execution(* test3.User.show(..))") public void exception(){ System.out.println("我是异常通知"); } @Around(value = "execution(* test3.User.show(..))") public void around(ProceedingJoinPoint proceedingJoinPoint) throws Throwable{ System.out.println("环绕通知开始"); proceedingJoinPoint.proceed(); System.out.println("环绕通知结束"); } }
④MainTest类:
public class MainTest { public static void main(String[] args){ //1.加载xml文件 ApplicationContext context=new ClassPathXmlApplicationContext("applicationContext.xml"); //2.拿到user对象,这里user是bean里面的id User user = (User)context.getBean("user"); user.show(); } }
⑤运行结果: