spring-boot自动配置
2017-06-13 00:00
411 查看
摘要: spring-boot的自动配置大大简化了开发中繁琐的配置,今天下午研究了一下实现这神奇功能的原理。
先看下@SpringBootApplication这个注解,这是一个组合注解,部分源码如下:
可以看到@EnableAutoConfiguration这个注解,这个就是自动配置的核心所在,接下来看下这个注解的源码:
可以发现此处导入了EnableAutoConfigurationImportSelector.class这个类,继续观察EnableAutoConfigurationImportSelector这个类的源码
发现继承于AutoConfigurationImportSelector这个类,发现有如下代码
这里扫描了具有META-INF/spring.factories文件的jar包。点开具有*autoconfigure的包,打开META-INF/spring.factories文件,发现有类似
@Configuration
EnableConfigurationProperties 属性注入类
ConditionalOnClass 条件注解,当容器有指定的Bean的条件下。
ConditionalOnProperty 条件注解,指定属性是否有指定的值,这个注解测试了下,没有达到预期效果,不知道怎么回事。
这里便是spring-boot自动配置的秘密所在了,接下来自己建一个项目,让其也拥有自动配置的功能:当类存在时,自动配置这个类的Bean,并可将Bean的属性在appliction.properties中配置。
pom中引入相关组件
属性配置,类型安全属性获取。
根据HelloService这个类是否存在,来创建这个类的Bean
自动配置类
注册自动配置类,在src/main/resources目录下,新建META-INF目录并在其中新建spring.factories文件,输入如下代码
这里,一个拥有自动配置的项目完成。在其他项目中引用maven坐标,并在application.properties中自定义hello.msg="xxx".使用代码如下:
项目源码地址
先看下@SpringBootApplication这个注解,这是一个组合注解,部分源码如下:
@Target(ElementType.TYPE) @Retention(RetentionPolicy.RUNTIME) @Documented @Inherited @SpringBootConfiguration @EnableAutoConfiguration @ComponentScan(excludeFilters = { @Filter(type = FilterType.CUSTOM, classes = TypeExcludeFilter.class), @Filter(type = FilterType.CUSTOM, classes = AutoConfigurationExcludeFilter.class) }) public @interface SpringBootApplication { //省略若干代码... }
可以看到@EnableAutoConfiguration这个注解,这个就是自动配置的核心所在,接下来看下这个注解的源码:
@SuppressWarnings("deprecation") @Target(ElementType.TYPE) @Retention(RetentionPolicy.RUNTIME) @Documented @Inherited @AutoConfigurationPackage @Import(EnableAutoConfigurationImportSelector.class) public @interface EnableAutoConfiguration { //省略若干行代码... }
可以发现此处导入了EnableAutoConfigurationImportSelector.class这个类,继续观察EnableAutoConfigurationImportSelector这个类的源码
public class EnableAutoConfigurationImportSelector extends AutoConfigurationImportSelector { //省略若干行代码 }
发现继承于AutoConfigurationImportSelector这个类,发现有如下代码
protected List<String> getCandidateConfigurations(AnnotationMetadata metadata, AnnotationAttributes attributes) { List<String> configurations = SpringFactoriesLoader.loadFactoryNames( getSpringFactoriesLoaderFactoryClass(), getBeanClassLoader()); Assert.notEmpty(configurations, "No auto configuration classes found in META-INF/spring.factories. If you " + "are using a custom packaging, make sure that file is correct."); return configurations; }
这里扫描了具有META-INF/spring.factories文件的jar包。点开具有*autoconfigure的包,打开META-INF/spring.factories文件,发现有类似
org.springframework.boot.autoconfigure.web.MultipartAutoConfiguration,打开任意一个AutoConfiguration,可以发现有如下注解:
@Configuration @EnableConfigurationProperties(UeditorProperties.class) @ConditionalOnClass(ActionEnter.class) @ConditionalOnProperty(prefix="ueditor",value="enabled",matchIfMissing=true)
@Configuration
EnableConfigurationProperties 属性注入类
ConditionalOnClass 条件注解,当容器有指定的Bean的条件下。
ConditionalOnProperty 条件注解,指定属性是否有指定的值,这个注解测试了下,没有达到预期效果,不知道怎么回事。
这里便是spring-boot自动配置的秘密所在了,接下来自己建一个项目,让其也拥有自动配置的功能:当类存在时,自动配置这个类的Bean,并可将Bean的属性在appliction.properties中配置。
pom中引入相关组件
<dependencies> <!--自动配置--> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-autoconfigure</artifactId> <version>${spring-boot}</version> </dependency> <!--属性的自动注入--> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-configuration-processor</artifactId> <optional>true</optional> <version>${spring-boot}</version> </dependency> </dependencies>
属性配置,类型安全属性获取。
@ConfigurationProperties(prefix = "hello") public class HelloServiceProperties { private static final String MSG = "world"; private String msg = MSG; public static String getMSG() { return MSG; } public String getMsg() { return msg; } public void setMsg(String msg) { this.msg = msg; } }
根据HelloService这个类是否存在,来创建这个类的Bean
public class HelloService { private String msg; public String sayHello(){ return "hello"+msg; } public String getMsg() { return msg; } public void setMsg(String msg) { this.msg = msg; } }
自动配置类
@Configuration @EnableConfigurationProperties(HelloServiceProperties.class) @ConditionalOnClass(HelloService.class) public class HelloServiceAutoConfigure { @Autowired private HelloServiceProperties helloServiceProperties; @Bean @ConditionalOnMissingBean(HelloService.class) public HelloService helloService() { HelloService helloService = new HelloService(); helloService.setMsg(helloServiceProperties.getMsg()); return helloService; } }
注册自动配置类,在src/main/resources目录下,新建META-INF目录并在其中新建spring.factories文件,输入如下代码
org.springframework.boot.autoconfigure.EnableAutoConfiguration=\ com.xiake.springboot.start.hello.HelloServiceAutoConfigure
这里,一个拥有自动配置的项目完成。在其他项目中引用maven坐标,并在application.properties中自定义hello.msg="xxx".使用代码如下:
@Autowired HelloService helloService; @ResponseBody @RequestMapping("/sayHello") public ResponseData sayHello(HttpServletRequest request){ return ResponseData.success(helloService.sayHello()); //输出hello.msg中的内容:xxx }
项目源码地址
相关文章推荐
- 参照SpringBoot的自动配置
- Spring Boot自动配置实例
- 初识Spring Boot框架(二)之DIY一个Spring Boot的自动配置
- SpringBoot学习笔记(三) SpringBoot 自动配置原理
- springboot自动配置的核心原理
- Spring Boot自动配置类
- Spring Boot核心原理-自动配置
- springboot Test 自动配置注解详单
- Spring Boot核心原理-自动配置
- 初识Spring Boot框架之Spring Boot的自动配置
- Spring boot学习笔记 002——Spring Boot的自动配置、Command-line Runner
- 初识Spring Boot框架(二)之DIY一个Spring Boot的自动配置
- 初识Spring Boot框架(二)之DIY一个Spring Boot的自动配置
- Idea 打包maven项目 以及spring boot 的自动配置
- Spring Boot教程(二)--- 推荐的基础 POM 文件和自动配置
- 学记:为spring boot写一个自动配置
- 初识Spring Boot框架(二)之DIY一个Spring Boot的自动配置
- Spring Boot自动配置详解
- spring boot自动配置之jdbc
- 一个由于springboot自动配置所产生的问题的解决