spring aop中aspect和advisor的区别
2020-06-02 11:41 Tony、 阅读(786) 评论(0) 编辑 收藏 举报在使用xml配置spring aop的时候一般有两种方式
1 <aop:advisor> :基本上用于事务管理
2 <aop:aspect> :日志 缓存 增强等功能
实现方式
<aop:advisor> 需要实现接口
1 环绕切: 实现 MethodInterceptor 接口
2 前切:实现 MethodBeforeAdvice 接口
3 后切:实现 MethodAfterAdvice 接口
import org.springframework.aop.MethodBeforeAdvice; import java.lang.reflect.Method; public class MyBeforeAdvice implements MethodBeforeAdvice { @Override public void before(Method method, Object[] objects, Object o) throws Throwable { System.out.println("执行前置通知"); } }
import org.aopalliance.intercept.MethodInterceptor; import org.aopalliance.intercept.MethodInvocation; public class MyAround implements MethodInterceptor { @Override public Object invoke(MethodInvocation methodInvocation) throws Throwable { System.out.println("环绕-前置"); Object proceed = methodInvocation.proceed(); System.out.println("环绕-后置"); return proceed; } }
import org.springframework.aop.AfterReturningAdvice; import java.lang.reflect.Method; public class MyAfterAdvice implements AfterReturningAdvice { @Override public void afterReturning(Object o, Method method, Object[] objects, Object o1) throws Throwable { System.out.println("执行后置通知"); } }
public interface BaseServlet { void run(); }
public class MyServlet implements BaseServlet { @Override public void run() { System.out.println("MyServlet run"); } }
import com.my.servlet.BaseServlet; import org.springframework.context.support.ClassPathXmlApplicationContext; public class AopAdvisorApp { public static void main(String[] args) { ClassPathXmlApplicationContext ac = new ClassPathXmlApplicationContext("adviceApplicationContext.xml"); BaseServlet myServlet = ac.getBean("myServlet", BaseServlet.class); myServlet.run(); } }
<?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" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd"> <bean id="myServlet" class="com.my.servlet.MyServlet"/> <bean id="myBeforeAdvice" class="com.my.aop.advisor.MyBeforeAdvice"/> <bean id="myAfterAdvice" class="com.my.aop.advisor.MyAfterAdvice"/> <bean id="myAround" class="com.my.aop.advisor.MyAround"/> <!-- Aop配置 --> <aop:config> <aop:pointcut id="mypoint" expression="execution(* com.my.servlet.*.*(..))"/> <aop:advisor advice-ref="myBeforeAdvice" pointcut-ref="mypoint"/> <aop:advisor advice-ref="myAfterAdvice" pointcut-ref="mypoint"/> <aop:advisor advice-ref="myAround" pointcut-ref="mypoint"/> </aop:config> </beans>
执行结果:
六月 02, 2020 3:07:02 下午 org.springframework.context.support.ClassPathXmlApplicationContext prepareRefresh
信息: Refreshing org.springframework.context.support.ClassPathXmlApplicationContext@17f052a3: startup date [Tue Jun 02 15:07:02 CST 2020]; root of context hierarchy
六月 02, 2020 3:07:02 下午 org.springframework.beans.factory.xml.XmlBeanDefinitionReader loadBeanDefinitions
信息: Loading XML bean definitions from class path resource [advisorApplicationContext.xml]
执行前置通知
环绕-前置
MyServlet run
环绕-后置
执行后置通知
<aop:aspect> 不需要实现接口
import org.aspectj.lang.ProceedingJoinPoint; public class MyAdvice { public void before() { System.out.println("执行前置通知 before"); } public void after() { System.out.println("执行后置通知 before"); } public Object arround(ProceedingJoinPoint p) throws Throwable { System.out.println("环绕前置"); Object proceed = p.proceed(); System.out.println("环绕后置"); return proceed; } }
public class AopAspectApp { public static void main(String[] args) { ClassPathXmlApplicationContext ac = new ClassPathXmlApplicationContext("aspectApplicationContext.xml"); BaseServlet myServlet = ac.getBean("myServlet", BaseServlet.class); myServlet.run(); } }
<?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" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd"> <bean id="myServlet" class="com.my.servlet.MyServlet"/> <bean id="myAdvice" class="com.my.aop.aspect.MyAdvice"/> <!-- Aop配置 --> <aop:config> <aop:aspect ref="myAdvice"> <aop:pointcut id="mypoint" expression="execution(* com.my.servlet.*.*(..))"/> <aop:before method="before" pointcut-ref="mypoint"></aop:before> <aop:after method="after" pointcut-ref="mypoint"></aop:after> <aop:around method="arround" pointcut-ref="mypoint"></aop:around> </aop:aspect> </aop:config> </beans>
执行结果:
六月 02, 2020 3:06:24 下午 org.springframework.context.support.ClassPathXmlApplicationContext prepareRefresh
信息: Refreshing org.springframework.context.support.ClassPathXmlApplicationContext@17f052a3: startup date [Tue Jun 02 15:06:24 CST 2020]; root of context hierarchy
六月 02, 2020 3:06:24 下午 org.springframework.beans.factory.xml.XmlBeanDefinitionReader loadBeanDefinitions
信息: Loading XML bean definitions from class path resource [aspectApplicationContext.xml]
执行前置通知 before
环绕前置
MyServlet run
环绕后置
执行后置通知 before