分布式配置中心: Spring Cloud Config
Spring Cloud Config 是一種用來(lái)動(dòng)態(tài)獲取Git、SVN、本地的配置文件的一種工具
1.為何統(tǒng)一管理微服務(wù)配置
對(duì)于Spring Boot應(yīng)用,我們可以將配置內(nèi)容寫入 application.yml,設(shè)置多個(gè)profile,也可以用多個(gè)application-{profile}.properties文件配置,并在啟動(dòng)時(shí)指定spring.profiles.active={profile}來(lái)加載不同環(huán)境下的配置。
在Spring Cloud微服務(wù)架構(gòu)中,這種方式未必適用,微服務(wù)架構(gòu)對(duì)配置管理有著更高的要求,如:
集中管理:成百上千(可能沒(méi)這么多)個(gè)微服務(wù)需要集中管理配置,否則維護(hù)困難、容易出錯(cuò);
運(yùn)行期動(dòng)態(tài)調(diào)整:某些參數(shù)需要在應(yīng)用運(yùn)行時(shí)動(dòng)態(tài)調(diào)整(如連接池大小、熔斷閾值等),并且調(diào)整時(shí)不停止服務(wù);
自動(dòng)更新配置:微服務(wù)能夠在配置發(fā)生變化是自動(dòng)更新配置。
以上這些要求,傳統(tǒng)方式是無(wú)法實(shí)現(xiàn)的,所以有必要借助一個(gè)通用的配置管理機(jī)制,通常使用配置服務(wù)器來(lái)管理配置。
2.Sping Cloud Config 介紹
Spring Cloud Config分為Config Server和Config Client兩部分,為分布式系統(tǒng)外部化配置提供了支持。 Spring Cloud Config非常適合Spring應(yīng)用程序,也能與其他編程語(yǔ)言編寫的應(yīng)用組合使用。
微服務(wù)在啟動(dòng)時(shí),通過(guò)Config Client請(qǐng)求Config Server以獲取配置內(nèi)容,同時(shí)會(huì)緩存這些內(nèi)容。
config-server 配置服務(wù)端,服務(wù)管理配置信息
config-client 客戶端,客戶端調(diào)用server端暴露接口獲取配置信息
上圖:

