Tip: 此篇已加入.NET Core微服務基礎系列文章索引
=> Steeltoe目錄快速導航:
1. 基於Steeltoe使用Spring Cloud Eureka
2. 基於Steeltoe使用Spring Cloud Zuul
3. 基於Steeltoe使用Spring Cloud Hystrix
4. 基於Steeltoe使用Spring Cloud Config
一、關於Spring Cloud Config
在分散式系統中,每一個功能模組都能拆分成一個獨立的服務,一次請求的完成,可能會呼叫很多個服務協調來完成,為了方便服務配置檔案統一管理,更易於部署、維護,所以就需要分散式配置中心元件了,在Spring Cloud中,就有這麼一個分散式配置中心元件 — Spring Cloud Config。
Spring Cloud Config 為分散式系統中的外部配置提供伺服器和客戶端支援。使用Config Server,我們可以為所有環境中的應用程式管理其外部屬性。它非常適合spring應用,也可以使用在其他語言的應用上。隨著應用程式通過從開發到測試和生產的部署流程,我們可以管理這些環境之間的配置,並確定應用程式具有遷移時需要執行的一切。伺服器儲存後端的預設實現使用git,因此它輕鬆支援標籤版本的配置環境,以及可以訪問用於管理內容的各種工具。
Spring Cloud Config的原理圖大致如下圖(此圖來自mazen1991)所示:
我們將配置檔案放入git或者svn等服務中,通過一個Config Server服務來獲取git中的配置資料,而我們需要使用的到配置檔案的Config Client系統可以通過Config Server來獲取對應的配置。
二、快速構建Config Server
示例版本:Spring Boot 1.5.15.RELEASE,Spring Cloud Edgware.SR3
(1)新增Spring Cloud Config相關依賴包
<dependencies> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter</artifactId> </dependency> <!-- 熱啟動,熱部署依賴包,為了除錯方便,加入此包 --> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-devtools</artifactId> <optional>true</optional> </dependency> <!-- spring cloud config --> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-config-server</artifactId> </dependency> </dependencies> <!-- spring cloud dependencies --> <dependencyManagement> <dependencies> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-dependencies</artifactId> <version>Edgware.SR3</version> <type>pom</type> <scope>import</scope> </dependency> </dependencies> </dependencyManagement>
(2)啟動類新增註解
@SpringBootApplication @EnableConfigServer public class ConfigServiceApplication { public static void main(String[] args) { SpringApplication.run(ConfigServiceApplication.class, args); } }
(3)Config相關配置項
server: port: 8888 spring: application: name: config-server cloud: config: server: git: # 配置Git倉庫地址 uri: https://github.com/EdisonChou/Microservice.PoC.Steeltoe # 配置搜尋目錄 search-paths: config # Git倉庫賬號(如果需要認證) username: # Git倉庫密碼(如果需要認證) password:
這裡我在GitHub中(https://github.com/EdisonChou/Microservice.PoC.Steeltoe/config目錄中)放了一個sample-service-foo.properties的配置檔案,裡面只有兩行內容:
info.profile=default-1.0 info.remarks=this is a remarks of default profile
此外,對於Spring Cloud Config,端點與配置檔案的對映規則如下:
/{application}/{profile}[/{label}]
/{application}-{profile}.yml
/{label}/{application}-{profile}.yml
/{application}-{profile}.properties
/{label}/{application}-{profile}.properties
其中,application: 表示微服務的虛擬主機名,即配置的spring.application.name
profile: 表示當前的環境,dev, test or production?
label: 表示git倉庫分支,master or relase or others repository name? 預設是master
三、ASP.NET Core中整合Config Server
(1)快速準備一個ASP.NET Core WebAPI專案(示例版本:2.1),這裡以上一篇示例程式碼中的AgentService為例
(2)通過NuGet安裝Config相關包:
PM>Install-Package Steeltoe.Extensions.Configuration.ConfigServerCore
(3)改寫Program類
public class Program { public static void Main(string[] args) { CreateWebHostBuilder(args).Build().Run(); } public static IWebHostBuilder CreateWebHostBuilder(string[] args) => WebHost.CreateDefaultBuilder(args) .AddConfigServer() // Add config server via steeltoe .UseUrls("http://*:8010") .UseStartup<Startup>(); }
(3)改寫Starup類
public class Startup { public Startup(IConfiguration configuration) { Configuration = configuration; } public IConfiguration Configuration { get; } // This method gets called by the runtime. Use this method to add services to the container. public void ConfigureServices(IServiceCollection services) { services.AddOptions(); // Add Steeltoe Discovery Client service client services.AddDiscoveryClient(Configuration); // Add Steeltoe Config Client service container services.AddConfiguration(Configuration); services.AddMvc().SetCompatibilityVersion(CompatibilityVersion.Version_2_1); // Add Configuration POCO services.Configure<ConfigServerData>(Configuration); } // This method gets called by the runtime. Use this method to configure the HTTP request pipeline. public void Configure(IApplicationBuilder app, IHostingEnvironment env) { if (env.IsDevelopment()) { app.UseDeveloperExceptionPage(); } app.UseMvc(); // Add Steeltoe Discovery Client service app.UseDiscoveryClient(); } }
(4)為自定義配置內容封裝一個類
public class ConfigServerData { public Info Info { get; set; } } public class Info { public string Profile { get; set; } public string Remarks { get; set; } }
對應:info.profile 以及 info.remarks
(5)改寫Controller,通過依賴注入獲取Config內容
[Route("api/[controller]")] [ApiController] public class ValuesController : ControllerBase { private IOptionsSnapshot<ConfigServerData> IConfigServerData { get; set; } private IConfigurationRoot Config { get; set; } public ValuesController(IConfigurationRoot config, IOptionsSnapshot<ConfigServerData> configServerData) { if (configServerData != null) { IConfigServerData = configServerData; } Config = config; } [HttpGet] [Route("/refresh")] public IActionResult Refresh() { if (Config != null) { Config.Reload(); } return Ok("Refresh Config Successfully!"); } // GET api/values [HttpGet] public ActionResult<IEnumerable<string>> Get() { var config = IConfigServerData.Value; return new string[] { $"Profile : {config.Info.Profile}", $"Remarks : {config.Info.Remarks}" }; } }
這裡提供了一個重新整理Config的方法Refresh,由於在沒有藉助訊息匯流排的情況下,Config Server的Config重新整理之後不會推送到各個Config Client,因此需要各個Config Client手動Refresh一下,如下圖所示:
這裡也提一下Spring Cloud Config推薦的重新整理配置的方式,即整合Spring Cloud Bus,如下圖所示:
從上圖中我們可以看出,它將Config Server加入訊息匯流排之中,並使用Config Server的/bus/refersh端點來實現配置的重新整理(一個觀察者模式的典型應用)。這樣,各個微服務只需要關注自身的業務邏輯,而無需再自己手動重新整理配置。但是,遺憾的是,Pivotal目前在Steeltoe中還沒有為.NET應用程式提供Spring Cloud Bus的整合,不過可以研究其機制,通過訊息佇列的客戶端如RabbitMQ.Client去自己定製響應事件。
四、快速驗證
(1)從Config Server中獲取sampleservice-foo.properties配置檔案
(2)啟動AgentService,驗證是否能從ConfigServer獲取到正確的配置內容
(3)修改配置檔案的屬性值:info.profile改為default-1.1,然後提交到github倉庫
(4)驗證Config Server是否已經獲取到最新的info.profile
(5)手動重新整理AgentService的Config物件
(6)驗證是否能夠獲取最新的info.profile
五、小結
本文極簡地介紹了一下Spring Cloud Config,並快速構建了一個用於演示的Config Server,然後通過Steeltoe OSS提供的Config客戶端將ASP.NET Core與Spring Cloud Config進行整合,最後進行了驗證能夠正常地從Config Server中獲取最新的配置內容。當然,關於Spring Cloud Config的內容還有許多,如果要真正使用Spring Cloud Config還需要考慮如何實現自動重新整理的問題。從Spring Cloud Config與Apollo的使用體驗上來說,本人是更加喜歡Apollo的,無論是功能的全面性和使用的體驗來說,Apollo更勝一籌,而且國內的落地案例也更多。因此,如果專案中需要使用或整合統一配置中心,Apollo會是首選。
示例程式碼
Click => https://github.com/EdisonChou/Microservice.PoC.Steeltoe/tree/master/src/Chapter3-ConfigServer
參考資料
Steeltoe官方文件:《Steeltoe Doc》
Steeltoe官方示例:https://github.com/SteeltoeOSS/Samples
蟋蟀,《.NET Core 微服務架構 Steeltoe的使用》
周立,《Spring Cloud與Docker 微服務架構實戰》
mazhen1991,《使用Spring Cloud Config來統一管理配置檔案》
冰與火IAF,《Spring Cloud:分散式配置中心 Config》