栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > Java

springboot aop原理解析(四)

Java 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

springboot aop原理解析(四)

@EnableAspectJAutoProxy
基于注解的方式实现AOP需要在配置类中添加注解@EnableAspectJAutoProxy,可以看到他通过import注入了AspectJAutoProxyRegistrar。AspectJAutoProxyRegistrar实现了importBeanDefinitionRegistrar,因此spring启动时候会调用其registerBeanDefinitions方法。

下面看一下AspectJAutoProxyRegistrar的registerBeanDefinitions方法,这个方法在他的父类里面,如下。第一行代码registerAspectJAnnotationAutoProxyCreatorIfNecessary点进去发现注册了AnnotationAwareAspectJAutoProxyCreator这个对象。但是注入这个对象的作用何在?

public void registerBeanDefinitions(
			Annotationmetadata importingClassmetadata, BeanDefinitionRegistry registry) {

		AopConfigUtils.registerAspectJAnnotationAutoProxyCreatorIfNecessary(registry);

		AnnotationAttributes enableAspectJAutoProxy =
				AnnotationConfigUtils.attributesFor(importingClassmetadata, EnableAspectJAutoProxy.class);
		if (enableAspectJAutoProxy != null) {
			if (enableAspectJAutoProxy.getBoolean("proxyTargetClass")) {
				AopConfigUtils.forceAutoProxyCreatorToUseClassProxying(registry);
			}
			if (enableAspectJAutoProxy.getBoolean("exposeProxy")) {
				AopConfigUtils.forceAutoProxyCreatorToExposeProxy(registry);
			}
		}
	}

AnnotationAwareAspectJAutoProxyCreator的继承关系图如下,可以看到他实现了BeanPostProcessor。既然他是个后置处理器,那么在spring启动时候就会通过PostProcessorRegistrationDelegate的registerBeanPostProcessors方法进行注册,加入到beanPostProcessors集合。

接下来doGetBean在调用initializeBean时候,在初始化方法后会调用applyBeanPostProcessorsAfterInitialization方法。getBeanPostProcessors会拿到之前注册的所有Bean后置处理器,遍历执行每一个的 方法。那么自然而然AnnotationAwareAspectJAutoProxyCreator也会被执行。

	public Object applyBeanPostProcessorsAfterInitialization(Object existingBean, String beanName)
			throws BeansException {

		Object result = existingBean;
		// getBeanPostProcessors会拿到之前注册的所有Bean后置处理器,遍历执行每一个的postProcessAfterInitialization方法。
		for (BeanPostProcessor processor : getBeanPostProcessors()) {
			Object current = processor.postProcessAfterInitialization(result, beanName);
			if (current == null) {
				return result;
			}
			result = current;
		}
		return result;
	}

AbstractAutoProxyCreator的postProcessAfterInitialization方法如下

	public Object postProcessAfterInitialization(@Nullable Object bean, String beanName) {
		if (bean != null) {
			Object cacheKey = getCacheKey(bean.getClass(), beanName);
			if (this.earlyProxyReferences.remove(cacheKey) != bean) {
				return wrapIfNecessary(bean, beanName, cacheKey);
			}
		}
		return bean;
	}

wrapIfNecessary主要作用是查找当前bean的增强方法,然后根据增强方法创建代理。

	protected Object wrapIfNecessary(Object bean, String beanName, Object cacheKey) {
		if (StringUtils.hasLength(beanName) && 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;
		}

		//为当前bean找相应的增强,并生成代理类。如果没有找到说明不需要增强直接返回。
		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;
	}

获取增强器
getAdvicesAndAdvisorsForBean是获取增强器方法,内部调用了findEligibleAdvisors,这个方法首先查找所有的Advisor,再从中找出匹配当前bean的Advisor返回。

	protected List findEligibleAdvisors(Class beanClass, String beanName) {
	//查找所有的增强Advisor
		List candidateAdvisors = findCandidateAdvisors();
		//匹配的Advisor
		List eligibleAdvisors = findAdvisorsThatCanApply(candidateAdvisors, beanClass, beanName);
		extendAdvisors(eligibleAdvisors);
		if (!eligibleAdvisors.isEmpty()) {
			eligibleAdvisors = sortAdvisors(eligibleAdvisors);
		}
		return eligibleAdvisors;
	}