3.Config Server
Config Server是一個(gè)集中式、可擴(kuò)展的配置服務(wù)器,它可以集中管理應(yīng)用程序各個(gè)環(huán)境下的配置,默認(rèn)使用Git存儲(chǔ)配置內(nèi)容。
3.1 創(chuàng)建Config Server
3.1.1 創(chuàng)建用于存放配置文件的git倉(cāng)庫(kù),添加配置文件
service1.properties
profile=default-1.0
service1-dev.properties
profile=dev-1.0
service1-test.properties
profile=test-1.0
service1-pro.properties
profile=pro-1.0
3.1.2 創(chuàng)建一個(gè)Spring Boot應(yīng)用config-server,添加spring-cloud-config-server依賴
dependencies {
compile('org.springframework.cloud:spring-cloud-config-server:1.4.1.RELEASE')
}
3.1.3 在啟動(dòng)類添加@EnableConfigServer注解
@EnableConfigServer
@SpringBootApplication
public class Application {
public static void main(String[] args) {
SpringApplication.run(Application.class,args);
}
}
3.1.4 在application.yml中配置Git倉(cāng)庫(kù)地址
server:
port: 8181
spring:
application:
name: config-server
cloud:
config:
server:
git:
uri: https://github.com/Lessismoreputin/spring-cloud-config-repository
username:
password:
3.2 Config Server文件映射
3.2.1 配置文件映射關(guān)系
Config Server啟動(dòng)以后,我們可以通過(guò)它暴露的端點(diǎn)獲取配置文件內(nèi)容,http請(qǐng)求地址與配置文件映射關(guān)系如下:
# 映射{application}-{profile}.properties文件
/{application}/{profile}/[{label}]
/{label}/{application}-{profile}.properties
/{application}-{profile}.properties
/{label}/{application}-{profile}.yml
/{application}-{profile}.yml
{application}通常使用微服務(wù)名稱,對(duì)應(yīng)Git倉(cāng)庫(kù)中文件名的前綴;
{profile}對(duì)應(yīng){application}-后面的dev、pro、test等;
{label}對(duì)應(yīng)Git倉(cāng)庫(kù)的分支名,默認(rèn)為master。
4.Config Client
Config Client是Config Server的客戶端,用于操作存儲(chǔ)在Config Server中的配置內(nèi)容。
4.1 創(chuàng)建Config Client
4.1.1 創(chuàng)建一個(gè)Spring Boot項(xiàng)目config-client,添加依賴
dependencies {
compile('org.springframework.boot:spring-boot-starter-web')
compile('org.springframework.boot:spring-boot-starter-actuator')
compile('org.springframework.cloud:spring-cloud-starter-config:1.4.1.RELEASE')
}
4.1.2 創(chuàng)建配置文件application.yml
通常情況下,Config Client作為微服務(wù)的一部分,微服務(wù)的spring.application.name屬性值決定了Git倉(cāng)庫(kù)中配置文件的的文件名前綴,需要為哪個(gè)微服務(wù)提供配置文件,配置文件的文件名就需要以spring.application.name屬性值作為前綴。
server:
port: 8282
spring:
application:
name: service1 # 對(duì)應(yīng)config-server獲取的配置文件的{application}
4.1.3 創(chuàng)建配置文件bootstrap.yml
Spring Boot應(yīng)用程序啟動(dòng)時(shí)加載application.yml/application.properties。Spring Cloud中有“引導(dǎo)上下文”的概念,引導(dǎo)上下文加載bootstrap.yml/bootstrap.properties,而且具有更高的優(yōu)先級(jí),默認(rèn)情況下bootstrap.yml/bootstrap.properties中的屬性不能被覆蓋。
spring:
application:
name: service1 # 對(duì)應(yīng)config-server獲取的配置文件的{application}
cloud:
config:
uri: http://localhost:8181 # 對(duì)應(yīng)config-server地址,默認(rèn)值http://localhost:8888
profile: pro # 對(duì)應(yīng)config-server獲取的配置文件的{profile}
label: master # 對(duì)應(yīng)config-server獲取的配置文件的{label},即Git倉(cāng)庫(kù)分支
4.1.4 編寫測(cè)試用的Controller
@RestController
public class ConfigController {
@Value("${profile}")
private String profile;
@GetMapping("/profile")
public String profile(){
return this.profile;
}
}
4.2 測(cè)試驗(yàn)證
依次啟動(dòng)config-server:8181和config-client:8282,訪問(wèn)http://localhost:8282/profile,返回如下結(jié)果
pro-1.0
Config Client能夠正常通過(guò)Config Server獲取Git倉(cāng)庫(kù)中指定環(huán)境的配置內(nèi)容。
5.Git倉(cāng)庫(kù)配置
Config Server的application.yml配置文件中,通過(guò)spring.cloud.config.server.git.uri指定Git倉(cāng)庫(kù)地址,實(shí)際上該屬性的配置方式非常靈活,支持多種方式。
5.1 占位符
{application}、{profile}、{label}等占位符可以用于映射配置文件,還可以用于Config Server中配置Git倉(cāng)庫(kù)地址。
5.1.1 使用{application}指定Git倉(cāng)庫(kù)地址
Step 1:在Config Server中用{application}占位符的形式指定Git倉(cāng)庫(kù)地址
spring:
cloud:
config:
server:
git:
uri: https://github.com/Lessismoreputin/{application}
Step 2:在Config Client中修改spring.application.name=spring-cloud-config-repository,因?yàn)榻艘粋€(gè)Git倉(cāng)庫(kù),這里簡(jiǎn)單起見(jiàn),就不再創(chuàng)建新的Git倉(cāng)庫(kù)了。
spring:
application:
name: spring-cloud-config-repository
Step 3:在Git倉(cāng)庫(kù)中創(chuàng)建一個(gè)application-dev.yml的文件
profile: application-test
特別注意:用占位符的形式定義Git倉(cāng)庫(kù)地址時(shí),配置文件的文件名必須為application*.yml或application*.properties。
Step 4:依次啟動(dòng)Config Server和Config Client,訪問(wèn)http://localhost:8282/profile,結(jié)果如下
application-test
6 配置規(guī)則詳解
Config Client從Config Server中獲取配置數(shù)據(jù)的流程:
1.Config Client 啟動(dòng)時(shí),根據(jù) bootstrap.properties 中配置的應(yīng)用名稱(application)、環(huán)境名(profile)和分支名(label),向 Config Server 請(qǐng)求獲取配置數(shù)據(jù);
2.Config Server 根據(jù) Config Client 的請(qǐng)求及配置,從Git倉(cāng)庫(kù)(這里以Git為例)中查找符合的配置文件;
3.Config Server 將匹配到的Git倉(cāng)庫(kù)拉取到本地,并建立本地緩存;
4.Config Server 創(chuàng)建Spring的 ApplicationContext 實(shí)例,并根據(jù)拉取的配置文件, 填充配置信息,然后將該配置信息返回給 Config Client ;
5.Config Client 獲取到 Config Server 返回的配置數(shù)據(jù)后,將這些配置數(shù)據(jù)加載到自己的上下文中。同時(shí),因?yàn)檫@些配置數(shù)據(jù)的優(yōu)先級(jí)高于本地Jar包中的配置,因此將不再加載本地的配置。

那么, Config Server 又是如何與Git倉(cāng)庫(kù)中的配置文件進(jìn)行匹配的呢?通常,我們會(huì)為一個(gè)項(xiàng)目建立類似如下的配置文件:
mallweb.properties : 基礎(chǔ)配置文件;
mallweb-dev.properties : 開發(fā)使用的配置文件;
mallweb-test.properties : 測(cè)試使用的配置文件;
mallweb-prod.properties : 生產(chǎn)環(huán)境使用的配置文件;
當(dāng)我們?cè)L問(wèn) Config Server 的端點(diǎn)時(shí),就會(huì)按照如下映射關(guān)系來(lái)匹配相應(yīng)的配置文件:
/{application}/{profile}[/{label}]
/{application}-{profile}.yml
/{label}/{application}-{profile}.yml
/{application}-{profile}.properties
/{label}/{application}-{profile}.properties
上面的Url將會(huì)映射為格式為:{application}-{profile}.properties(yml)的配置文件。另外, label 則對(duì)應(yīng)Git上分支名稱,是一個(gè)可選參數(shù),如果沒(méi)有則為默認(rèn)的 master 分支。
而 Config-Client 的 bootstrap.properties 配置對(duì)應(yīng)如下:
spring.application.name application;
spring.cloud.config.profile profile;
spring.cloud.config.label label.
7.Config Server健康狀況
Config Server自帶了健康狀況指示器,暴露的endpoint為/health,用于檢查配置的倉(cāng)庫(kù)是否可用。
對(duì)于文中的Config Server,請(qǐng)求http://localhost:8181/health返回如下結(jié)果
{
"status": "UP"
}
Less is more.