以HttpEncodingAutoConfiguration(Http编码自动配置)为例解释自动配置原理;
@Configuration(
proxyBeanMethods = false
)
@EnableConfigurationProperties({ServerProperties.class})
@ConditionalOnWebApplication(
type = Type.SERVLET
)
@ConditionalOnClass({CharacterEncodingFilter.class})
@ConditionalOnProperty(
prefix = "server.servlet.encoding",
value = {"enabled"},
matchIfMissing = true
)
public class HttpEncodingAutoConfiguration {
private final Encoding properties;
public HttpEncodingAutoConfiguration(ServerProperties properties) {
this.properties = properties.getServlet().getEncoding();
}
@Bean
@ConditionalOnMissingBean
public CharacterEncodingFilter characterEncodingFilter() {
CharacterEncodingFilter filter = new OrderedCharacterEncodingFilter();
filter.setEncoding(this.properties.getCharset().name());
filter.setForceRequestEncoding(this.properties.shouldForce(org.springframework.boot.web.servlet.server.Encoding.Type.REQUEST));
filter.setForceResponseEncoding(this.properties.shouldForce(org.springframework.boot.web.servlet.server.Encoding.Type.RESPONSE));
return filter;
}
@Configuration(proxyBeanMethods = false)图灵leon
标记了@Configuration Spring底层会给配置创建cglib动态代理。 作用:就是防止每次调用本类的Bean方法而重新创建对
象,Bean是默认单例的
@EnableConfigurationProperties(ServerProperties.class)
启用可以在配置类设置的属性 对应的类
@xxxConditional根据当前不同的条件判断,决定这个配置类是否生效?
@Conditional派生注解(Spring注解版原生的@Conditional作用)
作用:必须是@Conditional指定的条件成立,才给容器中添加组件,配置配里面的所有内容才生效;
我们怎么知道哪些自动配置类生效;
我们可以通过设置配置文件中:启用 debug=true属性;来让控制台打印自动配置报告,这样我们就可以很方便的知道哪些自动配置类生效;
============================
CONDITIONS EVALUATION REPORT
============================
Positive matches:‐‐‐**表示自动配置类启用的**
‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐
...省略...
Negative matches:‐‐‐**没有匹配成功的自动配置类**
‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐‐
...省略...
2、细节
一但这个配置类生效;这个配置类就会给容器中添加各种组件;这些组件的属性是从对应的properties类中获取的,这些类里面的每一个
属性又是和配置文件绑定的;
所有在配置文件中能配置的属性都是在xxxxProperties类中封装;配置文件能配置什么就可以参照某个功能对图灵leon
应的这个属性类
还记得这个过滤器吧, 对,就是我们以前设置编码的, 我们现在不需要去web.xml配置
过滤器了, 只需要往容器中注入该过滤器。它的值都是通过properties设置的
@Bean
@ConditionalOnMissingBean
public CharacterEncodingFilter characterEncodingFilter() {
CharacterEncodingFilter filter = new OrderedCharacterEncodingFilter();
filter.setEncoding(this.properties.getCharset().name());
filter.setForceRequestEncoding(this.properties.shouldForce(org.springframework.boot.web.servlet.server.Encoding.Type.REQUEST));
filter.setForceResponseEncoding(this.properties.shouldForce(org.springframework.boot.web.servlet.server.Encoding.Type.RESPONSE));
return filter;
}
properties.getServlet().getEncoding().setCharset(UTF_8); 就等于如下配置:
properties= server 为什么呢? 因为 ServerProperties 上面有个注解
@ConfigurationProperties(prefix = "server") 已经设置名为server
getServlet()= servlet
getEncoding()=encoding
setCharset(UTF_8)= charset=UTF-8
server.servlet.encoding.charset=UTF‐8
所以只有知道了自动配置的原理及源码
才能灵活的配置
SpringBoot