SpringBoot自定义Start
一、start介绍
启动器(Start)包含许多依赖项,这些依赖项是使项目快速启动和运行所需的依赖项。
总结:整合特定功能所需要的的所有jar包。
二、原理
springboot在启动的时候会将所依赖所有start的jar包中的META-INF下的spring-factories中配置的XXAutoConfiguration类注入到spring容器中。
1、Spring Boot在启动时扫描项目所依赖的JAR包,寻找包含spring.factories文件的JAR包,
2、然后读取spring.factories文件获取配置的自动配置类AutoConfiguration,
3、然后将自动配置类下满足条件(@ConditionalOnXxx)的@Bean放入到Spring容器中(Spring Context)
这样使用者就可以直接用来注入,因为该类已经在容器中了
三、start案例
以阿里开发的dubbo为例:
<dependency>
<groupId>com.alibaba.boot</groupId>
<artifactId>dubbo-spring-boot-starter</artifactId>
<version>${dubbo.starter.version}</version>
</dependency>
下面就是该start所需要的的所有jar包依赖信息
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<parent>
<groupId>com.alibaba.boot</groupId>
<artifactId>dubbo-spring-boot-parent</artifactId>
<version>0.2.0</version>
<relativePath>../dubbo-spring-boot-parent</relativePath>
</parent>
<modelVersion>4.0.0</modelVersion>
<artifactId>dubbo-spring-boot-starter</artifactId>
<packaging>jar</packaging>
<name>Dubbo Spring Boot Starter</name>
<description>Dubbo Spring Boot Starter</description>
<dependencies>
<!-- Spring Boot dependencies -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
<scope>true</scope>
</dependency>
<!-- Dubbo -->
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>dubbo</artifactId>
</dependency>
<!-- ZK -->
<dependency>
<groupId>org.apache.zookeeper</groupId>
<artifactId>zookeeper</artifactId>
</dependency>
<dependency>
<groupId>org.apache.curator</groupId>
<artifactId>curator-framework</artifactId>
</dependency>
<dependency>
<groupId>com.alibaba.boot</groupId>
<artifactId>dubbo-spring-boot-autoconfigure</artifactId>
<version>${project.version}</version>
</dependency>
</dependencies>
</project>
四、自定义start
1、步骤
1、引入spring-boot-autoconfigure/spring-boot-configuration-processor依赖
2、配置XXautoConfigure实体类
3、配置spring.factories配置文件
2、搭建自定义spring-boot-start
项目目录结构
UserProperties.class(该自定义start需要在被引入项目中配置的信息)
package com.yuyou.user;
import org.springframework.boot.context.properties.ConfigurationProperties;
@ConfigurationProperties(prefix = "spring.user")
public class UserProperties {
private String name;
private int age;
private String address;
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
public String getAddress() {
return address;
}
public void setAddress(String address) {
this.address = address;
}
}
UserService.class(该start需要完成的功能方法)
package com.yuyou.user;
public class UserService {
private UserProperties properties;
public UserService(){
}
public UserService(UserProperties properties){
this.properties = properties;
}
public void getMyUser(){
System.out.println("hello my baseinfo is:"+properties.getName()+"age:"+properties.getAge()+"address:"+properties.getAddress());
}
}
UserServiceAutoConfiguration(该start自动配置类)
package com.yuyou.user;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
@Configuration
@EnableConfigurationProperties(UserProperties.class)
@ConditionalOnClass(UserService.class)
@ConditionalOnProperty(prefix = "spring.user", value = "enable", matchIfMissing = true)
public class UserServiceAutoConfiguration {
@Autowired
private UserProperties properties;
@Bean
@ConditionalOnMissingBean(UserService.class)
public UserService userService(){
UserService userService = new UserService(properties);
return userService;
}
}
spring.properties
org.springframework.boot.autoconfigure.EnableAutoConfiguration=com.yuyou.user.UserServiceAutoConfiguration
完成之后 mvn clean install
3、引入自定义start项目
pom依赖
<dependency>
<groupId>com.yuyou</groupId>
<artifactId>user-spring-boot-start</artifactId>
<version>0.0.1-SNAPSHOT</version>
</dependency>
application.yml 配置自定义start的properties
spring:
user:
name: springbootyin
age: 22
address: jiangsu
IndexController.class
package com.yuyou.web;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;
import com.yuyou.user.UserService;
@RestController
public class IndexController {
@Autowired
private UserService userService;
@Value("${spring.user.name}")
private String name;
@GetMapping("/get")
public String get(){
userService.getMyUser();
return "success"+name;
}
}
启动项目:访问http://localhost:8080/get打印自定义的配置信息
五、总结
@ConfigurationProperties: 注解主要用来把properties配置文件转化为对应的XxxProperties来使用的,并不会把该类放入到IOC容器中,如果想放入到容器中可以在XxxProperties上使用@Component来标注,也可以使用@EnableConfigurationProperties(XxxProperties.class)统一配置到Application上来,这种方式可以在Application上来统一开启指定的属性,这样也没必要在每个XxxProperties上使用@Component
@EnableConfigurationProperties(XxxProperties.class) 注解的作用是@ConfigurationProperties注解生效。如果只配置@ConfigurationProperties注解,在IOC容器中是获取不到properties配置文件转化的bean的