前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >Spring Boot 核心特性之组件自动装配

Spring Boot 核心特性之组件自动装配

作者头像
itliusir
发布2018-08-28 16:00:16
8190
发布2018-08-28 16:00:16
举报
文章被收录于专栏:刘君君

摘要: Spring Boot 核心特性之组件自动装配

正文:

Spring Boot 核心特性之组件自动装配

Spring Framework 手动装配

模式注解装配
  • ex:@Component@Service@Configuration
  • 装配方式:<context:componet-scan>@ComponentScan

@Component是一种由Spring 容器托管的通用模式组件

Spring Framework 注解

场景

version

@Repository

数据仓储模式注解

2.0

@Component

通用组件模式注解

2.5

@Service

服务模式注解

2.5

@Controller

Web 控制器模式注解

2.5

@Configuration

配置类模式注解

3.0

  • 自定义模式注解

“派生性”(“基注解”<”派生注解”),可以参考以上注解实现自定义注解: @Component<@Repository<CustomRepository

@Enable 模块装配

Spring Framework从3.1开始支持@Enable 模块驱动 ,模块是指具备相同领域的功能组件集合组合成为一个独立的单元

举例:

@Enable 注解模块

模块说明

@EnableWebMvc

Web MVC模块

@EnableAsync

异步处理模块

@EnableAutoConfiguration

自动配置模块

@EnableEurekaClient

Eureka Client模块

注解驱动方式 version:3.0 举例: org.springframework.web.servlet.config.annotation.EnableWebMvc

代码语言:javascript
复制

@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.TYPE)
@Documented
@Import(DelegatingWebMvcConfiguration.class)
public @interface EnableWebMvc {}

org.springframework.web.servlet.config.annotation.DelegatingWebMvcConfiguration

代码语言:javascript
复制
@Configuration
public class DelegatingWebMvcConfiguration extends WebMvcConfigurationSupport {}

接口编程方式 version:3.1 举例: org.springframework.boot.autoconfigure.EnableAutoConfiguration

代码语言:javascript
复制
 @Target(ElementType.TYPE)
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Import(EnableAutoConfigurationImportSelector.class)
public @interface EnableAutoConfiguration {}

org.springframework.boot.autoconfigure.EnableAutoConfigurationImportSelector

代码语言:javascript
复制
public class EnableAutoConfigurationImportSelector
  extends AutoConfigurationImportSelector {}
public class AutoConfigurationImportSelector
		implements DeferredImportSelector, BeanClassLoaderAware, ResourceLoaderAware,
BeanFactoryAware, EnvironmentAware, Ordered {
  @Override
	public String[] selectImports(AnnotationMetadata annotationMetadata) {}
}
条件装配

Spring Framework从3.1开始支持在Bean 装配时增加前置条件判断

  • @Profile 配置化方式条件装配 version:3.1 举例:
    • class
代码语言:javascript
复制
@Configuration
@Profile("development")
public class StandaloneDataConfig {
    @Bean
    public DataSource dataSource() {}
}
@Configuration
@Profile("production")
public class JndiDataConfig {
    @Bean
    public DataSource dataSource() throws Exception {}
}
代码语言:javascript
复制
@Configuration
public class SomeConfig {
    @Bean("dataSource")
    @Profile("development")
    public DataSource standaloneDataSource() {}
    @Bean("dataSource")
    @Profile("production")
    public DataSource jndiDataSource() throws Exception {}
}
代码语言:javascript
复制
AnnotationConfigApplicationContext ctx = new AnnotationConfigApplicationContext();
ctx.getEnvironment().setActiveProfiles("development");
ctx.register(SomeConfig.class, StandaloneDataConfig.class, JndiDataConfig.class);
ctx.refresh();

@Conditional 编程方式条件装配 version:4.0 举例:

代码语言:javascript
复制

@Target({ ElementType.TYPE, ElementType.METHOD })
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Conditional(OnClassCondition.class)
public @interface ConditionalOnClass {}
  • Spring-Boot的@Conditional:
    • ConditionalOnBean
    • ConditionalOnMissingBean
    • ConditionalOnClass
    • ConditionalOnMissingClass
    • ConditionalOnProperty
    • ConditionalOnJava
    • ConditionalOnWebApplication

Spring Boot 自动装配

代码语言:javascript
复制
激活:@EnableAutoConfiguration
Spring Boot 默认没有激活自动装配,存在@SpringBootApplication注解中