findCandidateAdvisors查找所有的增强Advisor

	protected List findCandidateAdvisors() {
		//调用父类的方法找到所有BeanFactory已经存在的Advisor
		List advisors = super.findCandidateAdvisors();
		
		if (this.aspectJAdvisorsBuilder != null) {
		//找到所有的bean,遍历每一个bean是否是AspectJ,对其进行解析	
		advisors.addAll(this.aspectJAdvisorsBuilder.buildAspectJAdvisors());
		}
		return advisors;
	}

buildAspectJAdvisors拿到BeanFactory注册的所有Bean,找出当前标注AspectJ注解的类

	public List buildAspectJAdvisors() {
		List aspectNames = this.aspectBeanNames;

		if (aspectNames == null) {
			synchronized (this) {
				aspectNames = this.aspectBeanNames;
				if (aspectNames == null) {
					List advisors = new ArrayList<>();
					aspectNames = new ArrayList<>();
					//获取BeanFactory注册的Bean
					String[] beanNames = BeanFactoryUtils.beanNamesForTypeIncludingAncestors(
							this.beanFactory, Object.class, true, false);
							//遍历每个bean,找出AspectJ注解标注的bean
					for (String beanName : beanNames) {
						if (!isEligibleBean(beanName)) {
							continue;
						}
						// We must be careful not to instantiate beans eagerly as in this case they
						// would be cached by the Spring container but would not have been weaved.
						Class beanType = this.beanFactory.getType(beanName, false);
						if (beanType == null) {
							continue;
						}
						if (this.advisorFactory.isAspect(beanType)) {
							aspectNames.add(beanName);
							Aspectmetadata amd = new Aspectmetadata(beanType, beanName);
							if (amd.getAjType().getPerClause().getKind() == PerClauseKind.SINGLETON) {
								metadataAwareAspectInstanceFactory factory =
										new BeanFactoryAspectInstanceFactory(this.beanFactory, beanName);
								List classAdvisors = this.advisorFactory.getAdvisors(factory);
								if (this.beanFactory.isSingleton(beanName)) {
									this.advisorsCache.put(beanName, classAdvisors);
								}
								else {
									this.aspectFactoryCache.put(beanName, factory);
								}
								advisors.addAll(classAdvisors);
							}
							else {
								// Per target or per this.
								if (this.beanFactory.isSingleton(beanName)) {
									throw new IllegalArgumentException("Bean with name '" + beanName +
											"' is a singleton, but aspect instantiation model is not singleton");
								}
								metadataAwareAspectInstanceFactory factory =
										new PrototypeAspectInstanceFactory(this.beanFactory, beanName);
								this.aspectFactoryCache.put(beanName, factory);
								advisors.addAll(this.advisorFactory.getAdvisors(factory));
							}
						}
					}
					this.aspectBeanNames = aspectNames;
					return advisors;
				}
			}
		}

		if (aspectNames.isEmpty()) {
			return Collections.emptyList();
		}
		List advisors = new ArrayList<>();
		for (String aspectName : aspectNames) {
			List cachedAdvisors = this.advisorsCache.get(aspectName);
			if (cachedAdvisors != null) {
				advisors.addAll(cachedAdvisors);
			}
			else {
				metadataAwareAspectInstanceFactory factory = this.aspectFactoryCache.get(aspectName);
				advisors.addAll(this.advisorFactory.getAdvisors(factory));
			}
		}
		return advisors;
	}

获取当前AspectJ修饰的bean的所有方法,解析每一个方法封装Advisor。

