消息总线

Posted dalaoyang

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了消息总线相关的知识,希望对你有一定的参考价值。

SpringCloudBus:事件、消息总线,用于在集群(例如,配置变化事件)中传播状态变化,可与Spring Cloud Config联合实现热部署。

在上一篇写出了springcloud对微服务的集中配置,那么就出现了一个问题,如果修改配置了怎么实现不需重启服务来实现配置的更新,下面有集中解决方法。

1.使用/refresh手动刷新配置

缺点:单点刷新,如果集群服务多的话,无论是工作量还是维护上都十分麻烦。

使用上一篇的config-client服务,加入依赖,

 
   
   
 
  1. spring-boot-starter-actuator

pom文件如下:

 
   
   
 
  1. <?xml version="1.0" encoding="UTF-8"?>

  2. <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"

  3.    xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">

  4.    <modelVersion>4.0.0</modelVersion>

  5.    <groupId>com.dalaoyang</groupId>

  6.    <artifactId>springcloud_config_client</artifactId>

  7.    <version>0.0.1-SNAPSHOT</version>

  8.    <packaging>jar</packaging>

  9.    <name>springcloud_config_client</name>

  10.    <description>springcloud_config_client</description>

  11.    <parent>

  12.        <groupId>org.springframework.boot</groupId>

  13.        <artifactId>spring-boot-starter-parent</artifactId>

  14.        <version>1.5.9.RELEASE</version>

  15.        <relativePath/> <!-- lookup parent from repository -->

  16.    </parent>

  17.    <properties>

  18.        <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>

  19.        <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>

  20.        <java.version>1.8</java.version>

  21.        <spring-cloud.version>Edgware.SR1</spring-cloud.version>

  22.    </properties>

  23.    <dependencies>

  24.        <dependency>

  25.            <groupId>org.springframework.cloud</groupId>

  26.            <artifactId>spring-cloud-starter-eureka</artifactId>

  27.        </dependency>

  28.        <dependency>

  29.            <groupId>org.springframework.boot</groupId>

  30.            <artifactId>spring-boot-starter-test</artifactId>

  31.            <scope>test</scope>

  32.        </dependency>

  33.        <dependency>

  34.            <groupId>org.springframework.cloud</groupId>

  35.            <artifactId>spring-cloud-starter-config</artifactId>

  36.        </dependency>

  37.        <dependency>

  38.            <groupId>org.springframework.boot</groupId>

  39.            <artifactId>spring-boot-starter-actuator</artifactId>

  40.        </dependency>

  41.    </dependencies>

  42.    <dependencyManagement>

  43.        <dependencies>

  44.            <dependency>

  45.                <groupId>org.springframework.cloud</groupId>

  46.                <artifactId>spring-cloud-dependencies</artifactId>

  47.                <version>${spring-cloud.version}</version>

  48.                <type>pom</type>

  49.                <scope>import</scope>

  50.            </dependency>

  51.        </dependencies>

  52.    </dependencyManagement>

  53.    <build>

  54.        <plugins>

  55.            <plugin>

  56.                <groupId>org.springframework.boot</groupId>

  57.                <artifactId>spring-boot-maven-plugin</artifactId>

  58.            </plugin>

  59.        </plugins>

  60.    </build>

  61. </project>

在Controller类上加入@RefreshScope注解,由于上一篇controller写在了启动类上,所以直接加在启动类上,代码如下:

 
   
   
 
  1. package com.dalaoyang;

  2. import org.springframework.beans.factory.annotation.Value;

  3. import org.springframework.boot.SpringApplication;

  4. import org.springframework.boot.autoconfigure.SpringBootApplication;

  5. import org.springframework.cloud.context.config.annotation.RefreshScope;

  6. import org.springframework.web.bind.annotation.RequestMapping;

  7. import org.springframework.web.bind.annotation.RestController;

  8. @SpringBootApplication

  9. @RestController

  10. @RefreshScope

  11. public class SpringcloudConfigClientApplication {

  12.    public static void main(String[] args) {

  13.        SpringApplication.run(SpringcloudConfigClientApplication.class, args);

  14.    }

  15.    @Value("${title}")

  16.    String title;

  17.    @RequestMapping("/getTitle")

  18.    public String getTitle(){

  19.        return title;

  20.    }

  21. }

配置文件新增配置management.security.enabled=false,在刷新时关闭安全验证。

代码如下:

 
   
   
 
  1. spring.application.name=config-client

  2. spring.cloud.config.label=master

  3. spring.cloud.config.profile=test

  4. spring.cloud.config.uri= http://localhost:9000/

  5. eureka.client.service-url.defaultZone=http://eureka.dalaoyang.cn/eureka/

  6. ## 刷新时,关闭安全验证

  7. management.security.enabled=false

分别启动项目config-server,config-client。访问http://localhost:8080/getTitle,结果如下图

修改git上配置,修改为dalaoyangtestchange,在次请求,结果没有改变,使用postman或者其他工具post请求http://localhost:8080/getTitle看到返回如下结果。

消息总线

在次访问http://localhost:8080/getTitle,如下图

消息总线

2.使用springcloudbus刷新配置

springcloudbus需要使用轻量消息代理,本文使用rabbitmq,启动rabbitmq如下图:

消息总线

访问http://localhost:15672/#/如下图

消息总线

