Spring Cloud Bus消息总线

6 篇文章 0 订阅

Spring Cloud Bus

Spring Cloud Bus是什么

Spring Cloud Bus叫事件总线,当我们的系统中服务越来越多之后,维护这样的刷新清单将会变得非常繁琐麻烦,而且容易犯错。Spring Cloud Bus使用 message broker 来连接分布式系统的所有节点。它可以用于广播配置文件的更改或者服务之间的通讯,也可以用于监控。本文要讲述的是用Spring Cloud Bus实现通知微服务架构的配置文件的更改。

SpringCloud Bus会向外提供一个http接口,即下图中的/bus/refresh。我们将这个接口配置到git的webhook上,当git上的内容发生改变时,就会自动调用/bus/refresh接口。Bus就会通知ConfigServer,configserver会发布更新消息到消息总线的消息队列,其他服务订阅到该消息就会信息刷新,从而实现整个微服务进行自动刷新。

Spring Cloud Bus的两种实现方式图解

  • f方法1 : 某个微服务承担刷新配置的任务

①提交配置出发post请求调用客户端A-3的/bus/refresh接口(spring boot 2.0.x以后是/actuator/bus-refresh)

②客户端A-3收到请求从Server端更新配置并且发送给Spring Cloud Bus消息总线

③Spring Cloud Bus接收消息并通知给其他连线在总线上的客户端,所有总线上的客户端均能接收到消息。

④其他客户端接收到消息,请求Server端获取最新配置

⑤全部客户端均获取到最新的配置

以上方式存在两个问题

  1. 微服务本身是业务模块,而不应该承担配置刷新的职责,打破了微服务的单一原则.
  2. WebHook的配置也随着承担刷新配置的微服务节点发生变化.
  • 方法2: 配置中心Server端承担起配置刷新的职责

①提交配置触发post请求给server端的/bus/refresh接口(spring boot 2.0.x以后是/actuator/bus-refresh)

②server端接收到请求并发送给SpringCloud Bus总线

③Sping Cloud Bus接收到消息并通知给其他连接的总线的客户端

④其他客户端接收到通知,请求Server端获取最新配置

⑤全部客户端获取到最新的配置

我们看到WebHook的直接请求server端,WebHook的配置不会发生变化,Server端承担起配置刷新的职责,不要业务端处理刷新了.完美解决上述的问题.

快速开始一个Spring Cloud Bus

Spring Cloud Bus通过添加Spring Boot自动配置,您需要做的是启用总线是将spring-cloud-starter-bus-amqpspring-cloud-starter-bus-kafka添加到您的依赖关系管理中,配置上RabbitMQ或Kafka环境,如果是配置RabbitMQ,application.yml中需添加RabbitMQ的配置信息,如下:

spring:
  rabbitmq:
    host: mybroker.com
    port: 5672
    username: user
    password: secret

/actuator/*执行器命名空间下还有一些http端点. /actuator/bus-refresh/{destination}和/actuator/bus-refresh.其中destination目的地是ApplicationContext ID,默认情况下,Spring Boot将ContextIdApplicationContextInitializer中的ID设置为spring.application.name,活动配置文件和server.port的组合。比如/actuator/bus-refresh?destination=customers:**" 即刷新服务名为customers的所有服务。/actuator/bus-refresh将重新加载每个应用程序的配置.一定要是Post请求,并且配置文件中加上注解如下:

management.endpoints.web.exposure.include=bus-refresh

Spring Cloud Bus的实例演示

  • 修改所有节点的配置
  1. 新建5个Demo放在github上 https://github.com/fangjian0423/rocketmq-binder-demo/tree/master/rocketmq-bus-demo
  2. 访问任意节点提供的 Controller 提供的获取配置的地址(key为hangzhou):
curl -X GET 'http://localhost:10001/bus/env?key=hangzhou'

所有节点返回的结果都是 unknown,因为所有节点的配置中没有 hangzhou 这个 key。

  1. Bus 内部提供了 EnvironmentBusEndpoint 这个 Endpoint 通过 message broker 用来新增/更新配置。

    访问任意节点该 Endpoint 对应的 url /actuator/bus-env?name=hangzhou&value=alibaba 进行配置项的新增(比如访问 node1 的url):

curl -X POST 'http://localhost:10001/actuator/bus-env?name=hangzhou&value=alibaba' -H 'content-type: application/json'
  1. 再次访问所有节点 /bus/env 获取配置:
$ curl -X GET 'http://localhost:10005/bus/env?key=hangzhou'
alibaba%
~ ⌚
$ curl -X GET 'http://localhost:10004/bus/env?key=hangzhou'
alibaba%
~ ⌚
$ curl -X GET 'http://localhost:10003/bus/env?key=hangzhou'
alibaba%
~ ⌚
$ curl -X GET 'http://localhost:10002/bus/env?key=hangzhou'
alibaba%
~ ⌚
$ curl -X GET 'http://localhost:10001/bus/env?key=hangzhou'
alibaba%

所有节点都新增了一个 key 为 hangzhou 的配置,且对应的 value 是 alibaba

  • 修改部分节点的配置
  1. 比如在 node1 上指定 destination 为 rocketmq-bus-node2 (node2 配置了 spring.cloud.bus.id 为 rocketmq-bus-node2:10002,可以匹配上) 进行配置的修改:
curl -X POST 'http://localhost:10001/actuator/bus-env/rocketmq-bus-node2?name=hangzhou&value=xihu' -H 'content-type: application/json'
  1. 获取配置如下:
$ curl -X GET 'http://localhost:10005/bus/env?key=hangzhou'
alibaba%
~ ⌚
$ curl -X GET 'http://localhost:10004/bus/env?key=hangzhou'
alibaba%
~ ⌚
$ curl -X GET 'http://localhost:10003/bus/env?key=hangzhou'
alibaba%
~ ⌚
$ curl -X GET 'http://localhost:10002/bus/env?key=hangzhou'
xihu%
~ ⌚
$ curl -X GET 'http://localhost:10001/bus/env?key=hangzhou'
xihu%

我们看到,只有 node1 和 node2 修改了配置,其余的 3 个节点配置未改变。node1的改变是因为在 node1 上发送消息,bus也会在node1进行配置修改.

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值