springAOP-AspectJ基本配置

it2024-10-26  36

文章目录

前言业务类基于xml配置AspectJapplication.xml切面类 基于注解配置AspectJ测试

前言

1、 什么是aop? 2、需要的jar包

业务类

一个简单的业务类

package com; import org.springframework.stereotype.Repository; @Repository("userDao1") public class UserDaoImpl implements UserDao{ public void say() { System.out.println("dao"); } @Override public void addUser() { // TODO Auto-generated method stub System.out.println("添加用户"); } @Override public void delUser() { // TODO Auto-generated method stub System.out.println("删除用户"); } }

基于xml配置AspectJ

application.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:aop="http://www.springframework.org/schema/aop" xmlns:context="http://www.springframework.org/schema/context" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-4.3.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-4.3.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-4.3.xsd"> <bean id="userDao" class="com.UserDaoImpl"></bean> <bean id="myAspect" class="com.MyAspect" /> <!-- 3 aop编程 --> <aop:config> <!-- 配置切面 --> <aop:aspect ref="myAspect"> <!-- 3.1 配置切入点,通知最后增强哪些方法 execution(* com.*.*(..))" 第一个*的位置 表示返回类型 *代表所有返回类型 第二个*的位置 表示类 第三个*的位置 表示方法 (..)表示方法的参数 ..代表任意参数 --> <aop:pointcut expression="execution(* com.*.*(..))" id="myPointCut" /> <!-- 3.2 关联通知Advice和切入点pointCut --> <!-- 3.2.1 前置通知 --> <aop:before method="myBefore" pointcut-ref="myPointCut" /> <!-- 3.2.2 后置通知,在方法返回之后执行,就可以获得返回值 returning属性:用于设置后置通知的第二个参数的名称,类型是Object --> <aop:after-returning method="myAfterReturning" pointcut-ref="myPointCut" returning="returnVal" /> <!-- 3.2.3 环绕通知 --> <aop:around method="myAround" pointcut-ref="myPointCut" /> <!-- 3.2.4 抛出通知:用于处理程序发生异常--> <!-- * 注意:如果程序没有异常,将不会执行增强 --> <!-- * throwing属性:用于设置通知第二个参数的名称,类型Throwable --> <aop:after-throwing method="myAfterThrowing" pointcut-ref="myPointCut" throwing="e" /> <!-- 3.2.5 最终通知:无论程序发生任何事情,都将执行 --> <aop:after method="myAfter" pointcut-ref="myPointCut" /> </aop:aspect> </aop:config> </beans>

切面类

package com; import org.aspectj.lang.JoinPoint; import org.aspectj.lang.ProceedingJoinPoint; import org.aspectj.lang.annotation.*; import org.springframework.stereotype.Component; public class MyAspect { // 前置通知 public void myBefore(JoinPoint joinPoint) { System.out.print("前置通知 :模拟执行权限检查...,"); System.out.print("目标类是:"+joinPoint.getTarget() ); System.out.println(",被织入增强处理的目标方法为:" +joinPoint.getSignature().getName()); } // 后置通知 public void myAfterReturning(JoinPoint joinPoint) { System.out.print("后置通知:模拟记录日志...," ); System.out.println("被织入增强处理的目标方法为:" + joinPoint.getSignature().getName()); } // 环绕通知 public Object myAround(ProceedingJoinPoint proceedingJoinPoint) throws Throwable { // 开始 System.out.println("环绕开始:执行目标方法之前,模拟开启事务..."); // 执行当前目标方法 Object obj = proceedingJoinPoint.proceed(); // 结束 System.out.println("环绕结束:执行目标方法之后,模拟关闭事务..."); return obj; } // 异常通知 public void myAfterThrowing(JoinPoint joinPoint, Throwable e) { System.out.println("异常通知:" + "出错了" + e.getMessage()); } // 最终通知 public void myAfter() { System.out.println("最终通知:模拟方法结束后的释放资源..."); } }

基于注解配置AspectJ

package com; import org.aspectj.lang.JoinPoint; import org.aspectj.lang.ProceedingJoinPoint; import org.aspectj.lang.annotation.*; import org.springframework.stereotype.Component; @Aspect @Component public class MyAspect { // 定义切入点表达式 @Pointcut("execution(* com.*.*(..))") // 使用一个返回值为void、方法体为空的方法来命名切入点 private void myPointCut(){} // 前置通知 @Before("myPointCut()") public void myBefore(JoinPoint joinPoint) { System.out.print("前置通知 :模拟执行权限检查...,"); System.out.print("目标类是:"+joinPoint.getTarget() ); System.out.println(",被织入增强处理的目标方法为:" +joinPoint.getSignature().getName()); } // 后置通知 @AfterReturning(value="myPointCut()") public void myAfterReturning(JoinPoint joinPoint) { System.out.print("后置通知:模拟记录日志...," ); System.out.println("被织入增强处理的目标方法为:" + joinPoint.getSignature().getName()); } // 环绕通知 @Around("myPointCut()") public Object myAround(ProceedingJoinPoint proceedingJoinPoint) throws Throwable { // 开始 System.out.println("环绕开始:执行目标方法之前,模拟开启事务..."); // 执行当前目标方法 Object obj = proceedingJoinPoint.proceed(); // 结束 System.out.println("环绕结束:执行目标方法之后,模拟关闭事务..."); return obj; } // 异常通知 @AfterThrowing(value="myPointCut()",throwing="e") public void myAfterThrowing(JoinPoint joinPoint, Throwable e) { System.out.println("异常通知:" + "出错了" + e.getMessage()); } // 最终通知 @After("myPointCut()") public void myAfter() { System.out.println("最终通知:模拟方法结束后的释放资源..."); } } <?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:aop="http://www.springframework.org/schema/aop" xmlns:context="http://www.springframework.org/schema/context" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-4.3.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-4.3.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-4.3.xsd"> <bean id="userDao" class="com.UserDaoImpl"></bean> <!-- 扫描包,使注解生效--> <context:component-scan base-package="com" /> <!-- 启动基于注解的声明式AspectJ支持 --> <aop:aspectj-autoproxy /> </beans>

测试

package com; import org.springframework.context.ApplicationContext; import org.springframework.context.support.ClassPathXmlApplicationContext; public class Test { public static void main(String[] args) { ApplicationContext ac = new ClassPathXmlApplicationContext("applicationContext.xml"); UserDao userDao = (UserDao) ac.getBean("userDao"); userDao.addUser(); } }
最新回复(0)