3:SpringCloud Config配置中心的bus动态刷新
概念从上一节 [2:SpringCloud Config配置中心] 中可以看到当配置中心服务中的配置变更后,如果不重启各个客户端服务,客户端服务无法获取到变更后的配置内容。为了解决这一问题,SpringCloud提供了一个消息总线(SpringCloud Bus),它本质上是一个消息系统,目前有rabbitmq和kafka两种实现。原理1,当配置变更后,我们调用刷新接口:默认为 ht...
概念
从上一节 [2:SpringCloud Config配置中心] 中可以看到当配置中心服务中的配置变更后,如果不重启各个客户端服务,客户端服务无法获取到变更后的配置内容。
为了解决这一问题,SpringCloud提供了一个消息总线(SpringCloud Bus),它本质上是一个消息系统,目前有rabbitmq和kafka两种实现。
原理
- 1,当配置变更后,我们调用刷新接口:默认为 http://ip:port/actuator/bus-refresh ,图中的bus/refresh是D版以前的接口,我们现在是基于G版的代码,默认已经变成了/actuator/bus-refresh
注:这里的 ip:port 可以是任意一个接入到了消息总线bus的服务,由于一般其它业务服务都是通过gateway来调用的,并不对外暴露 ip:port,而配置中心configServer是需要对外暴露ip的,所以一般会在注册中心configServer上调用刷新接口 - 2,注册中心configServer接收到刷新命令后,会把刷新消息广播到SpringCloud Bus消息总线
- 3,其它各个服务会接受到SpringCloud Bus消息总线广播的刷新消息,
- 4,各个服务重新从注册中心configServer上面拉取变更后的配置
springCloud Config配置中心
先创建并启动一个接入SpringCloud Bus消息总线的配置中心服务:
1,创建一个maven项目scd-config-server-bus
项目名称可以按需自定义
2,引入pom依赖
<?xml version="1.0"?>
<project xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd" xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<modelVersion>4.0.0</modelVersion>
<parent>
<!-- https://mvnrepository.com/artifact/org.springframework.cloud/spring-cloud-starter-parent -->
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-parent</artifactId>
<version>Greenwich.RELEASE</version>
</parent>
<groupId>com.scd</groupId>
<artifactId>scd-config-server-bus</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>scd-config-server-bus</name>
<url>http://maven.apache.org</url>
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<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>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-bus-amqp</artifactId>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
</project>
- 引入消息总线spring-cloud-starter-bus-amqp,消息总线有rabbitm和kafka两种实现,如果用kafka的话,引入spring-cloud-starter-bus-kafka即可。我们用rabbitmq作为示例
3,启动类上加@EnableConfigServer注解
@SpringBootApplication
@EnableConfigServer
public class Application {
public static void main(String[] args) {
SpringApplication.run(Application.class, args);
}
}
4,加上application.yml配置
spring:
application:
name: scd-config-server-bus
profiles:
active:
- native #使用本地配置
cloud:
config:
server:
bootstrap: true
native:
search-locations:
- classpath:config-repo/ # 搜索src/main/resource 下的config-repo文件夹下的文件
# git配置
# git:
# uri: https://gitee.com/ifrozen/spring-cloud-demo
# search-paths:
# - config-repo
# username: username
# password: password
#-------------------------------------------------------------------------
rabbitmq:
host: 192.168.14.231
port: 5672
username: i5x
password: i5xrabbitmq
virtual-host: i5x
#-------------------------------------------------------------------------
management:
# actuator的端口可以单独定义,如果不定义的话,默认为${server.port}
# server:
# port: 31000
endpoints:
web:
exposure:
include: "*" #默认只暴露了/actuator/info和/actuator/health,没有暴露/actuator/bus-refresh,这里把所有endpoints都暴露了
cors:
allowed-origins: "*"
allowed-methods: "*"
#---------------------------------------------------------------------
server:
port: 50010
#---------------------------------------------------------------------
eureka:
instance:
prefer-ip-address: true
status-page-url-path: /actuator/info
health-check-url-path: /actuator/health
hostname: localhost
client:
register-with-eureka: true #把本服务也注册到注册中心,从注册中心的服务列表中可以看到本服务
fetch-registry: true #从注册中心拉取服务列表
service-url:
defaultZone: http://localhost:50000/eureka/
- spring.rabbitmq.xxx为rabbitmq的连接配置,消息总线需要使用rabbitmq来通信
- management.endpoints.web.exposure.include: “*”,表示把所有endpoints端点都暴露出去,默认只暴露了/actuator/info和/actuator/health,没有暴露/actuator/bus-refresh
- management.endpoints.web.exposure.cors为跨域设置
5,创建配置仓库
在上面一步中设置了spring.cloud.config.server.native.search-locations为classpath:config-repo/ ,即仓库位置为src/main/resource 下的config-repo文件夹
我们创建scd-biz-smile-dev.yml,scd-biz-smile-test.yml,scd-biz-smile-prod.yml三个配置文件,分别代表调试,测试和正式环境的配置文件。
里面只有一个属性smile,值分别为dev,test,prod。例scd-biz-smile-dev.yml
smile: dev
完整示例代码可以参照:https://gitee.com/ifrozen/spring-cloud-demo/tree/master/demo-3
6,启动配置中心服务
启动配置中心服务,访问 http://localhost:50000/ 可以看到配置中心服务的启动状况
springCloud Config客户端
创建并启动一个接入消息总线SpringCloud Bus的客户端服务:
1,创建一个maven项目scd-biz-smile-bus
项目名称可以按需自定义
2,引入pom依赖
<?xml version="1.0"?>
<project xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd" xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<modelVersion>4.0.0</modelVersion>
<parent>
<!-- https://mvnrepository.com/artifact/org.springframework.cloud/spring-cloud-starter-parent -->
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-parent</artifactId>
<version>Greenwich.RELEASE</version>
</parent>
<groupId>com.scd</groupId>
<artifactId>scd-biz-smile-bus</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>scd-biz-smile-bus</name>
<url>http://maven.apache.org</url>
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>
spring-cloud-starter-netflix-hystrix
</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-config</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-bus-amqp</artifactId>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
</project>
- 引入消息总线spring-cloud-starter-bus-amqp,消息总线有rabbitm和kafka两种实现,如果用kafka的话,引入spring-cloud-starter-bus-kafka即可。我们用rabbitmq作为示例
3,启动类,普通的SpringCloudApplication启动类即可
@SpringCloudApplication
public class Application {
public static void main(String[] args) {
SpringApplication.run(Application.class, args);
}
}
创建一个普通controller类读取配置文件中的smile属性,一定要加上@RefreshScope注解,否则不会被bus刷新:
@RefreshScope
@RestController
public class SmileController {
@Value("${smile}")
private String smile;
@GetMapping("/config")
public String config() {
return smile;
}
}
消息总线会刷新两种类中的配置属性
- @RefreshScope注解修饰的类
- @ConfigurationProperties注解定义的类:例spring.rabbitmq的定义类RabbitProperties
@ConfigurationProperties(prefix = "spring.rabbitmq")
public class RabbitProperties {
/**
* RabbitMQ host.
*/
private String host = "localhost";
/**
* RabbitMQ port.
*/
private int port = 5672;
/**
* Login user to authenticate to the broker.
*/
private String username = "guest";
/**
* Login to authenticate against the broker.
*/
private String password = "guest";
.......
.......
}
4,yml配置文件
由于从配置中心拉取配置仓库要先于其它功能的启动,其它功能才能读取到配置。
所以配置文件需要增加一个bootstrap.yml,spring启动的时候,会先读取bootstrap.yml的配置来启动,然后再读取application.yml的配置来启动。
使用配置中心后,客户端服务的eureka配置和config配置必须写到bootstrap.yml里面去,其它配置可以写到application.yml里面去。
bootstrap.yml
spring:
cloud:
config:
discovery:
enabled: true
service-id: scd-config-server-bus
label: config-repo
name: scd-biz-smile
profile: dev
#---------------------------------------------------------------------
eureka:
instance:
prefer-ip-address: true
status-page-url-path: /actuator/info
health-check-url-path: /actuator/health
hostname: localhost
client:
register-with-eureka: true #把本服务也注册到注册中心,从注册中心的服务列表中可以看到本服务
fetch-registry: true #从注册中心拉取服务列表
service-url:
defaultZone: http://localhost:50000/eureka/
- spring.cloud.config.discovery.enabled用来开启配置中心
- spring.cloud.config.discovery.service-id指定配置中心服务
- spring.cloud.config.label对应配置仓库的目录,本例中为 config-repo
- spring.cloud.config.name对应配置文件名称最后一个 - 符号前面的名称,本例中为 scd-biz-smile
- spring.cloud.config.profile对应配置文件名称最后一个 - 符号后面的名称,本例中为 dev
application.yml
spring:
application:
name: scd-biz-smile-bus
#-------------------------------------------------------------------------
rabbitmq:
host: 192.168.14.231
port: 5672
username: i5x
password: i5xrabbitmq
virtual-host: i5x
#---------------------------------------------------------------------
server:
port: 50020
servlet:
context-path: /smile
#---------------------------------------------------------------------
- server.servlet.context-path为项目名
- spring.rabbitmq.xxx为rabbitmq的连接配置,消息总线需要使用rabbitmq来通信
完整示例代码可以参照:https://gitee.com/ifrozen/spring-cloud-demo/tree/master/demo-3
启动服务后,可以现在 http://localhost:50000/ 查看服务启动情况:
访问 http://localhost:50020/smile/config rest接口:
springCloud bus刷新配置
1,修改配置仓库的scd-biz-smile-dev.yml文件,把smile值改为dev-update:
smile: dev-update
2,然后不重启scd-biz-smile服务,直接访问 http://localhost:50020/smile/config rest接口,发现返回的还是变更前的dev
3,利用postman或者curl工具,发送post http://localhost:50010/actuator/bus-refresh ,这里的localhost:50010为注册中心服务scd-config-server-bus的ip和port,只有其暴露了/actuator/bus-refresh端点
可以查看scd-biz-smile-bus服务的log
4,再次访问 http://localhost:50020/smile/config rest接口:
可见已经取到了最新的配置值
更多推荐
所有评论(0)