Spring对JSR250注解支持的实现原理

Resource、PostConstruct、PreDestroy

CommonAnnotationBeanPostProcessor,之前的文章中(https://blog.csdn.net/u010597819/article/details/86646227?ops_request_misc=%257B%2522request%255Fid%2522%253A%2522158484144719726869023455%2522%252C%2522scm%2522%253A%252220140713.130056874…%2522%257D&request_id=158484144719726869023455&biz_id=0&utm_source=distribute.pc_search_result.none-task)已经提到过在创建ApplicationContext上下文时会同时创建AnnotatedBeanDefinitionReader类,该类中将CommonAnnotationBeanPostProcessor注册至上下文。而CommonAnnotationBeanPostProcessor则是对JSR-250的支持实现

CommonAnnotationBeanPostProcessor

该post-processor包含支持PostConstruct和PreDestroy注解,初始化注解和销毁注解,分别通过继承InitDestroyAnnotationBeanPostProcessor与预配置注解类型来提供支持。预配置在该类的构造器,如下:

public CommonAnnotationBeanPostProcessor() {
	setOrder(Ordered.LOWEST_PRECEDENCE - 3);
	setInitAnnotationType(PostConstruct.class);
	setDestroyAnnotationType(PreDestroy.class);
	ignoreResourceType("javax.xml.ws.WebServiceContext");
}

postProcessMergedBeanDefinition

实现MergedBeanDefinitionPostProcessor的后置动作,MergedBeanDefinitionPostProcessor接口在运行时的bean定义阶段回调postProcessMergedBeanDefinition动作
遍历bean方法,查找是否存在initAnnotationType、destroyAnnotationType注解,存在则添加至LifecycleMetadata元数据。
校验不是外部管理的初始化、销毁方法。校验通过则赋值至checkedInitMethods、checkedDestroyMethods

ReflectionUtils.doWithLocalMethods(targetClass, new ReflectionUtils.MethodCallback() {
	@Override
	public void doWith(Method method) throws IllegalArgumentException, IllegalAccessException {
		if (initAnnotationType != null) {
			if (method.getAnnotation(initAnnotationType) != null) {
				LifecycleElement element = new LifecycleElement(method);
				currInitMethods.add(element);
				if (debug) {
					logger.debug("Found init method on class [" + clazz.getName() + "]: " + method);
				}
			}
		}
		if (destroyAnnotationType != null) {
			if (method.getAnnotation(destroyAnnotationType) != null) {
				currDestroyMethods.add(new LifecycleElement(method));
				if (debug) {
					logger.debug("Found destroy method on class [" + clazz.getName() + "]: " + method);
				}
			}
		}
	}
});

postProcessPropertyValues

在populate注入属性之前回调
findResourceMetadata,遍历类的field字段查找Resource注解,存在则构建元数据对象并缓存
基于元数据对象inject注入Resource依赖

public PropertyValues postProcessPropertyValues(
		PropertyValues pvs, PropertyDescriptor[] pds, Object bean, String beanName) throws BeansException {

	InjectionMetadata metadata = findResourceMetadata(beanName, bean.getClass(), pvs);
	try {
		metadata.inject(bean, beanName, pvs);
	}
	catch (Throwable ex) {
		throw new BeanCreationException(beanName, "Injection of resource dependencies failed", ex);
	}
	return pvs;
}

InitDestroyAnnotationBeanPostProcessor

postProcessBeforeInitialization

bean初始化前回调所有初始化方法checkedInitMethods。即:PostConstruct。该初始化方法在populate注入属性之前。当然也在spring的init初始化方法之前。因为spring指定的init方法是在populate注入之后执行

postProcessBeforeDestruction

bean销毁前回调所有销毁方法checkedDestroyMethods。即:PreDestroy

发布了91 篇原创文章 · 获赞 103 · 访问量 3万+

猜你喜欢

转载自blog.csdn.net/u010597819/article/details/105024737