新建项目springcloud_bus,同时改造config-client,pom文件加入bus依赖,代码如下:

 
   
   
 
  1. <?xml version="1.0" encoding="UTF-8"?>

  2. <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"

  3.    xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">

  4.    <modelVersion>4.0.0</modelVersion>

  5.    <groupId>com.dalaoyang</groupId>

  6.    <artifactId>springcloud_bus</artifactId>

  7.    <version>0.0.1-SNAPSHOT</version>

  8.    <packaging>jar</packaging>

  9.    <name>springcloud_bus</name>

  10.    <description>springcloud_bus</description>

  11.    <parent>

  12.        <groupId>org.springframework.boot</groupId>

  13.        <artifactId>spring-boot-starter-parent</artifactId>

  14.        <version>1.5.9.RELEASE</version>

  15.        <relativePath/> <!-- lookup parent from repository -->

  16.    </parent>

  17.    <properties>

  18.        <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>

  19.        <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>

  20.        <java.version>1.8</java.version>

  21.        <spring-cloud.version>Edgware.SR1</spring-cloud.version>

  22.    </properties>

  23.    <dependencies>

  24.        <dependency>

  25.            <groupId>org.springframework.cloud</groupId>

  26.            <artifactId>spring-cloud-starter-eureka</artifactId>

  27.        </dependency>

  28.        <dependency>

  29.            <groupId>org.springframework.boot</groupId>

  30.            <artifactId>spring-boot-starter-test</artifactId>

  31.            <scope>test</scope>

  32.        </dependency>

  33.        <dependency>

  34.            <groupId>org.springframework.cloud</groupId>

  35.            <artifactId>spring-cloud-starter-config</artifactId>

  36.        </dependency>

  37.        <dependency>

  38.            <groupId>org.springframework.boot</groupId>

  39.            <artifactId>spring-boot-starter-actuator</artifactId>

  40.        </dependency>

  41.        <dependency>

  42.            <groupId>org.springframework.cloud</groupId>

  43.            <artifactId>spring-cloud-starter-bus-amqp</artifactId>

  44.        </dependency>

  45.    </dependencies>

  46.    <dependencyManagement>

  47.        <dependencies>

  48.            <dependency>

  49.                <groupId>org.springframework.cloud</groupId>

  50.                <artifactId>spring-cloud-dependencies</artifactId>

  51.                <version>${spring-cloud.version}</version>

  52.                <type>pom</type>

  53.                <scope>import</scope>

  54.            </dependency>

  55.        </dependencies>

  56.    </dependencyManagement>

  57.    <build>

  58.        <plugins>

  59.            <plugin>

  60.                <groupId>org.springframework.boot</groupId>

  61.                <artifactId>spring-boot-maven-plugin</artifactId>

  62.            </plugin>

  63.        </plugins>

  64.    </build>

  65. </project>

加入rabbitmq配置,配置文件如下:

 
   
   
 
  1. spring.rabbitmq.host=localhost

  2. spring.rabbitmq.port=5672

  3. spring.rabbitmq.username=guest

  4. spring.rabbitmq.password=guest

  5. ##端口号

  6. server.port=8881

  7. ## 刷新时,关闭安全验证

  8. management.security.enabled=false

  9. spring.application.name=config-client

  10. spring.cloud.config.label=master

  11. spring.cloud.config.profile=test

  12. spring.cloud.config.uri= http://localhost:9000/

  13. eureka.client.service-url.defaultZone=http://eureka.dalaoyang.cn/eureka/

启动类加入注解@RefreshScope,代码如下:

 
   
   
 
  1. package com.dalaoyang;

  2. import org.springframework.beans.factory.annotation.Value;

  3. import org.springframework.boot.SpringApplication;

  4. import org.springframework.boot.autoconfigure.SpringBootApplication;

  5. import org.springframework.cloud.context.config.annotation.RefreshScope;

  6. import org.springframework.web.bind.annotation.RequestMapping;

  7. import org.springframework.web.bind.annotation.RestController;

  8. @SpringBootApplication

  9. @RestController

  10. @RefreshScope

  11. public class SpringcloudBusApplication {

  12.    public static void main(String[] args) {

  13.        SpringApplication.run(SpringcloudBusApplication.class, args);

  14.    }

  15.    @Value("${title}")

  16.    String title;

  17.    @RequestMapping("/getTitle")

  18.    public String getTitle(){

  19.        return title;

  20.    }

  21. }

config-client加入同样依赖和配置,重启config-client,启动springcloud_bus,先去http://eureka.dalaoyang.cn/,可以看到

消息总线

先将git上配置改回dalaoyang_test,分别请求http://localhost:8881/getTitle和http://localhost:8080/getTitle结果如下:

消息总线

消息总线

然后用postman使用post请求访问http://localhost:8881/bus/refresh

再次分别请求http://localhost:8881/getTitle和http://localhost:8080/getTitle结果如下:

从图中可以看出刷新配置成功。

3.局部刷新配置,配置与第2种方法一样,只是在使用postman刷新时略加改变,在本文中使用http://localhost:8881/bus/refresh?destination=config-client:8881可以刷新服务名为config-client端口为8881的服务,如果想要刷新服务名为config-client的所有服务可以写成http://localhost:8881/bus/refresh?destination=config-client:**

源码下载 :大老杨码云

个人网站:https://www.dalaoyang.cn


以上是关于消息总线的主要内容,如果未能解决你的问题,请参考以下文章

linux 进程间通信 dbus-glib实例详解二(上) 消息和消息总线(附代码)

linux 进程间通信 dbus-glib实例详解二(下) 消息和消息总线(ListActivatableNames和服务器的自动启动)(附代码)

从 SQL 向 Azure 服务总线队列添加消息

我最喜欢的进程之间通信方式-消息总线

我最喜欢的进程之间通信方式-消息总线

使用 Durable Functions 推送到服务总线的消息计数不可靠