public List getAdvisors(metadataAwareAspectInstanceFactory aspectInstanceFactory) {
		//获取标记为AspectJ的类
		Class aspectClass = aspectInstanceFactory.getAspectmetadata().getAspectClass();
		//获取标记为AspectJ的name
		String aspectName = aspectInstanceFactory.getAspectmetadata().getAspectName();
		validate(aspectClass);

		metadataAwareAspectInstanceFactory lazySingletonAspectInstanceFactory =
				new LazySingletonAspectInstanceFactoryDecorator(aspectInstanceFactory);

		//获取当前AspectJ对象的所有方法,对每一个方法获取相应的Advisor
		List advisors = new ArrayList<>();
		for (Method method : getAdvisorMethods(aspectClass)) {
			//解析提取Advisor
			Advisor advisor = getAdvisor(method, lazySingletonAspectInstanceFactory, 0, aspectName);
			if (advisor != null) {
				//缓存
				advisors.add(advisor);
			}
		}

		if (!advisors.isEmpty() && lazySingletonAspectInstanceFactory.getAspectmetadata().isLazilyInstantiated()) {
			Advisor instantiationAdvisor = new SyntheticInstantiationAdvisor(lazySingletonAspectInstanceFactory);
			advisors.add(0, instantiationAdvisor);
		}

		for (Field field : aspectClass.getDeclaredFields()) {
			Advisor advisor = getDeclareParentsAdvisor(field);
			if (advisor != null) {
				advisors.add(advisor);
			}
		}

		return advisors;
	}

解析每个方法上面的注解,主要有Before.class,After.class,Around.class,PointCut.class等,根据不同的注解封装成不同的Advisor增强器。

	public Advisor getAdvisor(Method candidateAdviceMethod, metadataAwareAspectInstanceFactory aspectInstanceFactory,
			int declarationOrderInAspect, String aspectName) {

		validate(aspectInstanceFactory.getAspectmetadata().getAspectClass());
		//解析方法上面的注解
		AspectJexpressionPointcut expressionPointcut = getPointcut(
				candidateAdviceMethod, aspectInstanceFactory.getAspectmetadata().getAspectClass());
		if (expressionPointcut == null) {
			return null;
		}
		//根据注解信息封装Advisor 
		return new InstantiationModelAwarePointcutAdvisorImpl(expressionPointcut, candidateAdviceMethod,
				this, aspectInstanceFactory, declarationOrderInAspect, aspectName);
	}
	private AspectJexpressionPointcut getPointcut(Method candidateAdviceMethod, Class candidateAspectClass) {
		AspectJAnnotation aspectJAnnotation =
//找到方法上的注解				AbstractAspectJAdvisorFactory.findAspectJAnnotationOnMethod(candidateAdviceMethod);
		if (aspectJAnnotation == null) {
			return null;
		}
		//封装成AspectJexpressionPointcut 
		AspectJexpressionPointcut ajexp =
				new AspectJexpressionPointcut(candidateAspectClass, new String[0], new Class[0]);
//设置pointcut切点表达式信息		ajexp.setexpression(aspectJAnnotation.getPointcutexpression());
		if (this.beanFactory != null) {
			ajexp.setBeanFactory(this.beanFactory);
		}
		return ajexp;
	}
	protected static AspectJAnnotation findAspectJAnnotationOnMethod(Method method) {
	//ASPECTJ_ANNOTATION_CLASSES 包含Before.class,After.class,Around.class,PointCut.class等注解
		for (Class clazz : ASPECTJ_ANNOTATION_CLASSES) {
		//找到相匹配的注解封装成AspectJAnnotation
			AspectJAnnotation foundAnnotation = findAnnotation(method, (Class) clazz);
			if (foundAnnotation != null) {
				return foundAnnotation;
			}
		}
		return null;
	}

