Spring Cloud Config & Spring Cloud Bus 学习笔记

Spring Cloud Config & Spring Cloud Bus

Spring Cloud Config

官方文档 https://spring.io/projects/spring-cloud-config

微服务意味着要将单体应用中的业务拆分成一个个子服务,每个服务的粒度相对较小,因此系统中会出现大量的服务。由于每个服务都需要必要的配置信息才能运行,所以一套集中式的、动态的配置管理设施是必不可少的。

是什么

​ Spring Cloud Config provides server and client-side support for externalized configuration in a distributed system. With the Config Server you have a central place to manage external properties for applications across all environments. The concepts on both client and server map identically to the Spring Environment and PropertySource abstractions, so they fit very well with Spring applications, but can be used with any application running in any language. As an application moves through the deployment pipeline from dev to test and into production you can manage the configuration between those environments and be certain that applications have everything they need to run when they migrate. The default implementation of the server storage backend uses git so it easily supports labelled versions of configuration environments, as well as being accessible to a wide range of tooling for managing the content. It is easy to add alternative implementations and plug them in with Spring configuration.

Spring Cloud Config为分布式系统中的外部化配置提供了服务器和客户端支持。 通过配置服务器,您可以在所有环境中管理应用程序的外部属性。 客户端和服务器上的概念都映射到SpringEnvironmentPropertySource 抽象,因此它们非常适合Spring应用程序,但也可以用于以任何语言运行的任何应用程序。 当应用程序通过部署管道从开发到测试再到生产时,您可以管理这些环境之间的配置,并确保应用程序在迁移时拥有运行所需的一切。 服务器存储后端的默认实现使用git,因此它很容易支持带标签的配置环境版本,并且可以使用各种工具来管理内容。 很容易添加替代实现并将它们与Spring配置一起插入。

能干嘛

  • 不同环境不同配置,动态化的配置更新,分环境部署比如dev/test/prod/beta/release
  • 运行期间动态调整配置,不再需要在每个服务部署的机器上编写配置文件,服务会向配置中心统一拉取配置自己的信息
  • 当配置发生变动时,服务不需要重启即可感知到配置的变化并应用新的配置
  • 将配置信息以REST接口的形式暴露

Demo

建议先看看配置读取规则:

# 方式一
http://localhost:3344/master/config-dev.yml 对应 /{label}/{application}-{profile}.yml
# 方式二
http://localhost:3344/config-dev.yml 对应 /{application}-{profile}.yml
# 方式三
http://localhost:3344/config/dev/master 对应 /{application}/{profile}[/{label}]

推荐使用gitee来跑示例,github经常访问不了

  • 先新建一个仓库,添加对应的配置文件

新建模块cloud-config-center-3344 服务端

依赖

<dependencies>
    <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.boot</groupId>
        <artifactId>spring-boot-starter-web</artifactId>
    </dependency>

    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-actuator</artifactId>
    </dependency>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-devtools</artifactId>
        <scope>runtime</scope>
        <optional>true</optional>
    </dependency>
    <dependency>
        <groupId>org.projectlombok</groupId>
        <artifactId>lombok</artifactId>
        <optional>true</optional>
    </dependency>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-test</artifactId>
        <scope>test</scope>
    </dependency>
</dependencies>

配置

server:
  port: 3344

spring:
  application:
    name:  cloud-config-center #注册进Eureka服务器的微服务名
  cloud:
    config:
      server:
        git:
          uri: https://github.com/Ramelon/springcloud-config.git #GitHub上面的git仓库名字
        ####搜索目录
          search-paths:
            - springcloud-config
      ####读取分支
      label: master

#服务注册到eureka地址
eureka:
  client:
    service-url:
      defaultZone: http://localhost:7001/eureka

主启动类

/*
Spring Cloud Config Server provides an HTTP resource-based API for external configuration (name-value pairs or equivalent YAML content). The server is embeddable in a Spring Boot application, by using the @EnableConfigServer annotation.
*/
@SpringBootApplication
@EnableConfigServer
public class ConfigCenterMain3344{
    public static void main(String[] args) {
            SpringApplication.run(ConfigCenterMain3344.class, args);
    }
}