参考:org.springframework.boot.autoconfigure.AutoConfigurationImport

Selector#getCandidateConfigurations
 
 
代码语言:javascript
复制
配置:/META-INF/spring.factories

 规约文件,META-INFO指的是元信息目录,如spring.handlers、spring.schemas等

参考:org.springframework.core.io.support.SpringFactoriesLoader
 
代码语言:javascript
复制
实现:XxxAutoConfiguration
ex: org.springframework.boot.autoconfigure.jdbc.DataSourceAutoConfiguration
 

Demo-Spring-Boot-Starter

Demo-Spring-Boot-Starter

源码分析

ImportSelector部分

org.springframework.boot.autoconfigure.AutoConfigurationImportSelector#selectImports

代码语言:javascript
复制
@Override
	public String[] selectImports(AnnotationMetadata annotationMetadata) {
		if (!isEnabled(annotationMetadata)) {
			return NO_IMPORTS;
		}
		try {
          	//加载spring-boot-autoconfigure-1.5.6.RELEASE.jar!\META-INF\spring-autoconfigure-metadata.properties
			AutoConfigurationMetadata autoConfigurationMetadata = AutoConfigurationMetadataLoader
					.loadMetadata(this.beanClassLoader);
          	 //获取EnableAutoConfiguration里的exclude和excludeName-->LinkedHashMap-->AnnotationAttributes
			AnnotationAttributes attributes = getAttributes(annotationMetadata);
             //获取依赖里所有的xx.jar!\META-INF\spring.factories的value
			List<String> configurations = getCandidateConfigurations(annotationMetadata,
					attributes);
             //利用Set去重
			configurations = removeDuplicates(configurations);
             //排序->先按照字母排序->再按照Order排序(ex:MessageSourceAutoConfiguration#@AutoConfigureOrder)->然后根据@AutoConfigureBefore @AutoConfigureAfter(ex:WebSocketAutoConfiguration#@AutoConfigureBefore)排序
			configurations = sort(configurations, autoConfigurationMetadata);
             //对attributes封装与去重得到exclusions
			Set<String> exclusions = getExclusions(annotationMetadata, attributes);
			checkExcludedClasses(configurations, exclusions);
             //去掉exclusions里的XxAutoConf...
			configurations.removeAll(exclusions);
             //加载过滤器,对不满足ex:默认有一个OnClassCondition(org.springframework.boot.autoconfigure.AutoConfigurationImportSelector#getAutoConfigurationImportFilters(),见下图)的会排除掉()
			configurations = filter(configurations, autoConfigurationMetadata);
			fireAutoConfigurationImportEvents(configurations, exclusions);
			return configurations.toArray(new String[configurations.size()]);
		}
		catch (IOException ex) {
			throw new IllegalStateException(ex);
		}
	}
importFilter
importFilter
调用ImportSelector部分
代码语言:javascript
复制
org.springframework.context.support.PostProcessorRegistrationDelegate#invokeBeanFactoryPostProcessors
org.springframework.context.annotation.ConfigurationClassPostProcessor#postProcessBeanDefinitionRegistry
org.springframework.context.annotation.ConfigurationClassPostProcessor#processConfigBeanDefinitions
org.springframework.context.annotation.ConfigurationClassParser#parse(java.util.Set<org.springframework.beans.factory.config.BeanDefinitionHolder>)
org.springframework.context.annotation.ConfigurationClassParser#processDeferredImportSelectors
String[] imports = deferredImport.getImportSelector().selectImports(configClass.getMetadata());
processImports(configClass, asSourceClass(configClass), asSourceClasses(imports), false);
本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2018-08-13,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 正文:
  • Spring Boot 核心特性之组件自动装配
    • Spring Framework 手动装配
      • 模式注解装配
      • @Enable 模块装配
      • 条件装配
    • Spring Boot 自动装配
      • Demo-Spring-Boot-Starter
        • 源码分析
          • ImportSelector部分
          • 调用ImportSelector部分
      相关产品与服务
      容器服务
      腾讯云容器服务(Tencent Kubernetes Engine, TKE)基于原生 kubernetes 提供以容器为核心的、高度可扩展的高性能容器管理服务,覆盖 Serverless、边缘计算、分布式云等多种业务部署场景,业内首创单个集群兼容多种计算节点的容器资源管理模式。同时产品作为云原生 Finops 领先布道者,主导开源项目Crane,全面助力客户实现资源优化、成本控制。
      领券
      问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档