寻找匹配的增强器
前面找出了所有的增强器,接下来应该从中找出与当前bean匹配的增强器Advisor。具体方法如下findAdvisorsThatCanApply

	protected List findAdvisorsThatCanApply(
			List candidateAdvisors, Class beanClass, String beanName) {

		ProxyCreationContext.setCurrentProxiedBeanName(beanName);
		try {
			return AopUtils.findAdvisorsThatCanApply(candidateAdvisors, beanClass);
		}
		finally {
			ProxyCreationContext.setCurrentProxiedBeanName(null);
		}
	}

具体匹配的方法,获取当前类所有的接口,获取每一个接口的方法,判断当前方法是否存在这个注解。

	public static boolean canApply(Pointcut pc, Class targetClass, boolean hasIntroductions) {
		Assert.notNull(pc, "Pointcut must not be null");
		if (!pc.getClassFilter().matches(targetClass)) {
			return false;
		}

		MethodMatcher methodMatcher = pc.getMethodMatcher();
		if (methodMatcher == MethodMatcher.TRUE) {
			// No need to iterate the methods if we're matching any method anyway...
			return true;
		}

		IntroductionAwareMethodMatcher introductionAwareMethodMatcher = null;
		if (methodMatcher instanceof IntroductionAwareMethodMatcher) {
			introductionAwareMethodMatcher = (IntroductionAwareMethodMatcher) methodMatcher;
		}

		Set> classes = new linkedHashSet<>();
		if (!Proxy.isProxyClass(targetClass)) {
			classes.add(ClassUtils.getUserClass(targetClass));
		}
		classes.addAll(ClassUtils.getAllInterfacesForClassAsSet(targetClass));

		for (Class clazz : classes) {
			Method[] methods = ReflectionUtils.getAllDeclaredMethods(clazz);
			for (Method method : methods) {
				if (introductionAwareMethodMatcher != null ?
						introductionAwareMethodMatcher.matches(method, targetClass, hasIntroductions) :
						methodMatcher.matches(method, targetClass)) {
					return true;
				}
			}
		}

		return false;
	}

创建代理类
上面获取到当前bean匹配的Advisors,接下来创建代理类。

	protected Object createProxy(Class beanClass, @Nullable String beanName,
			@Nullable Object[] specificInterceptors, TargetSource targetSource) {

		if (this.beanFactory instanceof ConfigurableListableBeanFactory) {
			AutoProxyUtils.exposeTargetClass((ConfigurableListableBeanFactory) this.beanFactory, beanName, beanClass);
		}
		//通过ProxyFactory 创建proxy代理
		ProxyFactory proxyFactory = new ProxyFactory();
		//设置属性
		proxyFactory.copyFrom(this);
		//proxy-target-class=true表示强制使用cglib代理
		if (!proxyFactory.isProxyTargetClass()) {
			if (shouldProxyTargetClass(beanClass, beanName)) {
				proxyFactory.setProxyTargetClass(true);
			}
			else {
				evaluateProxyInterfaces(beanClass, proxyFactory);
			}
		}
		//获取当前bean所有的Advisor,包括指定的拦截器
		Advisor[] advisors = buildAdvisors(beanName, specificInterceptors);
		//加入到proxyFactory,后面执行时会调用
		proxyFactory.addAdvisors(advisors);
		proxyFactory.setTargetSource(targetSource);
		customizeProxyFactory(proxyFactory);

		proxyFactory.setFrozen(this.freezeProxy);
		if (advisorsPreFiltered()) {
			proxyFactory.setPreFiltered(true);
		}
		
		ClassLoader classLoader = getProxyClassLoader();
		if (classLoader instanceof SmartClassLoader && classLoader != beanClass.getClassLoader()) {
			classLoader = ((SmartClassLoader) classLoader).getOriginalClassLoader();
		}
		//创建代理
		return proxyFactory.getProxy(classLoader);
	}

