六、原理解析
1. Profile
通过profile可以做到不同的环境自动使用不同的配置文件
1.1 application-profile
- application.yaml 配置文件是默认加载的
- application-xxx.yaml 配置文件则可以做到自由加载
有以下三个配置文件:
application.properties
# 激活 application-dev.yaml 配置文件
spring.profiles.active=dev
application-dev.yaml
server:
port: 8000
application-prod.yaml
server:
port: 9000
启动spring-boot,发现tomcat的端口号是8000,说明application-prod.yaml没生效
tip: 主配置文件与profile文件有相同的配置,则以profile文件为准
1.2 @Profile条件装配
关于@Profile的使用请看下面的例子:
- 开发者类和用户类继承自Person
net.tiejiankudan.part12_principle.domain.Person
public interface Person {
abstract public String getName();
abstract public int getAge();
}
net.tiejiankudan.part12_principle.domain.impl.Developer
@Data
@ToString
public class Developer implements Person {
private String name;
private int age;
}
net.tiejiankudan.part12_principle.domain.impl.User
@Data
@ToString
public class User implements Person {
private String name;
private int age;
}
- 配置类
net.tiejiankudan.part12_principle.config.DevConfig
@Configuration
// 当dev环境时,此配置文件生效
@Profile("dev")
public class DevConfig {
@Bean
@ConfigurationProperties(prefix = "person")
public Person person(){
return new Developer();
}
}
net.tiejiankudan.part12_principle.config.ProdConfig
@Configuration
// 当prod环境时,此配置文件生效
@Profile("prod")
public class ProdConfig {
@Bean
@ConfigurationProperties(prefix = "person")
public Person person(){
return new User();
}
}
- 再来个controller检测效果
net.tiejiankudan.part12_principle.controller.TestController
@RestController
public class TestController {
@Autowired
Person person;
@GetMapping("/getperson")
public Person getPersonObj() {
return person;
}
}
- 配置文件
application-dev.yaml
server:
port: 8000
person:
name: 开发者
age: 19
application-prod.yaml
server:
port: 9000
person:
name: 用户
age: 30
application.properties 的两种情形
# 访问controller结果是开发者,说明DevConfig生效
spring.profiles.active=dev
# 访问controller结果是用户,说明ProdConfig生效
spring.profiles.active=prod
1.3 profile 分组
我的理解就是有多个配置文件共同组成一中环境所需的配置,用分组就可以批量激活多个profiles
例如有一下两个配置文件:
application-devdb.yaml
server:
port: 2333
application-devmq.yml
person:
name: dev-group
age: 19
主配置文件 application.properties
spring.profiles.active=development
spring.profiles.group.development[0]=devdb
spring.profiles.group.development[1]=devmq
再来个配置文件net.tiejiankudan.part12_principle.config.GroupConfig
@Configuration
@Profile("development")
public class GroupConfig {
@Bean
@ConfigurationProperties(prefix = "person")
public Person person(){
return new Developer();
}
}
浏览器访问:http://localhost:2333/getperson 结果是 {“name”:“dev-group”,“age”:19}
说明以上两个配置文件都生效了
2. 外部化配置
2.1 外部配置源
官方介绍:Spring Boot Features
我们的spring-boot可以从以下14个地方获得配置信息,而且下面的会覆盖上面的配置:
[具体位置见上面的网址] (‾◡◝)
值得注意的是:
-
- Default properties
-
- Command line arguments.
命令行参数携带的配置会覆盖配置文件,将上面的代码打成jar包,然后输入$ java -jar part12_principle-0.0.1-SNAPSHOT.jar --spring.profiles.active=dev
发现环境变成了dev
2.2 配置文件查找位置
后面的位置优先级高
-
classpath 根路径
-
classpath 根路径下config目录
-
jar包当前目录
-
jar包当前目录的config目录
-
/config子目录的直接子目录
2.3 配置文件加载顺序
-
当前jar包内部的application.properties和application.yml
-
当前jar包内部的application-{profile}.properties 和 application-{profile}.yml
-
引用的外部jar包的application.properties和application.yml
-
引用的外部jar包的application-{profile}.properties 和 application-{profile}.yml
3. 自定义starter
- 创建自动配置工程,在这个工程里写自动配置类,并在/META-INF/spring.factories中配置自动加载自动配置,参考其他自动配置类
- 创建starter工程,在这个工程中的pom文件中标记依赖上面写好的工程
- 创建测试工程,引入我们写好的starter。切记,每个工程都要安装到仓库里
4. SpringBoot原理
略