回到AOP:使用around通知的积极方面
在第一部分,您看到了如何使用Spring AOP来实现跟踪和记录方面。跟踪和记录都是“消极”方面,因为它们的出现并不会对应用程序的其他行为产生影响。它们都使用了消极的before和after形式的通知。
但是如果您希望改变应用程序的常规行为呢?例如说,您希望重写一个方法?这样的话,您就需要使用更积极的around形式的通知。
第一部分的简单例子应用程序包括IbusinessLogic接口、BusinessLogic类和MainApplication类,如下所示:
public interface IBusinessLogic
{
public void foo();
}
public class BusinessLogic
implements IBusinessLogic
{
public void foo()
{
System.out.println(
"Inside BusinessLogic.foo()");
}
}
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.FileSystemXmlApplicationContext;
public class MainApplication
{
public static void main(String [] args)
{
// Read the configuration file
ApplicationContext ctx =
new FileSystemXmlApplicationContext(
"springconfig.xml");
//Instantiate an object
IBusinessLogic testObject =
(IBusinessLogic) ctx.getBean(
"businesslogicbean");
// Execute the public
// method of the bean
testObject.foo();
}
}
要对一个BusinessLogic类的实例彻底重写对foo()方法的调用,需要创建around通知,如下面的AroundAdvice类所示:
import org.aopalliance.intercept.MethodInvocation;
import org.aopalliance.intercept.MethodInterceptor;
public class AroundAdvice
implements MethodInterceptor
{
public Object invoke(
MethodInvocation invocation)
throws Throwable
{
System.out.println(
"Hello world! (by " +
this.getClass().getName() +
")");
return null;
}
}
要在Spring中用作around通知,AroundAdvice类必须实现MethodInterceptor接口和它的invoke (..)方法。每当截获到方法的重写,invoke(..)方法就会被调用。最后一步是改变包含在应用程序的springconfig.xml文件中的 Spring运行时配置,以便可以对应用程序应用AroundAdvice。
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE beans PUBLIC "-//SPRING//DTD BEAN//EN"
"http://www.springframework.org/dtd/spring-beans.dtd">
<beans>
<!-- Bean configuration -->
<bean id="businesslogicbean"
class="org.springframework.aop.framework.ProxyFactoryBean">
<property name="proxyInterfaces">
<value>IBusinessLogic</value>
</property>
<property name="target">
<ref local="beanTarget"/>
</property>
<property name="interceptorNames">
<list>
<value>theAroundAdvisor</value>
</list>
</property>
</bean>
<!-- Bean Classes -->
<bean id="beanTarget"
class="BusinessLogic"/>
<!-- Advisor pointcut definition for around advice -->
<bean id="theAroundAdvisor"
class="org.springframework.aop.support.RegexpMethodPointcutAdvisor">
<property name="advice">
<ref local="theAroundAdvice"/>
</property>
<property name="pattern">
<value>.*</value>
</property>
</bean>
<!-- Advice classes -->
<bean id="theAroundAdvice"
class="AroundAdvice"/>
</beans>
根据该springconfig.xml配置文件,theAroundAdvisor截获所有对BusinessLogic类的方法的调用。接下来,theAroundAdvisor被关联到theAroundAdvice,表明当截获一个方法时,就应该使用在AroundAdvice类中指定的通知。既然已经指定了around通知的正确配置,下一次执行MainApplication类时,BusinessLogic bean的foo()方法就会被截获并重写,如图3所示:

图3. 使用around通知重写对BusinessLogic类中的foo()方法的调用
