詳解Spring獲取配置的三種方式
前言
最近在寫框架時(shí)遇到需要根據(jù)特定配置(可能不存在)加載 bean 的需求,所以就學(xué)習(xí)了下 Spring 中如何獲取配置的幾種方式。
Spring 中獲取配置的三種方式
- 通過(guò) @Value 方式動(dòng)態(tài)獲取單個(gè)配置
- 通過(guò) @ConfigurationProperties + 前綴方式批量獲取配置
- 通過(guò) Environment 動(dòng)態(tài)獲取單個(gè)配置
通過(guò) @Value 動(dòng)態(tài)獲取單個(gè)配置
1.作用
可修飾到任一變量獲取,使用較靈活
2.優(yōu)點(diǎn)
使用簡(jiǎn)單,且使用關(guān)聯(lián)的鏈路較短
3.缺點(diǎn)
- 配置名不能被有效枚舉到
- 每一個(gè)配置的使用都需重新定義,使用較為麻煩
- 項(xiàng)目強(qiáng)依賴配置的定義,配置不存在則會(huì)導(dǎo)致項(xiàng)目無(wú)法啟動(dòng)
4.使用場(chǎng)景
- 項(xiàng)目強(qiáng)依賴該配置的加載,想要從源頭避免因配置缺失導(dǎo)致的未知問(wèn)題
- 只想使用少數(shù)幾個(gè)配置
5.代碼示例
@Configuration
public class ConfigByValueAnnotation {
@Value("${server.port}")
private String serverPort;
public String getServerPort() {
return serverPort;
}
}6.測(cè)試代碼
@DisplayName("multipart get config")
@SpringBootTest
public class MultipartGetConfigTest {
private static final Logger log = LoggerFactory.getLogger(MultipartGetConfigTest.class);
@Autowired
private ConfigByValueAnnotation configByValueAnnotation;
@Test
public void getByValueAnnotation(){
log.info("get by @Value, value: {}", configByValueAnnotation.getServerPort());
}
}7.測(cè)試結(jié)果
org.spring.demo.MultipartGetConfigTest : get by @Value, value: 7100
通過(guò)@ConfigurationProperties+前綴方式批量獲取
1.作用
用于配置類的修飾或批量配置的獲取
2.優(yōu)點(diǎn)
- 使用配置只需確定 key 的前綴即能使用,有利于批量獲取場(chǎng)景的使用
- 因采用前綴匹配,所以在使用新的相同前綴 key 的配置時(shí)無(wú)需改動(dòng)代碼
3.缺點(diǎn)
- 使用復(fù)雜,需定義配置類或者手動(dòng)創(chuàng)建 bean 后引入使用
- 增加新的前綴相同 key 時(shí)可能會(huì)引入不穩(wěn)定因素
4.使用場(chǎng)景
- 需要同時(shí)使用多前綴相同 key 的配置
- 期望增加新配置但不修改代碼的 properties 注入
5.代碼示例
@Component
@ConfigurationProperties(prefix = "server", ignoreInvalidFields = true)
public class ConfigByConfigurationProperties {
private Integer port;
public Integer getPort() {
return port;
}
public ConfigByConfigurationProperties setPort(Integer port) {
this.port = port;
return this;
}
}@Configuration
public class ConfigByConfigurationPropertiesV2 {
@Bean("configByValueAnnotationV2")
@ConfigurationProperties(prefix = "server2")
public Properties properties(){
return new Properties();
}
}6.測(cè)試代碼
@DisplayName("multipart get config")
@SpringBootTest
public class MultipartGetConfigTest {
private static final Logger log = LoggerFactory.getLogger(MultipartGetConfigTest.class);
@Autowired
private ConfigByConfigurationProperties configByConfigurationProperties;
@Autowired
@Qualifier("configByValueAnnotationV2")
private Properties properties;
@Test
public void getByConfigurationProperties(){
log.info("get by @ConfigurationProperties, value: {}", configByConfigurationProperties.getPort());
log.info("get by @ConfigurationProperties and manual create bean, value: {}", properties.getProperty("port"));
}
}7.測(cè)試結(jié)果
org.spring.demo.MultipartGetConfigTest : get by @ConfigurationProperties, value: 7100
org.spring.demo.MultipartGetConfigTest : get by @ConfigurationProperties and manual create bean, value: 7100
通過(guò) Environment 動(dòng)態(tài)獲取單個(gè)配置
1.作用
用于動(dòng)態(tài)在程序代碼中獲取配置,而配置 key 不需提前定義
2.優(yōu)點(diǎn)
- 獲取的配置的 key 可不提前定義,程序靈活性高
- 配置 key 可使用枚舉統(tǒng)一放置與管理
3.缺點(diǎn)
- 使用較復(fù)雜,需繼承 Environment 接口形成工具類進(jìn)行獲取
- 獲取 key 對(duì)應(yīng)的枚舉與 key 定義分離,value 獲取鏈路較長(zhǎng)
4.使用場(chǎng)景
- 只需使用少量的配置
- 獲取配置的 key 無(wú)提前定義,需要根據(jù)對(duì)配置的有無(wú)進(jìn)行靈活使用
5.代碼示例
@Component
public class ConfigByEnvironment implements EnvironmentAware {
private static final Logger log = LoggerFactory.getLogger(ConfigByEnvironment.class);
private Environment environment;
public Optional<String> get(String configKey){
String config = environment.getProperty(configKey);
return Objects.isNull(config) ? Optional.empty() : Optional.of(config);
}
public void get(String configKey, Consumer<String> consumer){
Optional<String> config = get(configKey);
if(!config.isPresent()){
log.warn("application config, get config by key fail, key: {}", configKey);
}
config.ifPresent(consumer);
}
@Override
public void setEnvironment(@NonNull Environment environment) {
this.environment = environment;
}
}
public enum ConfigByEnvironmentKey {
SERVER_PORT("server.port", "server port");
private String key;
private String description;
ConfigByEnvironmentKey(String key, String description) {
this.key = key;
this.description = description;
}
public String getKey() {
return key;
}
public String getDescription() {
return description;
}
}6.測(cè)試代碼
@DisplayName("multipart get config")
@SpringBootTest
public class MultipartGetConfigTest {
private static final Logger log = LoggerFactory.getLogger(MultipartGetConfigTest.class);
@Autowired
private ConfigByEnvironment configByEnvironment;
@Test
public void getByEnvironment(){
configByEnvironment.get(ConfigByEnvironmentKey.SERVER_PORT.getKey()).ifPresent(value -> log.info("get by environment, value: {}", value));
}
}7.測(cè)試結(jié)果
org.spring.demo.MultipartGetConfigTest : get by environment, value: 7100
總結(jié)
| 獲取配置方式 | 優(yōu)點(diǎn) | 缺點(diǎn) | 使用場(chǎng)景 |
|---|---|---|---|
| 通過(guò) @Value 動(dòng)態(tài)獲取單個(gè)配置 | 使用簡(jiǎn)單,且使用關(guān)聯(lián)的鏈路較短 | 1. 配置名不能被有效枚舉到 2. 每一個(gè)配置的使用都需重新定義,使用較為麻煩 3. 項(xiàng)目強(qiáng)依賴配置的定義,配置不存在則會(huì)導(dǎo)致項(xiàng)目無(wú)法啟動(dòng) | 1. 項(xiàng)目強(qiáng)依賴該配置的加載,想要從源頭避免因配置缺失導(dǎo)致的未知問(wèn)題 2. 只想使用少數(shù)幾個(gè)配置 |
| 通過(guò) @ConfigurationProperties + 前綴方式批量獲取 | 1. 使用配置只需確定 key 的前綴即能使用,有利于批量獲取場(chǎng)景的使用 2. 因采用前綴匹配,所以在使用新的相同前綴 key 的配置時(shí)無(wú)需改動(dòng)代碼 | 1. 使用復(fù)雜,需定義配置類或者手動(dòng)創(chuàng)建 bean 后引入使用 2. 增加新的前綴相同 key 時(shí)可能會(huì)引入不穩(wěn)定因素 | 1. 需要同時(shí)使用多前綴相同 key 的配置 2. 期望增加新配置但不修改代碼的 properties 注入 |
| 通過(guò) Environment 動(dòng)態(tài)獲取單個(gè)配置 | 1. 獲取的配置的 key 可不提前定義,程序靈活性高 2. 配置 key 可使用枚舉統(tǒng)一放置與管理 | 1. 使用較復(fù)雜,需繼承 Environment 接口形成工具類進(jìn)行獲取 2. 獲取 key 對(duì)應(yīng)的枚舉與 key 定義分離,value 獲取鏈路較長(zhǎng) | 1. 只需使用少量的配置 2. 獲取配置的 key 無(wú)提前定義,需要根據(jù)對(duì)配置的有無(wú)進(jìn)行靈活使用 |
以上就是詳解Spring獲取配置的三種方式的詳細(xì)內(nèi)容,更多關(guān)于Spring 獲取配置的資料請(qǐng)關(guān)注腳本之家其它相關(guān)文章!
相關(guān)文章
Java跨平臺(tái)原理與虛擬機(jī)相關(guān)簡(jiǎn)介
這篇文章主要介紹了Java跨平臺(tái)原理與虛擬機(jī)的相關(guān)資料,幫助大家更好的理解和學(xué)習(xí)使用Java,感興趣的朋友可以了解下2021-03-03
SpringBoot多數(shù)據(jù)源的兩種實(shí)現(xiàn)方式實(shí)例
最近在項(xiàng)目開發(fā)中,需要為一個(gè)使用MySQL數(shù)據(jù)庫(kù)的SpringBoot項(xiàng)目,新添加一個(gè)PLSQL數(shù)據(jù)庫(kù)數(shù)據(jù)源,下面這篇文章主要給大家介紹了關(guān)于SpringBoot多數(shù)據(jù)源的兩種實(shí)現(xiàn)方式,需要的朋友可以參考下2022-04-04
druid配置數(shù)據(jù)庫(kù)連接使用密文密碼方式
這篇文章主要介紹了druid配置數(shù)據(jù)庫(kù)連接使用密文密碼方式,具有很好的參考價(jià)值,希望對(duì)大家有所幫助,2023-12-12
Java實(shí)現(xiàn)設(shè)計(jì)模式之責(zé)任鏈模式
責(zé)任鏈模式是一種行為設(shè)計(jì)模式,允許你將請(qǐng)求沿著處理鏈發(fā)送,然后處理者都可對(duì)其進(jìn)行處理,完成后可以再將其傳遞給下一個(gè)處理者。下面將會(huì)舉例說(shuō)明什么是責(zé)任鏈模式,責(zé)任鏈模式該如何使用2022-08-08
詳細(xì)說(shuō)明關(guān)于Java的數(shù)據(jù)庫(kù)連接(JDBC)
這篇文章主要介紹了詳細(xì)說(shuō)明關(guān)于Java的數(shù)據(jù)庫(kù)連接JDBC,JDBC是用Java語(yǔ)言向數(shù)據(jù)庫(kù)發(fā)送SQL語(yǔ)句,需要的朋友可以參考下面文章內(nèi)容2021-09-09

