Spring4.3.x 浅析xml配置的解析过程(7)——解析context命名空间之annotation-config标签
来源:互联网 发布:共享单车大数据应用 编辑:程序博客网 时间:2024/06/09 20:28
概述
Spring context命名空间有property-placeholder、property-override、annotation-config、component-scan、load-time-weaver、spring-configured、mbean-export和mbean-server 8个标签。
上一节探讨了 property-placeholder和property-override标签的解析,这一节来探讨一下annotation-config的解析与用途。
解析annotation-config标签
annotation-config标签用于向BeanDefinitionRegistry对象(BeanDefinition注册表)中注册处理注解配置的工厂后处理器类和bean后处理器类以及其他一些特定类对应的BeanDefinition对象。这些类和注解有
处理@Configuration注解的ConfigurationClassPostProcessor工厂后处理器;
处理@Autowired、@Value、@Inject以及@Lookup注解的AutowiredAnnotationBeanPostProcessor bean后处理器;
处理@Required注解的RequiredAnnotationBeanPostProcessor bean后处理器;
处理JSR-250的@Resource、@PostConstruct、@PreDestroy、@EJB和@WebServiceRef注解的CommonAnnotationBeanPostProcessor bean后处理器;
处理JPA注解的PersistenceAnnotationBeanPostProcessor bean后处理器
处理@EventListener注解的EventListenerMethodProcessor后处理器和创建ApplicationListener对象的EventListenerFactory对象。
annotation-config标签的解析器类为AnnotationConfigBeanDefinitionParser,它直接实现了BeanDefinitionParser接口,下面是它实现的parse方法的源代码。
@Override public BeanDefinition parse(Element element, ParserContext parserContext) { Object source = parserContext.extractSource(element); // 注册所有相关的BeanPostProcessor. Set<BeanDefinitionHolder> processorDefinitions = AnnotationConfigUtils.registerAnnotationConfigProcessors(parserContext.getRegistry(), source); CompositeComponentDefinition compDefinition = new CompositeComponentDefinition(element.getTagName(), source); parserContext.pushContainingComponent(compDefinition); for (BeanDefinitionHolder processorDefinition : processorDefinitions) { parserContext.registerComponent(new BeanComponentDefinition(processorDefinition)); } // 最后注册 composite component. parserContext.popAndRegisterContainingComponent(); return null; }
parse方法主要调用注解配置工具类AnnotationConfigUtils的registerAnnotationConfigProcessors静态方法来注册于注解配置有关的bean后处理器,这个方法的源码如下。
private static final boolean jsr250Present = ClassUtils.isPresent("javax.annotation.Resource", AnnotationConfigUtils.class.getClassLoader()); // 定义常量PERSISTENCE_ANNOTATION_PROCESSOR_CLASS_NAME // = "org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor" private static final boolean jpaPresent = ClassUtils.isPresent("javax.persistence.EntityManagerFactory", AnnotationConfigUtils.class.getClassLoader()) && ClassUtils.isPresent(PERSISTENCE_ANNOTATION_PROCESSOR_CLASS_NAME, AnnotationConfigUtils.class.getClassLoader()); /** * 注册用于注解配置的bean后处理器 **/ public static Set<BeanDefinitionHolder> registerAnnotationConfigProcessors( BeanDefinitionRegistry registry, Object source) { DefaultListableBeanFactory beanFactory = unwrapDefaultListableBeanFactory(registry); if (beanFactory != null) { if (!(beanFactory.getDependencyComparator() instanceof AnnotationAwareOrderComparator)) { beanFactory.setDependencyComparator(AnnotationAwareOrderComparator.INSTANCE); } // 设置自动注入候选对象的解析器,用于判断BeanDefinition是否为候选对象 if (!(beanFactory.getAutowireCandidateResolver() instanceof ContextAnnotationAutowireCandidateResolver)) { beanFactory.setAutowireCandidateResolver(new ContextAnnotationAutowireCandidateResolver()); } } Set<BeanDefinitionHolder> beanDefs = new LinkedHashSet<BeanDefinitionHolder>(4); // 设置处理@Configuration注解的工厂后处理器 // 常量CONFIGURATION_ANNOTATION_PROCESSOR_BEAN_NAME // ="org.springframework.context.annotation.internalConfigurationAnnotationProcessor"; if (!registry.containsBeanDefinition(CONFIGURATION_ANNOTATION_PROCESSOR_BEAN_NAME)) { RootBeanDefinition def = new RootBeanDefinition(ConfigurationClassPostProcessor.class); def.setSource(source); beanDefs.add(registerPostProcessor(registry, def, CONFIGURATION_ANNOTATION_PROCESSOR_BEAN_NAME)); } // 设置用于处理@Autowired、@Value、@Inject以及@Lookup注解 // 定义常量AUTOWIRED_ANNOTATION_PROCESSOR_BEAN_NAME // = "org.springframework.context.annotation.internalAutowiredAnnotationProcessor" if (!registry.containsBeanDefinition(AUTOWIRED_ANNOTATION_PROCESSOR_BEAN_NAME)) { RootBeanDefinition def = new RootBeanDefinition(AutowiredAnnotationBeanPostProcessor.class); def.setSource(source); beanDefs.add(registerPostProcessor(registry, def, AUTOWIRED_ANNOTATION_PROCESSOR_BEAN_NAME)); } // 设置处理@Required注解的bean后处理器 // 定义常量REQUIRED_ANNOTATION_PROCESSOR_BEAN_NAME // = "org.springframework.context.annotation.internalRequiredAnnotationProcessor" if (!registry.containsBeanDefinition(REQUIRED_ANNOTATION_PROCESSOR_BEAN_NAME)) { RootBeanDefinition def = new RootBeanDefinition(RequiredAnnotationBeanPostProcessor.class); def.setSource(source); beanDefs.add(registerPostProcessor(registry, def, REQUIRED_ANNOTATION_PROCESSOR_BEAN_NAME)); } // 设置处理JSR-250提供的注解的bean后处理器。 // 比如,@Resource, @PostConstruct, @PreDestroy, @EJB, @WebServiceRef // 检查系统是否支持JSR-250 // 定义常量COMMON_ANNOTATION_PROCESSOR_BEAN_NAME // = "org.springframework.context.annotation.internalCommonAnnotationProcessor"; if (jsr250Present && !registry.containsBeanDefinition(COMMON_ANNOTATION_PROCESSOR_BEAN_NAME)) { RootBeanDefinition def = new RootBeanDefinition(CommonAnnotationBeanPostProcessor.class); def.setSource(source); beanDefs.add(registerPostProcessor(registry, def, COMMON_ANNOTATION_PROCESSOR_BEAN_NAME)); } // 注册用于处理JPA注解的bean后处理器 // 检查系统是否支持JPA // 定义常量PERSISTENCE_ANNOTATION_PROCESSOR_BEAN_NAME // = "org.springframework.context.annotation.internalPersistenceAnnotationProcessor" if (jpaPresent && !registry.containsBeanDefinition(PERSISTENCE_ANNOTATION_PROCESSOR_BEAN_NAME)) { RootBeanDefinition def = new RootBeanDefinition(); try { // 定义常量PERSISTENCE_ANNOTATION_PROCESSOR_CLASS_NAME // = "org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor" def.setBeanClass(ClassUtils.forName(PERSISTENCE_ANNOTATION_PROCESSOR_CLASS_NAME, AnnotationConfigUtils.class.getClassLoader())); } catch (ClassNotFoundException ex) { throw new IllegalStateException( "Cannot load optional framework class: " + PERSISTENCE_ANNOTATION_PROCESSOR_CLASS_NAME, ex); } def.setSource(source); beanDefs.add(registerPostProcessor(registry, def, PERSISTENCE_ANNOTATION_PROCESSOR_BEAN_NAME)); } // 设置用于处理@EventListener注解的bean后处理器 // 定义常量EVENT_LISTENER_PROCESSOR_BEAN_NAME // = "org.springframework.context.event.internalEventListenerProcessor" if (!registry.containsBeanDefinition(EVENT_LISTENER_PROCESSOR_BEAN_NAME)) { RootBeanDefinition def = new RootBeanDefinition(EventListenerMethodProcessor.class); def.setSource(source); beanDefs.add(registerPostProcessor(registry, def, EVENT_LISTENER_PROCESSOR_BEAN_NAME)); } // 设置用于生产ApplicationListener对象的EventListenerFactory对象 // 定义常量EVENT_LISTENER_FACTORY_BEAN_NAME // = "org.springframework.context.event.internalEventListenerFactory" if (!registry.containsBeanDefinition(EVENT_LISTENER_FACTORY_BEAN_NAME)) { RootBeanDefinition def = new RootBeanDefinition(DefaultEventListenerFactory.class); def.setSource(source); beanDefs.add(registerPostProcessor(registry, def, EVENT_LISTENER_FACTORY_BEAN_NAME)); } return beanDefs; }
AnnotationConfigUtils用于注册BeanDefinition的registerPostProcessor静态方法的代码如下。
/** * 注册RootBeanDefinition对象 **/ private static BeanDefinitionHolder registerPostProcessor( BeanDefinitionRegistry registry, RootBeanDefinition definition, String beanName) { definition.setRole(BeanDefinition.ROLE_INFRASTRUCTURE); registry.registerBeanDefinition(beanName, definition); return new BeanDefinitionHolder(definition, beanName); }
总结
(1)annotation-config用于提供bean生命周期管理、bean的依赖注入以及动态注册事件监听器的注解处理器。
(2)annotation-config简化了我们的xml配置。在xml文件中,我们只需要通过bean标签定义bean,并不需要设置bean的依赖,也不需要设置bean的init和destroy方法。
- Spring4.3.x 浅析xml配置的解析过程(7)——解析context命名空间之annotation-config标签
- Spring4.3.x 浅析xml配置的解析过程(9)——解析aop命名空间之config标签
- Spring4.3.x 浅析xml配置的解析过程(6)——解析context命名空间之property-placeholder和property-override标签
- Spring4.3.x 浅析xml配置的解析过程(8)——解析context命名空间之component-scan标签
- Spring4.3.x 浅析xml配置的解析过程(5)——解析自定义命名空间的标签
- Spring4.3.x 浅析xml配置的解析过程(10)——解析aop命名空间之aspectj-autoproxy标签
- Spring4.3.x 浅析xml配置的解析过程(11)——解析aop命名空间之scoped-proxy标签
- Spring4.3.x 浅析xml配置的解析过程(4)——解析bean标签及其所有子标签
- Spring4.3.x 浅析xml配置的解析过程(1)——使用XmlBeanDefinitionReader解析xml配置
- Spring4.3.x 浅析xml配置的解析过程(2)——使用ResourceLoader创建Resource对象
- Spring4.3.x 浅析xml配置的解析过程(3)——使用DocumentLoader创建Document对象
- context:annotation-config 标签解析
- 在Spring的XML文件中通过命名空间配置的标签是怎么解析的?
- XML命名空间深度解析 —— 命名空间简介
- xml 解析 命名空间
- dom4j 解析带命名空间的XML
- PHP 解析有命名空间的 XML
- Spring注解之xml配置中的<context:component-scan />和<context:annotation-config/>
- HBuilder常用快捷键总结
- Android内存泄漏剖析之AsyncTask
- ES6/ES2015核心内容(下)
- Android中的MVC
- redis常用命令
- Spring4.3.x 浅析xml配置的解析过程(7)——解析context命名空间之annotation-config标签
- [WTF]Xposed使用
- 能否保证service不被杀死
- java的四舍五入操作
- Android 单元测试介绍
- poj1014多重背包--单调队列优化
- Intent可以传递哪些数据类型。
- java面试
- Struts2文件下载-绝对路径/相对路径