配置完成后: 访问http://localhost:3344/master/config-dev.yml,即可以获取对应的配置。

新建模块 cloud-config-client-3355

依赖

<dependencies>
    <dependency>
        <groupId>org.springframework.cloud</groupId>
        <artifactId>spring-cloud-starter-config</artifactId>
    </dependency>
    <dependency>
        <groupId>org.springframework.cloud</groupId>
        <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
    </dependency>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-web</artifactId>
    </dependency>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-actuator</artifactId>
    </dependency>

    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-devtools</artifactId>
        <scope>runtime</scope>
        <optional>true</optional>
    </dependency>
    <dependency>
        <groupId>org.projectlombok</groupId>
        <artifactId>lombok</artifactId>
        <optional>true</optional>
    </dependency>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-test</artifactId>
        <scope>test</scope>
    </dependency>
</dependencies>

配置

注意这里的文件不是application.xml而是bootstrap.xml

applicaiton.yml是用户级的资源配置项bootstrap.yml是系统级的,优先级更加高。Spring Cloud会创建一个Bootstrap Context,作为Spring应用的Application Context的父上下文。初始化的时候,Bootstrap Context负责从外部源加载配置属性并解析配置。这两个上下文共享一个从外部获取的Environment

server:
  port: 3355

spring:
  application:
    name: config-client
  cloud:
    #Config客户端配置
    config:
      label: master #分支名称
      name: config #配置文件名称
      profile: dev #读取后缀名称   上述3个综合:master分支上config-dev.yml的配置文件被读取http://localhost:3344/master/config-dev.yml
      uri: http://localhost:3344 #配置中心地址k

#服务注册到eureka地址
eureka:
  client:
    service-url:
      defaultZone: http://localhost:7001/eureka

主启动类

@EnableEurekaClient
@SpringBootApplication
public class ConfigClientMain3355{
    public static void main(String[] args){
        SpringApplication.run(ConfigClientMain3355.class,args);
    }
}

控制层

@RestController
public class ConfigClientController{
    @Value("${config.info}")
    private String configInfo;

    @GetMapping("/configInfo")
    public String getConfigInfo() {
        return configInfo;
    }
}

测试

http://localhost:3355/configInfo

查看仓库上对应的配置文件内容,成功实现了客户端3355访问SpringCloud Config3344通过GitHub获取配置信息

存在的问题

这个时候修改GitHub上面的配置文件,3344服务端可以立即响应出对应的信息,但是3355一定要重启才能刷新,不能动态刷新。

解决办法:动态刷新

需要引入spring-boot-starter-actuator依赖

配置增加

# 暴露监控端点
management:
  endpoints:
    web:
      exposure:
        include: "*"

控制层

增加@RefreshScope注解。

测试

修改GitHub文件

curl -X POST “http://localhost:3355/actuator/refresh”

访问http://localhost:3355/configInfo

发现能过得修改的配置文件

但是还是存在很多问题,如果存在多个微服务就要一次发送POST请求

现在需求一次通知,处处生效。下面的Bus很好的解决这个问题。

Spring Cloud Bus

什么是总线

在微服务架构的系统中,通常会使用轻量级的消息代理来构建一个共用的消息主题,并让系统中所有微服务实例都连接上来。由于该主题中产生的消息会被所有实例监听和消费,所以称它为消息总线。在总线上的各个实例,都可以方便地广播一些需要让其他连接在该主题上的实例都知道的消息。

基本原理

ConfigClient实例都监听MQ中同一个topic(默认是springCloudBus)。当一个服务刷新数据的时候,它会把这个信息放入到Topic中,这样其它监听同一Topic的服务就能得到通知,然后去更新自身的配置。

是什么

Spring Cloud Bus links nodes of a distributed system with a lightweight message broker. This can then be used to broadcast state changes (e.g. configuration changes) or other management instructions. AMQP and Kafka broker implementations are included with the project. Alternatively, any Spring Cloud Stream binder found on the classpath will work out of the box as a transport.

