RabbitMQ之Exchange(交换机)属性及备用交换机解读

news2024/11/24 21:03:42

目录

基本介绍

主要结论

备用交换机

 springboot代码实战(备用交换机)

实战架构

工程概述

RabbitConfigDeal 配置类:创建队列及交换机并进行绑定 

MessageService业务类:发送消息及接收消息

主启动类RabbitMq01Application:实现ApplicationRunner接口


基本介绍

在 RabbitMQ 中,交换机主要用来将生产者生产出来的消息,传送到对应的频道中,即交换机是一个消息传送的媒介,其英文被称为 exchange 。交换机在 RabbitMQ 中起着承上启下的作用。

它主要由以下属性可供选择 :

  1. Name:交换机名称;就是一个字符串
  2. Type:交换机类型,direct, topic, fanout, headers四种
  3. Durability:持久化,声明交换机是否持久化,代表交换机在服务器重启后是否还存在;
  4. Auto delete:是否自动删除,曾经有队列绑定到该交换机,后来解绑了,那就会自动删除该交换机;
  5. Internal:内部使用的,如果是yes,客户端无法直接发消息到此交换机,它只能用于交换机与交换机的绑定。
  6. Arguments:只有一个取值alternate-exchange,表示备用交换机;

主要结论

结论1:没发消息之前不会创建交换机和对列

结论2:发消息后,如果交换机不存在,才开始创建交换机,如果队列不存在,则创建新的对列

结论3:创建交换机或者队列完成后再重新创建,如果修改交换机或队列参数则会报错

406错误(inequivalent arg 'durable' for exchange 'exchange.durability' in vhost 'powernode': received 'false' but current is 'true', class-id=40, method-id=10))

结论4:设置持久化为false ,重启rabbitmq-server,则交换机丢失,实验durable参数,看下控制台,然后重启rabbitmq-server

结论5:自动删除为 true ,从控制台上手动解绑,会发现自动删除

备用交换机

备份 交换机可以理解为 RabbitMQ 中交换机的“备胎”,当我们为某一个交换机声明一个对应的备份交换机时, 就是为它创建一个备胎,当交换机接收到一条不可路由消息时,将会把这条消息转发到备份交换机中,由 备份交换机来进行转发和处理,通常备份交换机的类型为 Fanout ,这样就能把所有消息都投递到与其绑 定的队列中,然后我们在备份交换机下绑定一个队列,这样所有那些原交换机无法被路由的消息,就会都 进入这个队列了。到达这个队列以后消费者可以进行处理,通知开发人员进行查看。

当消息经过交换器准备路由给队列的时候,发现没有对应的队列可以投递信息,在rabbitmq中会默认丢弃消息,如果我们想要监测哪些消息被投递到没有对应的队列,我们可以用备用交换机来实现,可以接收备用交换机的消息,然后记录日志或发送报警信息。 

设置参考代码

Map<String, Object> arguments = new HashMap<>();
//指定当前正常的交换机的备用交换机是谁
arguments.put("alternate-exchange", EXCHANGE_ALTERNATE); 
//DirectExchange(String name, boolean durable, boolean autoDelete, Map<String, Object> arguments)
return new DirectExchange(EXCHANGE, true, false, arguments);
//return ExchangeBuilder.directExchange(EXCHANGE).withArguments(args).build();

 springboot代码实战(备用交换机)

实战架构

如上图,消息到达正常的交换机normalExchange后,发现没有对应的路由队列,消息会转发到备用交换机alternateExchange中,备用交换机是一个扇形交换机,随后会转发到alternateQueue队列中去。

工程概述

 工程采用springboot架构,主要用到的依赖为:

<!--        rabbit的依赖-->
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-amqp</artifactId>
        </dependency>

        <dependency>
            <groupId>org.projectlombok</groupId>
            <artifactId>lombok</artifactId>
        </dependency>

application.yml配置文件如下:

server:
  port: 8080
spring:
  rabbitmq:
    host: 123.249.70.148
    port: 5673
    username: admin
    password: 123456
    virtual-host: /

RabbitConfigDeal 配置类:创建队列及交换机并进行绑定 

@Configuration
public class RabbitConfigDeal {


}

创建正常交换机

    @Bean
    public DirectExchange normalExchange() {
        Map<String, Object> arguments = new HashMap<>();
        //设置备用交换机
        arguments.put("alternate-exchange", "alternateExchange");
        return ExchangeBuilder.directExchange("normalExchange")
                .withArguments(arguments)
                .build();
    }

