您的位置:首页 > 编程语言 > Java开发

spring心得9--自动代理知识点讲解及案例分析

2013-05-07 12:35 381 查看
1.自动代理知识点介绍


自动代理的产生原因:


有许多类需要通知时,显式的创建每个代理就会显得很笨拙。spring有一个自动代理机制,它可以让容器为我们产生代理。自动代理类分两种,分别是以下两种:

BeanNameAutoProxyCreator、DefaultAdvisorAutoProxyCreator


BeanNameAutoProxyCreator


该类为匹配一系列名字的Bean自动创建代理。这种名字匹配和前面讲到的NameMethodMatherPointcut类似,他也允许在名字的两端进行通配符。通常为符合相同命名规则的bean应用一个或一组切面。


DefaultAdvisorAutoProxyCreator


该类实现了BeanPostProcessor接口。当应用上下文读入所有的Bean的配置信息后,该类将扫描上下文,寻找所有的Advisor。他将这些Advisor应用到所有符合切入点的Bean中。很重要的一点是这个代理创建器只能与Advisor配合使用。该类需要Advisor来知道哪些Bean需要通知。

2.自动代理案例分析

1)BeanNameAutoProxyCreator类自动代理案例剖析

该案例的讲解是基于前面讲各种通知的例子,这里只列出配置文件和测试类(该测试一下测试了以下三种自动代理案例的知识点测试),如果需要参看抽象主题和真实主题,可以去看上一篇博客spring各种通知的案例讲解

sprin配置文件:spring-byNameAutoAdvisor.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"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd"> 
<!-- 创建前置通知 -->
<bean id="beforeAdvice" class="www.csdn.spring.proxy.advice.BeforeAdvice"/>
<!-- 创建后置通知 -->
<bean id="afterAdvice" class="www.csdn.spring.proxy.advice.AfterAdvice"/>
<!-- 创建环绕通知 -->
<bean id="aroundAdvice" class="www.csdn.spring.proxy.advice.AroundAdvice"/>
<!-- 创建异常通知 -->
<bean id="throwAdvice" class="www.csdn.spring.proxy.advice.ThrowAdvice"/>

<!-- 真实主题   目标对象 -->
<bean id="sayServiceImpl" class="www.csdn.spring.proxy.advice.SayServiceImpl"/>

<!-- 配置自动代理操作 -->
<bean class="org.springframework.aop.framework.autoproxy.BeanNameAutoProxyCreator">
<property name="beanNames">
<list>
<!-- <value>*ServiceImpl</value> -->
<value>*Service*</value>
</list>
</property>
<property name="interceptorNames">
<array>
<value>aroundAdvice</value>
</array>
</property>
</bean>
</beans>


测试类
AutoAdvisorTest.java

package www.csdn.spring.proxy.advice;

import org.junit.Test;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;

public class AutoAdvisorTest {

@Test
public void testAdvice() {
// 默认自动代理测试
ApplicationContext context = new ClassPathXmlApplicationContext(
"spring-default*.xml");
/*
* 自动代理测试 ApplicationContext context = new
* ClassPathXmlApplicationContext( "spring-byNameAuto*.xml");
*/
SayService sayService = context.getBean("sayServiceImpl",
SayService.class);
sayService.say("嗨!杨凯!");
}
}


2) DefaultAdvisorAutoProxyCreator类自动代理基于静态切入点案例分析

sprin配置文件:spring-defaultStaticAutoAdvisor.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"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd"> 
<!-- 创建前置通知 -->
<bean id="beforeAdvice" class="www.csdn.spring.proxy.advice.BeforeAdvice"/>
<!-- 创建后置通知 -->
<bean id="afterAdvice" class="www.csdn.spring.proxy.advice.AfterAdvice"/>
<!-- 创建环绕通知 -->
<bean id="aroundAdvice" class="www.csdn.spring.proxy.advice.AroundAdvice"/>
<!-- 创建异常通知 -->
<bean id="throwAdvice" class="www.csdn.spring.proxy.advice.ThrowAdvice"/>

<!-- 静态切入点 -->
<bean id="nameMatchMethodPointcutAdvisor" class="org.springframework.aop.support.NameMatchMethodPointcutAdvisor">
<!-- 织入通知,比如环绕通知 -->
<property name="advice">
<ref bean="aroundAdvice"/>
</property>
<!-- 指明切入点 -->
<property name="mappedName">
<value>say</value>
</property>
</bean>

<!-- 真实主题   目标对象 -->
<bean id="sayServiceImpl" class="www.csdn.spring.proxy.advice.SayServiceImpl"/>

<!-- 配置默认的自动代理操作 -->
<bean class="org.springframework.aop.framework.autoproxy.DefaultAdvisorAutoProxyCreator"/>
</beans>


3) DefaultAdvisorAutoProxyCreator类自动代理基于正则切入点案例分析

sprin配置文件:spring-defaultRegAutoAdvisor.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"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd"> 
<!-- 创建环绕通知 -->
<bean id="aroundAdvice" class="www.csdn.spring.proxy.advice.AroundAdvice"/>

<!-- 静态切入点 -->
<bean id="regexpMethodPointcutAdvisor" class="org.springframework.aop.support.RegexpMethodPointcutAdvisor">
<!-- 织入通知,比如环绕通知 -->
<property name="advice">
<ref bean="aroundAdvice"/>
</property>
<!-- 指明切入点 -->
<property name="patterns">
<!-- .是通配符的意思;第一个.*代表匹配任何包名和类名 ;第二个.*代表匹配以say开头的任意方法-->
<array>
<!--
<value>.*sayH.</value>
<value>.*bye.*</value>
<value>www.*\.SayService\.sayHell.</value>
<value>.+sayH.*</value>
-->
<value>.+sayH\..+</value>
</array>
</property>
</bean>

<!-- 真实主题   目标对象 -->
<bean id="sayServiceImpl" class="www.csdn.spring.proxy.advice.SayServiceImpl"/>

<!-- 配置默认的自动代理操作 -->
<bean class="org.springframework.aop.framework.autoproxy.DefaultAdvisorAutoProxyCreator"/>
</beans>
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: