Springboot自动配置原理

4 篇文章 0 订阅
2 篇文章 0 订阅

自动配置

Spring boot为了自动配置,增加了注解@EnableAutoConfiguration。一般只需要配置@SpringBootApplication即可,为什么呢?

很明显的,这个注解就是三个常用在一起的注解@SpringBootConfiguration,@EnableAutoConfiguration以及@ComponentScan的组合。

  @SpringBootConfiguration这个注解实际上和@Configuration有相同的作用,配备了该注解的类就能够以JavaConfig的方式完成一些配置,可以不再使用XML配置。

  @ComponentScan这个注解完成的是自动扫描的功能,相当于Spring XML配置文件中的:<context:component-scan>,可以使用basePackages属性指定要扫描的包,以及扫描的条件。如果不设置的话默认扫描@ComponentScan注解所在类的同级类和同级目录下的所有类,所以对于一个Spring Boot项目,一般会把入口类放在顶层目录中,这样就能够保证源码目录下的所有类都能够被扫描到。

@EnableAutoConfiguration开启自动配置,主要作用就是调用Spring-Core包里的 loadFactoryNames(),将autoconfig 包里的已经写好的自动配置加载进来。

@EnableAutoConfiguration注解代码如下:

这个注解是让Spring Boot的配置能够如此简化的关键性注解。通过@Import注释导入。让我们来查看EnableAutoConfigurationImportSelector.class的源码:

EnableAutoConfigurationImportSelector继承了AutoConfigurationImportSelector。进入他的父类AutoConfigurationImportSelector。找到selectImports()方法,他调用了getCandidateConfigurations()方法,在这里,这个方法又调用了Spring Core包中的loadFactoryNames()方法。这个方法的作用是,会查询META-INF/spring.factories文件中包含的JAR文件。

当找到spring.factories文件后,SpringFactoriesLoader将查询配置文件命名的属性。

Jar文件在org.springframework.boot.autoconfigure的spring.factories

spring.factories内容如下(截取部分),在这个文件中,可以看到一系列Spring Boot自动配置的列表:

Debug可以看出已经成功将各个配置类读取。

之后springboot会有一个排除机制,会根据pom文件中的启动器将一些没有使用到的配置类过滤,如下:

原先100个过滤之后就剩38个了。可以看出每个配置类命名格式为“xxxAutoConfiguration”。

每一个这样的 xxxAutoConfiguration类都是容器中的一个组件,都加入到容器中;用他们来做自动配置;

自动配置精髓

1、Spring Boot 启动时会加载大量的自动配置类

2、看需要的功能有没有在 Spring Boot 默认写好的自动配置类中;

3、再看自动配置类中到底配置了哪些组件;(只要已经包含了要用的组件,则无需再配置)

4、给容器中自动配置类添加组件的时候,会从properties类中获取某些属性,可以在配置文件中指定这些属性的值;

例子讲解HttpEncodingAutoConfiguration

Spring Boot的自动配置是基于类型安全配置,在application.properties直接配置可以覆盖该配置类的默认值

每一个自动配置类进行自动配置功能,以HttpEncodingAutoConfiguration(Http编码自动配置)为例解释自动配置原理:

@EnableConfigurationProperties(HttpEncodingProperties.class)

//开启配置属性的注入,通过@EnableConfigurationProperties声明,自动映射一个POJO到Spring Boot配置文件(默认是application.properties文件)的属性集

 

@ConditionalOnWebApplication

//这个注解的意思就是判断当前是不是web应用,@Conditional是spring底层,意思就是根据不同的条件,来进行自己不同的条件判断,如果满足指定的条件,那么整个配置类里边的配置才会生效。

 

@ConditionalOnClass(CharacterEncodingFilter.class)

//@ConditionOnClass激活一个配置,当类路径中存在这个类时才会配置该类。这个CharacterEncodingFilter类是SpringMVC中乱码解决的过滤器

 

@ConditionalOnProperty(prefix = "spring.http.encoding", value = "enabled", matchIfMissing = true)

//来判断配置文件中是否存在某个配置,就是是否存在spring.http.encoding.enabled这个配置,matchIfMissing的意思就是如果不存在也认为这个判断是正确的

 

@Bean

//配置CharacterEncodingFilter这个Bean

 

@ConditionalOnMissingBean(CharacterEncodingFilter.class)

//@ConditionalOnMissingBean启用一个Bean定义,但必须是这个Bean之前未定义过才有效。容器中没有CharacterEncodingFilter这个Bean才会执行下面代码

 

这个HttpEncodingAutoConfiguration只有一个有参构造器,在只有一个有参构造器的情况下,参数的值就会从容器中拿。

着重了解@Conditional注释,Spring 4框架的新特性

此注释使得只有在特定条件满足时才启用一些配置。SpringBoot的AutoConfig大量使用了@Conditional,它会根据运行环境来动态注入Bean。这里介绍一些@Conditional的使用和原理,并自定义@Conditional来自定义功能。

 

@Conditional是SpringFramework的功能,SpringBoot在它的基础上定义了

@ConditionalOnClass,@ConditionalOnProperty等一系列的注解来实现更丰富的内容。

具体几个@Conditon*注解的含义

@ConditionalOnBean

仅仅在当前上下文中存在某个对象时,才会实例化一个Bean

 

@ConditionalOnClass

某个class位于类路径上,才会实例化一个Bean,该注解的参数对应的类必须存在,否则不解析该注解修饰的配置类

 

@ConditionalOnExpression

当表达式为true的时候,才会实例化一个Bean

 

@ConditionalOnMissingBean

仅仅在当前上下文中不存在某个对象时,才会实例化一个Bean,该注解表示,如果存在它修饰的类的bean,则不需要再创建这个bean,可以给该注解传入参数例如@ConditionOnMissingBean(name = "example"),这个表示如果name为“example”的bean存在,这该注解修饰的代码块不执行

 

@ConditionalOnMissingClass

某个class类路径上不存在的时候,才会实例化一个Bean

 

@ConditionalOnNotWebApplication

不是web应用时,才会执行

Properties系列注释

@EnableConfigurationProperties

@ConfigurationProperties(prefix = "spring.http.encoding")

//在application.properties配置的时候前缀是spring.http.encoding

自动配置报告

自动配置类必须在一定的条件下才能生效;怎么知道哪些自动配置类生效呢?可以通过启用 debug=true属性,来让控制台打印自动配置报告,这样就可以很方便的知道哪些自动配置类生效;

总结

SpringBoot的自动配置得益于SpringFramework强大的支撑,框架早已有很多工具和注解可以自动装配Bean。SpringBoot通过一个个封装,将市面上通用的组件直接写好了配置类。当我们程序去依赖了这些组件的jar包后,启动SpringBoot应用,于是自动加载开始了。

我们也可以定义自己的自动装配组件,依赖之后,Spring直接可以加载我们定义的starter。

  • 0
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

41摄氏度男

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值