创建备用交换机

    @Bean
    public FanoutExchange alternateExchange() {
        return ExchangeBuilder.fanoutExchange("alternateExchange").build();
    }

 创建备用交换的队列

    @Bean
    public Queue alternateQueue(){
        return QueueBuilder.durable("alternateQueue").build();
    }

 绑定备用交换机和队列

    @Bean
    public Binding bindingAlternateExchange(Queue alternateQueue, FanoutExchange alternateExchange){
        return BindingBuilder.bind(alternateQueue).to(alternateExchange);
    }

MessageService业务类:发送消息及接收消息

@Component
@Slf4j
public class MessageService {
    @Resource
    private RabbitTemplate rabbitTemplate;

}

 发送消息方法

   public void sendMsg(){
        MessageProperties messageProperties = new MessageProperties();
        Message message1 = new Message("hello word ".getBytes(), messageProperties);
        //发送消息
        rabbitTemplate.convertAndSend("alternateExchange", "info", message1);
        log.info("发送完毕:{}" , new Date());

    }

这里用的路由key为info 。

MessageConvert

  • 涉及网络传输的应用序列化不可避免,发送端以某种规则将消息转成 byte 数组进行发送,接收端则以约定的规则进行 byte[] 数组的解析
  • RabbitMQ 的序列化是指 Messagebody 属性,即我们真正需要传输的内容,RabbitMQ 抽象出一个 MessageConvert 接口处理消息的序列化,其实现有 SimpleMessageConverter默认)、Jackson2JsonMessageConverter

  接受消息

    @RabbitListener(queues = {"alternateQueue"})
    public void receiveMsg(Message message){
        byte[] body = message.getBody();
        String queue = message.getMessageProperties().getConsumerQueue();
        String msg=new String(body);
        log.info("{}接收到消息时间:{},消息为{}",queue,new Date(),msg);
    }

 Message

在消息传递的过程中,实际上传递的对象为 org.springframework.amqp.core.Message ,它主要由两部分组成:

  1. MessageProperties // 消息属性

  2. byte[] body // 消息内容

@RabbitListener

使用 @RabbitListener 注解标记方法,当监听到队列 debug 中有消息时则会进行接收并处理

  • 消息处理方法参数是由 MessageConverter 转化,若使用自定义 MessageConverter 则需要在 RabbitListenerContainerFactory 实例中去设置(默认 Spring 使用的实现是 SimpleRabbitListenerContainerFactory)

  • 消息的 content_type 属性表示消息 body 数据以什么数据格式存储,接收消息除了使用 Message 对象接收消息(包含消息属性等信息)之外,还可直接使用对应类型接收消息 body 内容,但若方法参数类型不正确会抛异常:

    • application/octet-stream:二进制字节数组存储,使用 byte[]
    • application/x-java-serialized-object:java 对象序列化格式存储,使用 Object、相应类型(反序列化时类型应该同包同名,否者会抛出找不到类异常)
    • text/plain:文本数据类型存储,使用 String
    • application/json:JSON 格式,使用 Object、相应类型

主启动类RabbitMq01Application:实现ApplicationRunner接口

/**
 * @author 风轻云淡
 */
@SpringBootApplication
public class RabbitMq01Application implements ApplicationRunner {

    public static void main(String[] args) {
        SpringApplication.run(RabbitMq01Application.class, args);
    }

    @Resource
    private MessageService messageService;

    /**
     * 程序一启动就会调用该方法
     * @param args
     * @throws Exception
     */
    @Override
    public void run(ApplicationArguments args) throws Exception {
        messageService.sendMsg();

    }
}

在SpringBoot中,提供了一个接口:ApplicationRunner。 该接口中,只有一个run方法,他执行的时机是:spring容器启动完成之后,就会紧接着执行这个接口实现类的run方法。

由于该方法是在容器启动完成之后,才执行的,所以,这里可以从spring容器中拿到其他已经注入的bean。

启动主启动类后查看控制台:

