[J2EE]在Spring AOP中提供的切入类型:introduction |
感觉这个类型确实不错introduction在类中你可以动态的加入一些方法,而这些方法可以放在一个通用类中,然后通过通过Spring AOP的introduction切入实现,
例子看看吧
1)假设创建了一个BookService接口及其实现方法(你自己的业务对象):
//$ID:BookService.java Created:2005-11-6 by Kerluse Bennpackage com.osiris.springaop;
public interface BookService { public String OrderComputerMagazine(String userName,String bookName); public String OrderBook(String userName,String bookName);}
//$ID:BookServiceImpl.java Created:2005-11-6 by Kerluse Bennpackage com.osiris.springaop;
public class BookServiceImpl implements BookService{ public String OrderBook(String name,String bookName) { // TODO Add your codes here String result=null; result="订购"+bookName+"成功"; return result; }
public String OrderComputerMagazine(String userName, String bookName) { // TODO Add your codes here String result=null; result="订购"+bookName+"成功"; return result; }}
2)事实上你还有很多这样的对象,现在我们希望在每个对象中添加我们的功能最后修改的时间,功能如下:
//$ID:IAuditable.java Created:2005-11-7 by Kerluse Bennpackage com.osiris.springaop.advices.intruduction;
import java.util.Date;
public interface IAuditable { void setLastModifiedDate(Date date); Date getLastModifiedDate();}
3)因为我们使用的切入类型是introduction,Spring AOP为我们提供了一个描述这种类型的接口IntroductionInterceptor,所以我们的切入实现处理,也需要实现这个接口:
//$ID:AuditableMixin.java Created:2005-11-7 by Kerluse Bennpackage com.osiris.springaop.advices.intruduction;
import java.util.Date;
import org.aopalliance.intercept.MethodInvocation;import org.springframework.aop.IntroductionInterceptor;
public class AuditableMixin implements IAuditable,IntroductionInterceptor{ private Date lastModifiedDate; public Object invoke(MethodInvocation m) throws Throwable { // TODO Add your codes here if(implementsInterface(m.getMethod().getDeclaringClass())){ return m.getMethod().invoke(this,m.getArguments()); //invoke introduced mthod,here is IAuditable }else{ return m.proceed(); //delegate other method } }
public Date getLastModifiedDate() { // TODO Add your codes here return lastModifiedDate; }
public void setLastModifiedDate(Date date) { // TODO Add your codes here lastModifiedDate=date; }
public boolean implementsInterface(Class cls) { // TODO Add your codes here return cls.isAssignableFrom(IAuditable.class); } }4)ok,现在业务对象BookService类有了,自己希望添加的处理也有了IAuditable,那就剩下使用Spring AOP框架的问题了,配置bean.xml文件:
<?xml version="1.0" encoding="UTF-8"?><!DOCTYPE beans PUBLIC "-//SPRING//DTD BEAN//EN" "http://www.springframework.org/dtd/spring-beans.dtd"><beans> <!-- Beans --> <bean id="BookServiceTarget" class="com.osiris.springaop.BookServiceImpl" singleton="false"/> <!-- introduction advice --> <bean id="AuditableMixin" class="com.osiris.springaop.advices.intruduction.AuditableMixin" singleton="false"/> <!-- Introduction advisor --> <bean id="AuditableAdvisor" class="org.springframework.aop.support.DefaultIntroductionAdvisor" singleton="false"> <constructor-arg> <ref bean="AuditableMixin"/> </constructor-arg> </bean> <bean id="BookService" class="org.springframework.aop.framework.ProxyFactoryBean"> <property name="target"> <ref bean="BookServiceTarget"/> </property> <property name="singleton"> <value>false</value> </property> <!-- force to use cglib --> <property name="proxyTargetClass"> <value>true</value> </property> <!-- introduction methods --> <property name="proxyInterfaces"> <value>com.osiris.springaop.advices.intruduction.IAuditable</value> </property> <property name="interceptorNames"> <list> <value>AuditableAdvisor</value> </list> </property> </bean> </beans>
以上就是配置文件,现在我们假设使用业务对象如下,这里是一个简单测试类:
//$ID:MainApp.java Created:2005-11-6 by Kerluse Bennpackage com.osiris.springaop;
import java.util.Date;
import org.springframework.beans.factory.BeanFactory;import org.springframework.beans.factory.xml.XmlBeanFactory;import org.springframework.core.io.FileSystemResource;
import com.osiris.springaop.advices.intruduction.IAuditable;
public class MainApp { /** * @param args * @author Kerluse Benn */ public static void main(String[] args) throws Exception{ // TODO Add your codes here BeanFactory factory=new XmlBeanFactory(new FileSystemResource("bean.xml")); BookService bookService=(BookService)factory.getBean("BookService"); IAuditable auditable=(IAuditable)bookService; System.out.print(bookService.OrderBook("Kerluse Benn","Professional C#")); auditable.setLastModifiedDate(new Date()); System.out.println(" 订购时间为"+auditable.getLastModifiedDate()); Thread.sleep(10000); System.out.print(bookService.OrderBook("Kerluse Benn","Expert j2ee one-on-one")); auditable.setLastModifiedDate(new Date()); System.out.println(" 订购时间为"+auditable.getLastModifiedDate()); } }
输出结果:订购Professional C#成功 订购时间为Mon Nov 07 11:35:20 CST 2005订购Expert j2ee one-on-one成功 订购时间为Mon Nov 07 11:35:30 CST 2005
看见上面黑体字:
IAuditable auditable=(IAuditable)bookService;
由于bookService对象事实上已经实现了IAuditable接口,通过Spring AOP的introduction切入实现,所以在运行时(熟悉C++的vtable模型的可以在大脑里想一下)可以转换,我们就可以随意添加自己的接口方法了.
|
|
|