Alan Hou的个人博客

RabbitMQ消息中间件知识汇总

其它主流消息中间件:AcitveMQ(老牌,但性能略差)、Kafka(性能好,可靠性略差)、RocketMQ(收费)

RabbitMQ基于 AMQP 协议实现。适用于对数据一致性、稳定性和可靠性要求很高的场景,对性能和吞吐量的要求次之。

RabbitMQ 整体架构

安装

官网地址:https://www.rabbitmq.com/

Erlang 与 RabbitMQ 对应匹配版本:https://www.rabbitmq.com/which-erlang.html

安装环境:CentOS 7

安装 Erlang

方法一

参考地址:https://github.com/rabbitmq/erlang-rpm

方法二

下载地址:https://www.erlang-solutions.com/resources/download.html

可通过 erl 进入命令行查看

安装 RabbitMQ

以3.6.16为例

注意:如不安装 socat,会报如下错误

配置文件

服务启动/停止

启用插件后在浏览器中访问http://your.ip.addr:15672/,若无法访问请注意检查防火墙相关配置,默认登录用户名/密码: guest/guest

Docker 安装

命令行与管控台

消息生产与消费

ConnectionFactory:获取连接工厂

Connection:获取一个连接

Channel:数据通信信道,可发送和接收消息

Queue:具体的消息存储队列

Producer & Consumer:生产和消费者

示例代码:

注:未指定 exchange 时会使用默认AMQP default,但要求队列名称与routing key 相同(示例中为 test001)

Exchange 交换机

接收消息,并根据路由键转发消息所绑定的队列

Name:交换机名称

Type:交换机类型 direct、topic、fanout、headers

Durability:是否需要持久化,true 为 持久化

Auto delete:当最后一个绑定到 Exchange 上的队列删除后,自动删除该Exchange

Internal:当前 Exchange 是否用于 RabbitMQ 内部使用,默认为 False

Arguments:扩展参数,用于扩展 AMQP 协议自定义使用

主要概念

Binding-绑定:Exchange 和 Exchange、Queue 之间的连接关系

Queue-消息队列:实际存储消息,Durability设置是否持久化

Message-消息:服务器和应用程序之间传送的数据,由 Properties 和  Payload(Body )组成

Virtual Host-虚拟主机:逻辑隔离,最上层的消息路由,一个 VirtualHost 中不能有相同名称的 Exchange 或 Queue

属性设置及获取

消息如何保障100%的投递成功?

生产端的可靠性投递

BAT/TMD 互联网大厂的解决方案

幂等性

幂等性是指执行100次1000次…结果都相同

在海量订单产生的业务高峰期,如何避免消息的重复消费问题?

业界主流幂等性操作:

Confirm 确认消息实现

Return 消息机制

Return Listener 用于处理一些不可路由的消息(channel.addReturnListener),channel.basicPublish中的 mandatory 参数应设为 true,默认值 false 会删除找不到路由的消息

消费端自定义监听

消费端限流

RabbitMQ 提供了一种 qos(服务质量保证)功能

void BaiscQos(uint prefetchSize, ushort prefetchCount, bool global);

死信队列

DLX, Dead-Letter-Exchange,当消息在一个队列中变成死信后,它能被重新 publish 到另一个 Exchange,这个 Exchange就是 DLX

消息变成死信的几种情况:

正常声明交换机、队列、绑定,只需在队列上添加参数 arguments.put(“x-dead-letter-exchange”, “dlx.exchange”);

6种模式汇总(演示代码 Golang)

https://www.rabbitmq.com/getstarted.html

Simple简单模式

最简单常用的模式



生产者调用:

消费者调用:

Work 工作模式

一条消息只能被一个消费者获取

生产者调用:

消费者调用(起多个服务):

Publish/Subscribe 订阅模式

消息被路由投递给多个队列,一个消息被多个消费者获取。



生产者调用:

消费者调用(起多个服务):

Routing路由模式

一个消息被多个消费者获取。并且消息的目标队列可被生产者指定。



生产者调用:

消费者调用(起多个服务):

Topic话题模式

一个消息被多个消费者获取。消息的目标队列可用BindingKey以通配符(#:一个或多个词,*:一个词)的方式指定。



生产者调用:

消费者调用(起多个服务):

RPC模式

 

常见问题

1、ERROR: epmd error for host 10: badarg (unknown POSIX error)

2、{error,{not_a_dets_file,”/var/lib/rabbitmq/mnesia/rabbit@manamana/recovery.dets”}}}

删除/var/lib/rabbitmq/mnesia/rabbit@manamana/recovery.dets文件再重新启动即可

退出移动版