2023-10-01 11:57:57.660  INFO 83984 --- [           main] 
c.e.rabbitmq01.service.MessageService    : 
发送完毕:Sun Oct 01 11:57:57 CST 2023
2023-10-01 11:57:57.718  INFO 83984 --- [ntContainer#0-1] 
c.e.rabbitmq01.service.MessageService    : 
alternateQueue接收到消息时间:Sun Oct 01 11:57:57 CST 2023,消息为hello word 

我们在这里可以看见与备用交换机绑定的alternateQueue成功接收到了消息

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1090895.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

GO 语言的并发模式你了解多少?

工作中查看项目代码&#xff0c;发现会存在使用 GO 语言做并发的时候出现各种各样的异常情况&#xff0c;有的输出结果和自己期望和设计的不一致&#xff0c;有的是程序直接阻塞住&#xff0c;更有甚者直接是程序 crash 掉。 实际上&#xff0c;出现上述的情况&#xff0c;还是…

spring6-事务

文章目录 1、JdbcTemplate1.1、简介1.2、准备工作1.3、实现CURD①装配 JdbcTemplate②测试增删改功能③查询数据返回对象④查询数据返回list集合⑤查询返回单个的值 2、声明式事务概念2.1、事务基本概念①什么是事务②事务的特性 2.2、编程式事务2.3、声明式事务 3、基于注解的…

NewStarCTF2023week2-ez_sql

闭合之后尝试判断字段数&#xff0c;存在WAF&#xff0c;使用大小写绕过&#xff08;后面的sql语句也需要进行大小写绕过&#xff09; ?id1 Order by 5-- 测出有5列 ?id1 Order by 6-- 查一下数据库名、版本、用户等信息 ?id1Union Select database(),version(),user(),4,…

205、使用消息队列实现 RPC(远程过程调用)模型的 服务器端 和 客户端

目录 ★ RPC模型&#xff08;远程过程调用通信模型&#xff09;▲ 完整过程&#xff1a;代码演示总体流程解释&#xff1a;ConstantUtil 常量工具类ConnectionUtil RabbitMQ连接工具类Server 服务端Client 客户端测试结果服务端客户端 完整代码ConstantUtil 常量工具类Connecti…

CocosCreator 面试题(十一)Cocos Creator 屏幕适配

Cocos Creator 提供了多种屏幕适配的方式&#xff0c;以确保游戏在不同设备上能够正确显示和布局。 以下是 Cocos Creator 中常用的屏幕适配方式及其说明。 1、 Cocos Creator 项目设置中统一配置设计分辨率和屏幕适配 在同一个项目里的多个 Canvas 的设计分辨率仍然采用同一…

2023年中国改性ABS树脂产能、产量及市场规模分析[图]

ABS树脂是由丙烯腈&#xff08;Acrylonitrile&#xff09;、丁二烯&#xff08;Butadiene&#xff09;和苯乙烯&#xff08;Styrene&#xff09;三种单体共聚而成的热塑性聚合物&#xff0c;是介于通用塑料和工程塑料之间的一种高分子材料&#xff0c;是五大合成树脂之一。随着…

USB转串口芯片GP232RL 完全兼容替代FT232RL SSOP28

GP232RL是一款高度集成的USB到UART桥接控制器&#xff0c;提供了一种简单的解决方案&#xff0c;可以使用最少的元器件和PCB空 间&#xff0c;将RS232接口转换为USB接口 。GP232RL包括一个USB 2.0全速功能控制器、USB收发器、振荡器、EEPROM和带有完整的调制解调器控制信号的异…

优雅而高效的JavaScript——扩展运算符

&#x1f617;博主&#xff1a;小猫娃来啦 &#x1f617;文章核心&#xff1a;优雅而高效的JavaScript——扩展运算符 文章目录 什么是扩展运算符扩展运算符的定义扩展运算符的作用 扩展运算符在数组中的应用数组的展开数组的合并数组的复制数组的解构赋值 扩展运算符在对象中的…

IDEA创建项目失败提示 Failed to create directory 或 “项目初始化失败”

基本只有一个原因&#xff0c;IDEA对该文件夹操作没有权限 比如你把项目建在了C盘的User文件夹下&#xff0c;User是系统盘&#xff0c;不要乱在里面搞东西 其他教程也许有可能教你文件夹开放权限的方法 但我个人建议&#xff0c;换个普通的文件夹创建项目即可 或者新建个文件…

【计算机毕业设计】python学生成绩补考通知管理系统

经过分析和研究&#xff0c;基于Web的学生成绩管理系统主要包括学生信息管理模块&#xff0c;学生成绩管理模块&#xff0c;学生班级管理模块&#xff0c;学生课程管理模块和系统管理模块。其中信息管理包括信息的浏览和处理&#xff0c;成绩管理包括成绩查询和处理&#xff0c…

【C语言】结构体+位段+枚举+联合(2)

大家好&#xff0c;我是苏貝&#xff0c;本篇博客带大家了解结构体和位段以及枚举&#xff0c;如果你觉得我写的还不错的话&#xff0c;可以给我一个赞&#x1f44d;吗&#xff0c;感谢❤️ 这是这个系列的第二篇&#xff0c;上一篇详细介绍了结构体的基本知识&#xff0c;详情…

基于SSM的高校疫情管理系统的设计与实现

末尾获取源码 开发语言&#xff1a;Java Java开发工具&#xff1a;JDK1.8 后端框架&#xff1a;SSM 前端&#xff1a;Vue 数据库&#xff1a;MySQL5.7和Navicat管理工具结合 服务器&#xff1a;Tomcat8.5 开发软件&#xff1a;IDEA / Eclipse 是否Maven项目&#xff1a;是 目录…

HTML 核心技术点基础详细解析以及综合小案例

核心技术点 网页组成 排版标签 多媒体标签及属性 综合案例一 - 个人简介 综合案例二 - Vue 简介 02-标签语法 HTML 超文本标记语言——HyperText Markup Language。 超文本&#xff1a;链接 标记&#xff1a;标签&#xff0c;带尖括号的文本 标签结构 标签要成…

python基于协同过滤算法商品商城购物推荐系统vue

随着移动互联网的普及&#xff0c;电子商务的发展也引来了新一轮的发展&#xff0c;越来越手动消费者的喜爱&#xff0c;网络经济的发展对国家经济的发展也带来了很大的利好&#xff0c;带动了很多实体经济的转型&#xff0c;用户可以通过网络可以买到自己称心如意的商品&#…

Windows提权方法论

Windows提权方法论 1.溢出漏洞提权2.计划任务提权3.SAM文件提权4.启动项提权5.不带引号的服务路径提权 1.溢出漏洞提权 溢出提权攻击的基本原理是&#xff0c;通过向目标系统发送过长的输入数据&#xff0c;超出了程序所分配的缓冲区大小&#xff0c;导致溢出。攻击者可以利用…

如何理解BFC、开启BFC、BFC解决哪些问题

1.BFC 概念 BFC 英文名为 Block Formatting Context (块级格式化上下文) 具体可查看 MDN 2.BFC的作用 元素开启BFC后&#xff0c;子元素不会发生margin塌陷问题元素开启BFC后&#xff0c;子元素浮动&#xff0c;元素不发生高度塌陷元素开启BFC后&#xff0c;该元素不被其他元…

2023年中国分子筛稀土催化材料竞争格局及行业市场规模分析[图]

稀土催化材料能够起到提高催化剂热稳定性、催化剂活性、催化剂储氧能力&#xff0c;以及减少贵金属活性组分用量等作用&#xff0c;广泛应用于石油化工、汽车尾气净化、工业废气和人居环境净化、燃料电池等领域。 2015-2023年中国稀土催化材料规模及预测 资料来源&#xff1a;…

基于SSM的失物招领信息交互平台

末尾获取源码 开发语言&#xff1a;Java Java开发工具&#xff1a;JDK1.8 后端框架&#xff1a;SSM 前端&#xff1a;Vue 数据库&#xff1a;MySQL5.7和Navicat管理工具结合 服务器&#xff1a;Tomcat8.5 开发软件&#xff1a;IDEA / Eclipse 是否Maven项目&#xff1a;是 目录…

如何用vscode远程连接Linux服务器

文章目录 一、下载所需插件 二、远程连接 三、更改远程服务器名称 一、下载所需插件 打开商店 下载Remote - SSH 下载Remote - SSH扩展包 二、远程连接 点击远程资源管理器 点击SSH旁边的加号 输入&#xff1a;ssh 用户名服务器地址 介绍 第一个是保存到当前用户第二个是保…

2023年中国印花布产量及发展前景分析:数码印花将成为行业趋势[图]

印花布是用坯布印花纸高温印染加工而成&#xff0c;唐宋时期已很盛行&#xff0c;明清时期达到鼎盛。曾深受人们的喜爱&#xff0c;被作为陪嫁被褥、衣服的必备品。印花布上的图案称作花型&#xff0c;瓦栏、花型创意分享平台。 印花布种类 资料来源&#xff1a;共研产业咨询&…