统一配置中心Spring Cloud Config为各应用环境提供了一个中心化的外部配置。配置服务器默认采用git来存储配置信息,这样就有助于对配置进行版本管理,并且可以通过git客户端工具来方便维护配置内容。当然它也提供本地化文件系统的存储方式。使用集中式配置管理,在配置变更时,可以通知到各应用程序,应用程序不需要重启。Config Server创建Config Server端工程config-server:File -> New->Product… -> 选择Spring Initializr -> Project SDK用1.8 -> Next -> 输入Product Metadata -> Next(springboot选择2.0以上)选择Cloud Discovery -> 选择Eureka Discovery选择Cloud Config -> 选择Config Server由于选择了Eureka Discovery和Config Server,创建成功后pom.xml里已经帮你引入了以下依赖:<dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-config-server</artifactId></dependency><dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId></dependency>Config Server也是要注册到Eureka,作为Eureka Client,我们还要加入如下依赖:<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId></dependency><!– 避免后面的数据库配置出错,mysql依赖也加了 –><dependency> <groupId>mysql</groupId> <artifactId>mysql-connector-java</artifactId></dependency>再给启动类加上注解@EnableDiscoveryClient和@EnableConfigServer:package com.hicoview.config;import org.springframework.boot.SpringApplication;import org.springframework.boot.autoconfigure.SpringBootApplication;import org.springframework.cloud.client.discovery.EnableDiscoveryClient;import org.springframework.cloud.config.server.EnableConfigServer;@SpringBootApplication@EnableDiscoveryClient@EnableConfigServerpublic class EurekaApplication { public static void main(String[] args) { SpringApplication.run(EurekaApplication.class, args); }}配置application.yml:eureka: client: service-url: defaultZone: http://localhost:8761/eureka/spring: application: name: config cloud: config: server: git: uri: http://code.hicoview.com:8000/backend/config.git username: root password: 8ggf9afd6g9gj # 配置文件下载后存储的本地目录 basedir: /Users/zhutx/springcloud/config/basedirserver: port: 9999然后按照配置的git仓库地址,在github或gitlab上创建config仓库。以商品微服务的配置来演示,在config仓库创建product-dev.yml:server: port: 8080spring: datasource: driver-class-name: com.mysql.jdbc.Driver username: root password: passwd_1986 url: jdbc:mysql://127.0.0.1:3306/SpringCloud_Sell?characterEncoding=utf-8&useSSL=false启动作为Config Server的config-server工程,查看http://localhost:8761:访问配置服务端的以下任意地址,都可以显示出对应格式的配置内容:http://localhost:9999/product-dev.ymlhttp://localhost:9999/product-dev.propertieshttp://localhost:9999/product-dev.json可见,Config Server获取到了远程git仓库上的配置,并将其作为自身的REST服务提供了出去。接下来我们看看配置客户端Config Client(即product-server)怎么引用配置。Config Client我们给product-server加入配置客户端的依赖:<dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-config-client</artifactId></dependency>修改application.yml配置:spring: application: name: product cloud: config: discovery: enabled: true service-id: CONFIG profile: deveureka: client: service-url: defaultZone: http://localhost:8761/eureka/这样子就可以从Eureka服务注册中心找到CONFIG服务,并拿到product-dev.yml了。启动product-server,查看eureka注册中心,CONFIG这个Config Server服务已经注册上去了:如果代码里有操作数据库,那么启动其实会出错,因为spring boot不知道配置加载顺序。我们期望先拿到CONFIG的配置,再初始化数据库。解决办法是把product-server的application.yml改成bootstrap.yml就好。微服务工程使用配置服务的情况下,注意将application.yml都改成bootstrap.yml。并且,让bootstrap.yml文件只保留Eureka配置和获取Config Server服务的配置;另外,如果生产环境要使用统一配置中心,可以启动多个Config Server进程,保持高可用。同样的操作,把order-server配置也抽取到外部Spring Cloud Bus下图是当前的配置工作机制,config-server拉取远端git配置,并在本地存一份。然后config-server通过把自身注册到Eureka从而提供了拉取配置的服务,而配置客户端(product和order)通过引入config-client依赖,在启动时便能获取加载到了配置。我们需要做到修改远程配置,应用程序不重启,还需要借助Spring Cloud Bus。Spring Cloud Bus集成了MQ,并为config-server提供了这个配置刷新服务(bus-refresh)。如下图所示,做法是远端git修改配置后,通过webhook调用config-server的/bus-refresh服务,发布RabbitMQ消息,config-client接收消息并更新配置。我们先安装RabbitMQ:# docker安装rabbitmqdocker run -d –hostname my-rabbit -p 5672:5672 -p 15672:15672 rabbitmq:3.7.9-management# 验证下docker ps | grep ‘rabbitmq’能成功访问RabbitMQ控制台http://localhost:15671,继续。修改Config Server端,增加依赖:<dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-bus-amqp</artifactId></dependency>修改application.yml,增加以下配置,把包括bus-refresh在内的所有config server的服务都暴露出来:management: endpoints: web: exposure: include: “*“我们拿product-server来演示,修改product-server的pom增加依赖:<dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-bus-amqp</artifactId></dependency>然后提供一个接口,方便我们在配置变验证结果:@RestController@RequestMapping("/env”)@RefreshScopepublic class EnvController { @Value("${env}”) private String env; @GetMapping("/print") public String print() { return env; }}测试下,我们修改远端git配置,先增加env配置:server: port: 8080spring: datasource: driver-class-name: com.mysql.jdbc.Driver username: root password: passwd_1986 url: jdbc:mysql://127.0.0.1:3306/SpringCloud_Sell?characterEncoding=utf-8&useSSL=false# 增加了该配置env: dev重启下config-server和product-server。访问 product-server http://localhost:8080/env/print,显示dev然后我们把远端env配置项改成test调用config-server的配置刷新服务 bus-refresh:curl -v -X POST http://localhost:9999/actuator/bus-refresh再次访问 product-server http://localhost:8080/env/print,显示test至此,已经做到了变更配置不重启应用。我们再借助Git仓库的webhook功能,在push指令发生后帮我们发个bus-refresh请求就完美了。Gitlab的话在仓库的这个位置:Repository -> Settings -> Integrations -> Add webhook