Spring AOP讲解

Spring AOP:
首先看一个Spring装入bean的简单例子:
public class Customer {
    pirvate String name;
    private String age;


    ...set or get method
    ...toString method
}


public class CustomerDao {
    public Customer getCustomer() {
        return new Customer();
    }
}


public class CustomerService {
    CustomerDao customerDao;


    public setCustomerDao(CustomerDao customerDao) {
        this.customerDao = customerDao;
    }


    public Customer getCustomer() {
        customerDao.getCustomer();
    }
}


对应的applicationContext.xml配置文件:
(1)完整的xml配置文件模式(set方法注入bean)
<bean id="customerDao" class="../../CustomerDao" />
<bean id="customerService" class="../../CustomerService">
    <property name="customerDao" ref="customerDao" />
</bean>
(2)使用自动扫描组件的模式
<context:annotation-config /> //自动载入所有注解所需要的bean
<context:component-scan base-package="com.andy"></context:component-scan> //扫描所有组件,并且给这些组件自动注入bean
组件:@component包括有@controller @service @Repository
所有的bean装入完毕后,需要在注入的地方使用自动注入的注解:@Autowired
(3)使用构造器注入
<constructor-arg ref="...">
</constructor-arg>
补充:
并不是所有的bean的属性值都要写入到配置文件中,可以将属性值写入.properties文件中,
配置文件载入.properties文件:<context:property-placeholder location="classpath:/application.properties" />
在配置文件中,使用${key}的方式获取在.properties文件中对应的value的值


以上是spring注入的几种方式,那么接下来开始探讨spring aop
类似上面的CustomerService类中的getCustomer方法,我们现在需要在这个方法执行之前,或者之后,做一些事情,该如何实现,这就是spring aop能够解决的问题。


spring aop中包括四种类型通知(advices)的支持:
(1)方法执行前 ==> MethodBeforeAdvice
(2)方法执行后 ==> AfterReturningAdvice
(3)方法抛出异常后 ==> ThrowsAdvice
(4)环绕通知 ==> MethodInterceptor
public invoke(MethodInvocation methodInvocation) throws Throwable {
    try {
        // do something before method action
        Object result = methodInvocation.proceed();
        // do something after method action
    } catch(Excepiton e) {
        // do something when catch exception
    }
}


配置文件实现代理类:
<bean id="...Advice" class="../../..Advice" />
<bean id="customerServiceProxy" class="org.springframework.aop.framework.ProxyFactoryBean">
    <property name="target" ref="customerService" />
    <property name="interceptorNames">
        <list>
            <value>..Advice</value>
        </list>
    </property>
</bean>


以上是spring aop面向切面的一些操作,它对代理对象的所有方法实现了拦截操作,实际开发中,我们往往需要对某一指定名称的方法进行拦截。
那么接下来就需要去了解spring aop中的切点是什么:
切点就是被代理类中的某个点,或者说是某个方法。
通过切点拦截,有两种匹配切点的方法:
(1)名称匹配 NameMatchMethodPointcut
<bean id="customerPointcut" class="org.springframework.aop.support.NameMatchMethodPointcut">
    <property name="mappedName" value="getCustomer" />
</bean>
<bean id="customerAdvisor" class="org.springframework.aop.support.DefaultPointcutAdvisor">
    <property name="pointcut" ref="customerPointcut" />
    <property name="advice" ref="../../..Advice" />
</bean>
以上需要分别写出pointcut和advisor的bean,可以将这两者结合:
<bean id="customerAdvisor" class="org.springframework.aop.support.NameMatchMethodPointcutAdvisor">
    <property name="mappedName" value="getCustomer" />
    <property name="advice" value="../../..Advice" />
</bean>
proxy: {
    target: "被代理的类"
    interceptorNames: {
        是一个list,里面可以直接放多个advice,或者
        多个advisor: {
            pointcut: 匹配的切点(方法)
            advice: advice
        }
    }
}
(2)正则匹配 RegexpMethodYiibaicutAdvisor
<bean id="customerAdvisor" class="org.springframework.sop.support.RegexpMethodPointcutAdvisor">
    <property name="patterns">
        <list>
            <value>.*URL.*</value>
            <value>.*DAO.*</value>==>拦截DAO层中所有含有DAO的方法,来支持事务
        </list>
    </property>
    <property name="advice" ref="../../..Advice" />
</bean>


以上是对某一个bean实现代理,拦截该bean中某个特定pointcut或所有方法的讲解。
那么如果需要对所有的dao层中所有的bean都进行代理,实现事务处理,那么岂不是需要写很多代理类呢?
spring aop提供了自动创建代理的方法:
<bean id="customerAdvisor" class="org.springframework.aop.support.NameMatchMethodPointcutAdvisor">
    <property name="mappedName" value="getCustomer" />
    <property name="advice" ref="../..Advice" />
</bean>
<bean class="org.springframework.aop.framework.autoproxy.BeanNameAutoProxyCreator">
    <property name="beanNames">
        <list>
            <value>*Service</value>
        </list>
    </property>
    <property name="interceptorNames">
        <list>
            <value>customerAdvisor</value>
        </list>
    </property>
</bean>


还有一个威力巨大的自动创建代理的方法:
<bean class="org.springframework.aop.framework.autoproxy.DefaultAdvisorAutoProxyCreator" />
这种方法,会为所有的bean,只要包含advisor中pointcut方法名(getCustomer方法名)的,全部自动穿件代理,来支持AOP
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值