获取当前bean所有的Advisor,包括指定的拦截器

	protected Advisor[] buildAdvisors(@Nullable String beanName, @Nullable Object[] specificInterceptors) {
		// 获取当前bean的MethodInterceptor拦截器,并封装成Advisor
		Advisor[] commonInterceptors = resolveInterceptorNames();

		List allInterceptors = new ArrayList<>();
		if (specificInterceptors != null) {
			if (specificInterceptors.length > 0) {
				allInterceptors.addAll(Arrays.asList(specificInterceptors));
			}
			if (commonInterceptors.length > 0) {
			//applyCommonInterceptorsFirst=true表示优先执行拦截器
				if (this.applyCommonInterceptorsFirst) {
					allInterceptors.addAll(0, Arrays.asList(commonInterceptors));
				}
				else {
					allInterceptors.addAll(Arrays.asList(commonInterceptors));
				}
			}
		}

		Advisor[] advisors = new Advisor[allInterceptors.size()];
		//遍历allInterceptors,对每一个Interceptor包装成Advisor
		for (int i = 0; i < allInterceptors.size(); i++) {
			advisors[i] = this.advisorAdapterRegistry.wrap(allInterceptors.get(i));
		}
		return advisors;
	}
 

上面buildAdvisors方法主要把MethodInterceptor封装成Advisor,和之前解析得到的Advisor一起返回。下面通过ProxyFactory.getProxy进行代理的创建。

	public AopProxy createAopProxy(AdvisedSupport config) throws AopConfigException {
	//optimize=true表示采用cglib代理优化器 ,proxyTargetClass=true表示强制使用cglib代理,hasNoUserSuppliedProxyInterfaces没有实现接口
		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.");
			}
			//目标类是一个接口或者是一个代理类  用jdk动态代理
			if (targetClass.isInterface() || Proxy.isProxyClass(targetClass)) {
				return new JdkDynamicAopProxy(config);
			}
			//cglib代理
			return new ObjenesisCglibAopProxy(config);
		}
		else {
		//jdk代理
			return new JdkDynamicAopProxy(config);
		}
	}

上面指定了用哪种代理方式动态代理,下面具体看一下jdk获取代理类。

	public Object getProxy(@Nullable ClassLoader classLoader) {
		if (logger.isTraceEnabled()) {
			logger.trace("Creating JDK dynamic proxy: " + this.advised.getTargetSource());
		}
		return Proxy.newProxyInstance(classLoader, this.proxiedInterfaces, this);
	}

JdkDynamicAopProxy实现了InvocationHandler,所以主要处理逻辑都在invoke方法中。

public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
		Object oldProxy = null;
		boolean setProxyContext = false;

		TargetSource targetSource = this.advised.targetSource;
		Object target = null;

		try {
			if (!this.equalsDefined && AopUtils.isEqualsMethod(method)) {
				return equals(args[0]);
			}
			else if (!this.hashCodeDefined && AopUtils.isHashCodeMethod(method)) {
				return hashCode();
			}
			else if (method.getDeclaringClass() == DecoratingProxy.class) {
				return AopProxyUtils.ultimateTargetClass(this.advised);
			}
			else if (!this.advised.opaque && method.getDeclaringClass().isInterface() &&
					method.getDeclaringClass().isAssignableFrom(Advised.class)) {
				return AopUtils.invokeJoinpointUsingReflection(this.advised, method, args);
			}

			Object retVal;

			if (this.advised.exposeProxy) {
				oldProxy = AopContext.setCurrentProxy(proxy);
				setProxyContext = true;
			}

			target = targetSource.getTarget();
			Class targetClass = (target != null ? target.getClass() : null);

			// 获取当前方法的调用器链,就是之前解析的Advisors
			List chain = this.advised.getInterceptorsAndDynamicInterceptionAdvice(method, targetClass);

			//为空  直接调用目标方法
			if (chain.isEmpty()) {
				Object[] argsToUse = AopProxyUtils.adaptArgumentsIfNecessary(method, args);
				retVal = AopUtils.invokeJoinpointUsingReflection(target, method, argsToUse);
			}
			else {
			//封装成MethodInvocation,调用其proceed方法执行拦截器链
				MethodInvocation invocation =
						new ReflectiveMethodInvocation(proxy, target, method, args, targetClass, chain);
				retVal = invocation.proceed();
			}

			Class returnType = method.getReturnType();
			if (retVal != null && retVal == target &&
					returnType != Object.class && returnType.isInstance(proxy) &&
					!RawTargetAccess.class.isAssignableFrom(method.getDeclaringClass())) {
				retVal = proxy;
			}
			else if (retVal == null && returnType != Void.TYPE && returnType.isPrimitive()) {
				throw new AopInvocationException(
						"Null return value from advice does not match primitive return type for: " + method);
			}
			return retVal;
		}
		finally {
			if (target != null && !targetSource.isStatic()) {
				// Must have come from TargetSource.
				targetSource.releaseTarget(target);
			}
			if (setProxyContext) {
				// Restore old proxy.
				AopContext.setCurrentProxy(oldProxy);
			}
		}
	}

 

