本文最后更新于:June 15, 2022 pm
Spring 是目前主流的 Java Web 开发框架,是 Java 世界最为成功的框架。Spring框架是由于软件开发的复杂性而创建的。Spring使用的是基本的JavaBean来完成以前只可能由EJB完成的事情。然而,Spring的用途不仅仅限于服务器端的开发。从简单性、可测试性和松耦合性角度而言,绝大部分Java应用都可以从Spring中受益。该框架是一个轻量级的开源框架,具有很高的凝聚力和吸引力。Spring 框架不局限于服务器端的开发。从简单性、可测试性和松耦合的角度而言,任何 Java 应用都可以从 Spring 中受益。Spring 框架还是一个超级粘合平台,除了自己提供功能外,还提供粘合其他技术和框架的能力。
目录
ProxyFactory 目标类:
package com.SpringTestAnnotation.TestValue;import org.springframework.stereotype.Component;@Component public class OrderS { }
使用:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 package com.SpringTestAnnotation.TestValue;import org.springframework.beans.factory.annotation.Autowired;import org.springframework.stereotype.Component;@Component public class Per { @Autowired private OrderS orderS; public void show () { System.out.println("Per show " +orderS); } }
测试:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 package com.SpringTestAnnotation;import com.SpringTestAnnotation.TestValue.Per;import org.aopalliance.intercept.MethodInterceptor;import org.aopalliance.intercept.MethodInvocation;import org.springframework.aop.framework.ProxyFactory;import org.springframework.context.annotation.AnnotationConfigApplicationContext;public class TestAnnotation { public static void main (String[] args) { AnnotationConfigApplicationContext applicationContext = new AnnotationConfigApplicationContext(TestConfig.class); Per per = new Per(); ProxyFactory proxyFactory = new ProxyFactory(); proxyFactory.setTarget(per); proxyFactory.addAdvice(new MethodInterceptor() { @Override public Object invoke (MethodInvocation invocation) throws Throwable { System.out.println("before dong" ); Object proceed = invocation.proceed(); System.out.println("after dong" ); return proceed; } }); Per proxy = (Per) proxyFactory.getProxy(); proxy.show(); } }
addAdvice就表示代理逻辑。
输出结果:
before dong Per show null after dong
ProxyFactoryBean 相同代码不写,同上。
配置类:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 package com.SpringTestAnnotation;import com.SpringTestAnnotation.TestValue.Per;import org.aopalliance.intercept.MethodInterceptor;import org.aopalliance.intercept.MethodInvocation;import org.springframework.aop.framework.ProxyFactoryBean;import org.springframework.context.annotation.Bean;import org.springframework.context.annotation.ComponentScan;@ComponentScan(value = "com.SpringTestAnnotation") public class TestConfig { @Bean public ProxyFactoryBean perProxy () { Per per = new Per(); ProxyFactoryBean proxyFactoryBean = new ProxyFactoryBean(); proxyFactoryBean.setTarget(per); proxyFactoryBean.addAdvice(new MethodInterceptor() { @Override public Object invoke (MethodInvocation invocation) throws Throwable { System.out.println("before dong" ); Object proceed = invocation.proceed(); System.out.println("after dong" ); return proceed; } }); return proxyFactoryBean; } }
测试:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 package com.SpringTestAnnotation;import com.SpringTestAnnotation.TestValue.Per;import org.springframework.context.annotation.AnnotationConfigApplicationContext;public class TestAnnotation { public static void main (String[] args) { AnnotationConfigApplicationContext applicationContext = new AnnotationConfigApplicationContext(TestConfig.class); Per orderS = (Per) applicationContext.getBean("perProxy" ); orderS.show(); } }
输出结果:
before dong Per show null after dong
BeanNameAutoProxyCreator 配置类:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 package com.SpringTestAnnotation;import org.aopalliance.intercept.MethodInterceptor;import org.aopalliance.intercept.MethodInvocation;import org.springframework.aop.framework.autoproxy.BeanNameAutoProxyCreator;import org.springframework.context.annotation.Bean;import org.springframework.context.annotation.ComponentScan;@ComponentScan(value = "com.SpringTestAnnotation") public class TestConfig { @Bean public MethodInterceptor totheforAdvice () { return new MethodInterceptor() { @Override public Object invoke (MethodInvocation invocation) throws Throwable { System.out.println("before dong" ); Object proceed = invocation.proceed(); System.out.println("after dong" ); return proceed; } }; } @Bean public BeanNameAutoProxyCreator beanNameAutoProxyCreator () { BeanNameAutoProxyCreator beanNameAutoProxyCreator = new BeanNameAutoProxyCreator(); beanNameAutoProxyCreator.setBeanNames("per*" ); beanNameAutoProxyCreator.setInterceptorNames("totheforAdvice" ); beanNameAutoProxyCreator.setProxyTargetClass(true ); return beanNameAutoProxyCreator; } }
这里需要注意两个点:
setBeanNames(“per*“):表示匹配前缀以per的所有对象,并为其创建代理对象。
setInterceptorNames(“totheforAdvice”):这里的totheforAdvice为上面Bean的方法的名称。
测试:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 package com.SpringTestAnnotation;import com.SpringTestAnnotation.TestValue.Per;import org.springframework.context.annotation.AnnotationConfigApplicationContext;public class TestAnnotation { public static void main (String[] args) { AnnotationConfigApplicationContext applicationContext = new AnnotationConfigApplicationContext(TestConfig.class); Per orderS = (Per) applicationContext.getBean("per" ); orderS.show(); } }
输出结果:
before dong Per show com.SpringTestAnnotation.TestValue.OrderS@7f010382 after dong
配置类:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 package com.SpringTestAnnotation;import org.aopalliance.intercept.MethodInterceptor;import org.aopalliance.intercept.MethodInvocation;import org.springframework.aop.framework.autoproxy.DefaultAdvisorAutoProxyCreator;import org.springframework.aop.support.DefaultPointcutAdvisor;import org.springframework.aop.support.NameMatchMethodPointcut;import org.springframework.context.annotation.Bean;import org.springframework.context.annotation.ComponentScan;@ComponentScan(value = "com.SpringTestAnnotation") public class TestConfig { @Bean public DefaultPointcutAdvisor defaultPointcutAdvisor () { NameMatchMethodPointcut nameMatchMethodPointcut = new NameMatchMethodPointcut(); nameMatchMethodPointcut.setMappedName("show" ); DefaultPointcutAdvisor defaultPointcutAdvisor = new DefaultPointcutAdvisor(); defaultPointcutAdvisor.setPointcut(nameMatchMethodPointcut); defaultPointcutAdvisor.setAdvice(new MethodInterceptor() { @Override public Object invoke (MethodInvocation invocation) throws Throwable { System.out.println("before dong" ); Object proceed = invocation.proceed(); System.out.println("after dong" ); return proceed; } }); return defaultPointcutAdvisor; } @Bean public DefaultAdvisorAutoProxyCreator defaultAdvisorAutoProxyCreator () { DefaultAdvisorAutoProxyCreator defaultAdvisorAutoProxyCreator = new DefaultAdvisorAutoProxyCreator(); return defaultAdvisorAutoProxyCreator; } }
注意:setMappedName(“show”);中的show指定的方法的名称。对所有的有此方法的Bean,都会在执行时进行AOP。
测试:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 package com.SpringTestAnnotation;import com.SpringTestAnnotation.TestValue.Per;import org.springframework.context.annotation.AnnotationConfigApplicationContext;public class TestAnnotation { public static void main (String[] args) { AnnotationConfigApplicationContext applicationContext = new AnnotationConfigApplicationContext(TestConfig.class); Per orderS = (Per) applicationContext.getBean("per" ); orderS.show(); } }
结果输出:
before dong Per show com.SpringTestAnnotation.TestValue.OrderS@3967e60c after dong
从上面可以看出,我们只是定义了一个DefaultAdvisorAutoProxyCreator类型的Bean,所以,在配置类中可以直接使用注解@Import实现。如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 package com.SpringTestAnnotation;import org.aopalliance.intercept.MethodInterceptor;import org.aopalliance.intercept.MethodInvocation;import org.springframework.aop.framework.autoproxy.DefaultAdvisorAutoProxyCreator;import org.springframework.aop.support.DefaultPointcutAdvisor;import org.springframework.aop.support.NameMatchMethodPointcut;import org.springframework.context.annotation.Bean;import org.springframework.context.annotation.ComponentScan;import org.springframework.context.annotation.Import;@ComponentScan(value = "com.SpringTestAnnotation") @Import(DefaultAdvisorAutoProxyCreator.class) public class TestConfig { @Bean public DefaultPointcutAdvisor defaultPointcutAdvisor () { NameMatchMethodPointcut nameMatchMethodPointcut = new NameMatchMethodPointcut(); nameMatchMethodPointcut.setMappedName("show" ); DefaultPointcutAdvisor defaultPointcutAdvisor = new DefaultPointcutAdvisor(); defaultPointcutAdvisor.setPointcut(nameMatchMethodPointcut); defaultPointcutAdvisor.setAdvice(new MethodInterceptor() { @Override public Object invoke (MethodInvocation invocation) throws Throwable { System.out.println("before dong" ); Object proceed = invocation.proceed(); System.out.println("after dong" ); return proceed; } }); return defaultPointcutAdvisor; } }
实现效果一样。