我们接着上篇博客继续讲。在上篇博客中,讲述的是正在实例化的Bean的beanClass和Spring容器内所有的切面Advisor进行匹配的过程。这个过程如果返回了匹配上的Advisor(一个或多个),则表明这个Bean应该被代理;如果返回的结果为空,则这个Bean不会被代理。
代码块1
public abstract class AbstractAdvisorAutoProxyCreator extends AbstractAutoProxyCreator {
protected List<Advisor> findEligibleAdvisors(Class<?> beanClass, String beanName) {
List<Advisor> candidateAdvisors = findCandidateAdvisors();
//如果这一步返回的结果不是空集合,则表明有匹配上的切面Advisor
List<Advisor> eligibleAdvisors = findAdvisorsThatCanApply(candidateAdvisors, beanClass, beanName);
//对返回的切面集合做拓展
extendAdvisors(eligibleAdvisors);
if (!eligibleAdvisors.isEmpty()) {
//对切面集合做排序
eligibleAdvisors = sortAdvisors(eligibleAdvisors);
}
return eligibleAdvisors;
}
protected void extendAdvisors(List<Advisor> candidateAdvisors) {
//将ExposeInvocationInterceptor.ADVISOR实例加入到切面集合的首位元素,这个元素在生成AOP对象是要用到
AspectJProxyUtils.makeAdvisorChainAspectJCapableIfNecessary(candidateAdvisors);
}
}
AbstractAdvisorAutoProxyCreator有对切面排序的方法,不过其子类AspectJAwareAdvisorAutoProxyCreator重写了排序方法,正常应该调用其子类的方法
代码块2
public class AspectJAwareAdvisorAutoProxyCreator extends AbstractAdvisorAutoProxyCreator {
//按Ordered接口及@Order的序号值来作为排序的准则
protected List<Advisor> sortAdvisors(List<Advisor> advisors) {
AnnotationAwareOrderComparator.sort(advisors);
return advisors;
}
}
public class AspectJAwareAdvisorAutoProxyCreator extends AbstractAdvisorAutoProxyCreator {
private static final Comparator<Advisor> DEFAULT_PRECEDENCE_COMPARATOR = new AspectJPrecedenceComparator();
protected List<Advisor> sortAdvisors(List<Advisor> advisors) {
List<PartiallyComparableAdvisorHolder> partiallyComparableAdvisors =
new ArrayList<PartiallyComparableAdvisorHolder>(advisors.size());
for (Advisor element : advisors) {
partiallyComparableAdvisors.add(
//主要看DEFAULT_PRECEDENCE_COMPARATOR它的排序规则
new PartiallyComparableAdvisorHolder(element, DEFAULT_PRECEDENCE_COMPARATOR));
}
List<PartiallyComparableAdvisorHolder> sorted =
PartialOrder.sort(partiallyComparableAdvisors);
if (sorted != null) {
List<Advisor> result = new ArrayList<Advisor>(advisors.size());
for (PartiallyComparableAdvisorHolder pcAdvisor : sorted) {
result.add(pcAdvisor.getAdvisor());
}
return result;
}
else {
return super.sortAdvisors(advisors);
}
}
}
常量DEFAULT_PRECEDENCE_COMPARATOR是一个AspectJPrecedenceComparator对象,查看其排序的规则:
代码块3
class AspectJPrecedenceComparator implements Comparator<Advisor> {
private static final int HIGHER_PRECEDENCE = -1;
private static final int SAME_PRECEDENCE = 0;
private static final int LOWER_PRECEDENCE = 1;
public AspectJPrecedenceComparator() {
this.advisorComparator = AnnotationAwareOrderComparator.INSTANCE;
}
public int compare(Advisor o1, Advisor o2) {
//先根据@Order及Ordered的序号比较
int advisorPrecedence = this.advisorComparator.compare(o1, o2);
//如果没有这两个条件,返回的优先级相同,则按另一种规则比较
//Advisor实例是InstantiationModelAwarePointcutAdvisorImpl类型,所以declaredInSameAspect符合条件
if (advisorPrecedence == SAME_PRECEDENCE && declaredInSameAspect(o1, o2)) {
advisorPrecedence = comparePrecedenceWithinAspect(o1, o2);
}
return advisorPrecedence;
}
private int comparePrecedenceWithinAspect(Advisor advisor1, Advisor advisor2) {
//看InstantiationModelAwarePointcutAdvisorImpl的determineAdviceType()方法
//@After,@AfterReturning,@AfterThrowing这三个注解是afterAdvice
boolean oneOrOtherIsAfterAdvice =
(AspectJAopUtils.isAfterAdvice(advisor1) || AspectJAopUtils.isAfterAdvice(advisor2));
//Order按@Around, @Before, @After, @AfterReturning, @AfterThrowing的顺序
int adviceDeclarationOrderDelta = getAspectDeclarationOrder(advisor1) - getAspectDeclarationOrder(advisor2);
if (oneOrOtherIsAfterAdvice) {
// the advice declared last has higher precedence
//排序是对待织入一个Bean的多个切面进行排序,这些切面可能分布在不同的切面定义类里,也可能有多个切面定义在同一个类里
//afterAdvice有着比其他的advice更高的优先级,@After, @AfterReturning, @AfterThrowing这三个按倒序排列
//@Around, @Before这两个注解顺序排序,afterAdvice排在正常的advice前面
//排序后的顺序应该是:@AfterThrowing,@AfterReturning,@After,@Around,@Before
//顺序可能不正确,大家可以自己测试下,从代码上看是如此的
if (adviceDeclarationOrderDelta < 0) {
// advice1 was declared before advice2
// so advice1 has lower precedence
return LOWER_PRECEDENCE;
}
else if (adviceDeclarationOrderDelta == 0) {
return SAME_PRECEDENCE;
}
else {
return HIGHER_PRECEDENCE;
}
}
else {
// the advice declared first has higher precedence
if (adviceDeclarationOrderDelta < 0) {
// advice1 was declared before advice2
// so advice1 has higher precedence
return HIGHER_PRECEDENCE;
}
else if (adviceDeclarationOrderDelta == 0) {
return SAME_PRECEDENCE;
}
else {
return LOWER_PRECEDENCE;
}
}
}
}
接着上文将,合适的切面已经找到了,而且添加了一个头节点,对切面进行了排序,接下里就需要使用切面和Bean对象动态生成代理对象了:
代码块4
public abstract class AbstractAutoProxyCreator extends ProxyProcessorSupport implements SmartInstantiationAwareBeanPostProcessor, BeanFactoryAware {
protected Object wrapIfNecessary(Object bean, String beanName, Object cacheKey) {
if (beanName != null && this.targetSourcedBeans.contains(beanName)) {
return bean;
}
if (Boolean.FALSE.equals(this.advisedBeans.get(cacheKey))) {
return bean;
}
if (isInfrastructureClass(bean.getClass()) || shouldSkip(bean.getClass(), beanName)) {
this.advisedBeans.put(cacheKey, Boolean.FALSE);
return bean;
}
// Create proxy if we have advice.
Object[] specificInterceptors = getAdvicesAndAdvisorsForBean(bean.getClass(), beanName, null);
//找到了合适的切面数组
if (specificInterceptors != DO_NOT_PROXY) {
this.advisedBeans.put(cacheKey, Boolean.TRUE);
//开始创建代理对象
Object proxy = createProxy(
bean.getClass(), beanName, specificInterceptors, new SingletonTargetSource(bean));
this.proxyTypes.put(cacheKey, proxy.getClass());
return proxy;
}
this.advisedBeans.put(cacheKey, Boolean.FALSE);
return bean;
}
protected Object createProxy(
Class<?> beanClass, String beanName, Object[] specificInterceptors, TargetSource targetSource) {
if (this.beanFactory instanceof ConfigurableListableBeanFactory) {
AutoProxyUtils.exposeTargetClass((ConfigurableListableBeanFactory) this.beanFactory, beanName, beanClass);
}
ProxyFactory proxyFactory = new ProxyFactory();
//拷贝AOP配置,@EnableAspectJAutoProxy的proxyTargetClass值等
proxyFactory.copyFrom(this);
if (!proxyFactory.isProxyTargetClass()) {
if (shouldProxyTargetClass(beanClass, beanName)) {
proxyFactory.setProxyTargetClass(true);
}
else {
evaluateProxyInterfaces(beanClass, proxyFactory);
}
}
//如果有Advisor等类型的Bean,则实例化,加入Advisor数组,排在有注解生成的Advisor的前端
Advisor[] advisors = buildAdvisors(beanName, specificInterceptors);
for (Advisor advisor : advisors) {
proxyFactory.addAdvisor(advisor);
}
proxyFactory.setTargetSource(targetSource);
customizeProxyFactory(proxyFactory);
proxyFactory.setFrozen(this.freezeProxy);
if (advisorsPreFiltered()) {
proxyFactory.setPreFiltered(true);
}
return proxyFactory.getProxy(getProxyClassLoader());
}
}
通过代理工厂ProxyFactory生成代理实例:
代码块5
public class ProxyFactory extends ProxyCreatorSupport {
public Object getProxy(ClassLoader classLoader) {
//createAopProxy()一般生成ObjenesisCglibAopProxy实例
return createAopProxy().getProxy(classLoader);
}
public AopProxy createAopProxy(AdvisedSupport config) throws AopConfigException {
if (config.isOptimize() || config.isProxyTargetClass() || hasNoUserSuppliedProxyInterfaces(config)) {
Class<?> targetClass = config.getTargetClass();
if (targetClass == null) {
throw new AopConfigException("TargetSource cannot determine target class: " +
"Either an interface or a target is required for proxy creation.");
}
//如果被代理的Class是一个接口,或者被代理类是一个Proxy代理生成的类,则生成JdkDynamicAopProxy(一般不会)
if (targetClass.isInterface() || Proxy.isProxyClass(targetClass)) {
return new JdkDynamicAopProxy(config);
}
return new ObjenesisCglibAopProxy(config);
}
else {
return new JdkDynamicAopProxy(config);
}
}
}
接下去的就是通过Bean和Advisors生成代理对象了,很多都是CGLIB的代码,很晦涩麻烦,就不讲了。
接下来将一些通过CGLIB实现AOP的其他的知识点。
- 通过CGLIB生成的代理对象,持有原始Bean对象,同时继承自原始BeanClass
- 动态生成的对象的类名上含有 $$ 符号,所以判断一个对象是不是CGLIB生成的代理对象就看其类名上是否含有$$,详情看ClassUtils.isCglibProxy(Object)方法
- 当通过Advisors和Bean生成代理对象时,每一个Advisor会以MethodInterceptor的形式保存在代理对象中,每调用一个原始Bean的方法,均会触发所有的Advisor方法,而不仅仅是匹配注解表达式的方法,比如toString()
- JDK Proxy生成的动态代理对象类名以Proxy$+数字组成,代理对象继承自Proxy对象,实现了被代理对象的接口。数字代表着是jdk动态代理生成的第几个代理对象。