调用链具体执行逻辑,proceed->拦截器invoke->proceed。直到执行完最后一个拦截器,然后执行目标方法。

	public Object proceed() throws Throwable {
	//所有的Advisor执行完毕,调用目标方法自身
		if (this.currentInterceptorIndex == this.interceptorsAndDynamicMethodMatchers.size() - 1) {
			return invokeJoinpoint();
		}
//获取下一个拦截器,调用拦截器的invoke方法
		Object interceptorOrInterceptionAdvice =
				this.interceptorsAndDynamicMethodMatchers.get(++this.currentInterceptorIndex);
		if (interceptorOrInterceptionAdvice instanceof InterceptorAndDynamicMethodMatcher) {
			InterceptorAndDynamicMethodMatcher dm =
					(InterceptorAndDynamicMethodMatcher) interceptorOrInterceptionAdvice;
			Class targetClass = (this.targetClass != null ? this.targetClass : this.method.getDeclaringClass());
			if (dm.methodMatcher.matches(this.method, targetClass, this.arguments)) {
				return dm.interceptor.invoke(this);
			}
			else {
				return proceed();
			}
		}
		else {
		//调用拦截器的invoke方法,并把当前ReflectiveMethodInvocation对象传递过去,拦截器内部会继续调用proceed方法,组成一个调用链。
			return ((MethodInterceptor) interceptorOrInterceptionAdvice).invoke(this);
		}
	}

下面给出调用链代码示例

public class MethodInvocationHandler {

    private List methodInterceptors;
    private int currentInterceptorIndex=0;

    public MethodInvocationHandler(List methodInterceptors){
        this.methodInterceptors=methodInterceptors;
    }

    public void proceed(){
        if(currentInterceptorIndex==methodInterceptors.size()){
            System.out.println("methodInterceptors执行完毕");
            return;
        }

        MethodInterceptor methodInterceptor = methodInterceptors.get(currentInterceptorIndex++);
        methodInterceptor.invoke(this);
    }
}

public interface MethodInterceptor {

    void invoke(MethodInvocationHandler handler);
}

public class Test {
    static class AMethodInterceptor implements MethodInterceptor{

        @Override
        public void invoke(MethodInvocationHandler handler) {
            System.out.println("AMethodInterceptor开始执行");
            handler.proceed();
            System.out.println("AMethodInterceptor结束执行");
        }
    }

    static class BMethodInterceptor implements MethodInterceptor{

        @Override
        public void invoke(MethodInvocationHandler handler) {
            System.out.println("BMethodInterceptor开始执行");
            handler.proceed();
            System.out.println("BMethodInterceptor结束执行");
        }
    }

    public static void main(String[] args) {
        List methodInterceptors=new ArrayList<>();
        methodInterceptors.add(new AMethodInterceptor());
        methodInterceptors.add(new BMethodInterceptor());

        MethodInvocationHandler methodInvocationHandler = new MethodInvocationHandler(methodInterceptors);
        methodInvocationHandler.proceed();
    }
}

执行结果如下

转载请注明:文章转载自 www.mshxw.com
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号