Spring Cloud Bus用轻量级消息代理连接分布式系统的节点。 这可以用于广播状态更改(例如配置更改)或其他管理指令。 AMQP和Kafka代理实现包含在项目中。 或者,在类路径上找到的任何Spring Cloud Stream绑定器都可以作为传输工具开箱即用。

注:需要提前装好RabbitMQ

https://blog.csdn.net/Ramelon/article/details/129785224

Demo

新建模块 cloud-config-client-3366 这里不再演示,和3355的代码基本一致

  • 为3344/3355/3366添加Bus支持
<!--添加消息总线RabbitMQ支持-->
<dependency>
    <groupId>org.springframework.cloud</groupId>
    <artifactId>spring-cloud-starter-bus-amqp</artifactId>
</dependency>
  • 3344
##rabbitmq相关配置,暴露bus刷新配置的端点
management:
  endpoints: #暴露bus刷新配置的端点
    web:
      exposure:
        include: 'bus-refresh'
  • 3355/3366
# rabbitmq相关配置 15672是Web管理界面的端口;5672是MQ访问的端口
# 这里提一下如果在linux下安装的话,需要把下面对应的配置改成自己的配置
spring:  
  rabbitmq:
    host: localhost
    port: 5672
    username: guest
    password: guest
这里详细介绍下消息总线触发的两种方式
  • 利用消息总线触发一个客户端/bus/refresh,而刷新所有客户端的配置(刷新某个实例后实例发送消息到总线、总线把接收的消息发送到其他的实例上,再去服务端获取配置)
  • 利用消息总线触发一个服务端ConfigServer的/bus/refresh端点,而刷新所有客户端的配置(刷新服务端后,服务端发送消息到总线,总线再把接受的消息发送给实例,这些实例最后去服务端获取配置)

总结

方法二更合理

方法一不合理原因如下:

  • 打破了微服务的职责单一性,因为微服务本身是业务模块,它本不应该承担配置刷新的职责。
  • 破坏了微服务各节点的对等性
  • 有一定的局限性。例如,微服务在迁移时,它的网络地址常常会发生变化,此时如果想要做到自动刷新,那就会增加更多的修改
测试
  • 修改GitHub配置文件

  • curl -X POST “http://localhost:3344/actuator/bus-refresh”

  • http://config-3344.com:3344/config-dev.yml 能获取配置

  • http://localhost:3355/configInfo 能获取配置

  • http://localhost:3366/configInfo 能获取配置

问题

如何做到指定的更新,不指定的不更新

如下:

curl -X POST “http://localhost:3344/actuator/bus-refresh/config-client:3355”

这样只通知3355,不通知3366

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Spring Cloud Config是一个分布式配置管理工具,它提供了集中式的外部配置管理,可以帮助我们在微服务架构中管理和维护应用程序的配置。 Spring Cloud Config的核心思想是将应用程序的配置从代码中分离出来,以便在不重新部署应用程序的情况下进行配置的修改和更新。它使用Git或其他版本控制系统来存储和管理配置文件,并通过HTTP或消息总线将配置文件提供给应用程序。 Spring Cloud Config的主要组件包括: 1. Config Server:配置服务器,负责从Git或其他版本控制系统中读取配置文件,并将其提供给客户端应用程序。它可以通过HTTP或消息总线的方式将配置文件推送给客户端。 2. Config Client:配置客户端,是应用程序中的一个模块,负责从Config Server获取配置文件,并将其应用到应用程序中。 3. Spring Cloud Bus:消息总线,用于在微服务架构中传播配置文件的变更。当配置文件发生变化时,Config Server会通过消息总线通知所有的Config Client,从而实现配置的动态更新。 使用Spring Cloud Config可以实现以下功能: 1. 集中式管理和维护应用程序的配置,避免了在每个应用程序中硬编码配置信息的问题。 2. 实现配置的动态更新,当配置文件发生变化时,应用程序可以自动获取最新的配置。 3. 支持多环境的配置管理,可以为不同的环境提供不同的配置文件。 4. 支持配置的版本控制,可以通过Git或其他版本控制系统管理配置文件的历史记录。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值