AOP:AOP联盟提出思想.AOP联盟为增强定义一些接口:org.aopalliance.aop.Interface.Advice
1.Spring的Advice的类型:
Advice就是增强:
前置通知(在方法之前增强) org.springframework.aop.MethodBeforeAdvice
在目标方法执行前实施增强
后置通知(在方法之后增强) org.springframework.aop.AfterReturningAdvice
在目标方法执行后实施增强
环绕通知(在方法之前和之后增强) org.aopalliance.intercept.MethodInterceptor
在目标方法执行前后实施增强
异常抛出通知(在方法出现异常的时候) org.springframework.aop.ThrowsAdvice
在方法抛出异常后实施增强
引介通知 org.springframework.aop.IntroductionInterceptor(课程中不讲)
在目标类中添加一些新的方法和属性
2.Spring中提供了切面的类型:
切面:就是切入点和通知结合.
Advisor : 代表一般切面,Advice本身就是一个切面,对目标类所有方法进行拦截
* 一般切面:没有切入点,增强本身就是一个切面.(增强类上的所有的方法.)
PointcutAdvisor : 代表具有切点的切面,可以指定拦截目标类哪些方法
* 带有切入点切面:
IntroductionAdvisor : 代表引介切面,针对引介通知而使用切面(不要求掌握)
3.Spring的传统AOP的开发:(不带切点的切面)
步骤一:导入AOP开发的相应的jar包:
引入aop联盟规范包:com.springsource.org.aopalliance-1.0.0.jar
引入Spring对aop支持jar包:spring-aop-3.2.0.RELEASE.jar
步骤二:引入log4j和spring的配置文件:
在src下引入log4j.properties和applicationContext.xml
步骤三:创建包和接口及实现类
cn.green.demo3
OrderDao
OrderDaoImpl
步骤四:编写增强:
package cn.green.demo3;
import java.lang.reflect.Method;
import org.springframework.aop.MethodBeforeAdvice;
public class MyBeforeAdvice implements MethodBeforeAdvice {
public void before(Method arg0, Object[] arg1, Object arg2)
throws Throwable {
System.out.println("前置增强.....");
}
}
步骤五:在Spring中装配DAO和增强
<!-- 目标对象(被代理对象) -->
<bean id="orderDao" class="cn.green.demo3.OrderDaoImpl"></bean>
<!-- 前置增强代码 -->
<bean id="beforeAdvice" class="cn.green.demo3.MyBeforeAdvice"></bean>
步骤六:生成代理类:
不用手动编写代码:
* Spring完成生成代理对象基于一个ProxyFactoryBean.
* 在ProxyFactoryBean中有一些属性:
target : 代理的目标对象
proxyInterfaces : 代理要实现的接口
如果多个接口可以使用以下格式赋值
<list>
<value></value>
....
</list>
proxyTargetClass : 是否对类代理而不是接口,设置为true时,使用CGLib代理
interceptorNames : 需要织入目标的Advice
singleton : 返回代理是否为单实例,默认为单例
optimize : 当设置为true时,强制使用CGLib
<!-- 生成代理 -->
<bean id="orderDaoProxy" class="org.springframework.aop.framework.ProxyFactoryBean">
<!-- 目标对象 -->
<property name="target" ref="orderDao"/>
<!-- 设置目标对象的接口 :value中编写接口的全路径-->
<property name="proxyInterfaces" value="cn.green.demo3.OrderDao"/>
<!-- 配置增强 : interceptorNames : 一定要写value属性.-->
<property name="interceptorNames" value="beforeAdvice"/>
</bean>
步骤七:编程测试类:
package cn.green.demo3;
import javax.annotation.Resource;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.test.context.ContextConfiguration;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(value="classpath:applicationContext2.xml")
public class TestDemo {
@Resource(name="orderDaoProxy")
OrderDao orderDao;
@Test
public void demo01(){
orderDao.add();
orderDao.delete();
orderDao.update();
orderDao.find();
}
}
在这里面运用了注解开发模式,个人感觉注解比较简单,易于理解
4.Spring的传统AOP的开发:(带切点的切面)
使用普通Advice作为切面,将对目标类所有方法进行拦截,不够灵活,在实际开发中常采用 带有切点的切面.
PointcutAdvisor :带有切点的切面.
DefaultPointcutAdvisor 最常用的切面类型,它可以通过任意Pointcut和Advice 组合定义切面
RegexpMethodPointcutAdvisor 构造正则表达式切点切面
步骤一:导入AOP开发的相应的jar包:
引入aop联盟规范包:com.springsource.org.aopalliance-1.0.0.jar
引入Spring对aop支持jar包:spring-aop-3.2.0.RELEASE.jar
步骤二:引入log4j和spring的配置文件:
在src下引入log4j.properties和applicationContext.xml
步骤三:创建包和类:
package cn.green.demo4;
CustomerDao
步骤四:编写增强类:
package cn.green.demo4;
import org.aopalliance.intercept.MethodInterceptor;
import org.aopalliance.intercept.MethodInvocation;
public class MyAroundAdvice implements MethodInterceptor {
public Object invoke(MethodInvocation methodInvocation) throws Throwable {
System.out.println("前置增强.....");
Object obj = methodInvocation.proceed();
System.out.println("后置增强.....");
return obj;
}
}
步骤五:在Spring中管理DAO和增强
<!-- 目标对象 -->
<bean id="customerDao" class="cn.green.demo4.CustomerDao"></bean>
<!-- 增强的对象 -->
<bean id="aroundAdvice" class="cn.green.demo4.MyAroundAdvice"></bean>
步骤六:配置切面:
<!-- 配置切面 -->
<bean id="advisor" class="org.springframework.aop.support.RegexpMethodPointcutAdvisor">
<!-- 正则表达式 .:代表任意字符, *:任意个 -->
<property name="pattern" value=".*"/>
<!-- 在方法上应用哪些增强 -->
<property name="advice" ref="aroundAdvice"/>
</bean>
可以修改正则:
<!-- <property name="pattern" value=".*"/> -->
<!-- <property name="pattern" value="cn\.itcast\.spring3\.demo4\.CustomerDao\.add.*"/> -->
<property name="patterns" value=".*add.*,.*delete.*"/>
可以修改正则:
<!-- <property name="pattern" value=".*"/> -->
<!-- <property name="pattern" value="cn\.itcast\.spring3\.demo4\.CustomerDao\.add.*"/> -->
<property name="patterns" value=".*add.*,.*delete.*"/>
步骤七:生成代理:
<!-- 生成代理 -->
<bean id="customerDaoProxy" class="org.springframework.aop.framework.ProxyFactoryBean">
<property name="target" ref="customerDao"></property>
<property name="proxyTargetClass" value="true"></property>
<property name="interceptorNames" value="advisor"></property>
</bean>
步骤八:编写测试类:
package cn.green.demo4;
import javax.annotation.Resource;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.test.context.ContextConfiguration;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration("classpath:applicationContext2.xml")
public class TestDemo {
@Resource(name="customerDaoProxy")
CustomerDao customerDao;
@Test
public void demo01(){
customerDao.add();
customerDao.delete();
customerDao.find();
customerDao.update();
}
}