消息队列概述
消息队列是一种进程间通信或同一进程内不同线程的通信方式,用于解决系统间的异步通信和解耦问题
基本概念
- 消息(Message)
- 是消息队列系统中的基本数据单位,包含消息头和消息体
- 消息通常具有持久化属性,确保再系统故障时不会丢失
- 消息头(包含元数据信息)
- 消息ID(唯一标识符)
- 时间戳(创建/发送时间)
- 优先级(处理优先级)
- 过期时间(TTL)
- 路由信息(目的地等)
- 消息体(实际传输的数据内容)
- 文本格式(JSON/XML/纯文本)
- 二进制数据(图片/视频等)
- 队列(Queue)
- 是消息的存储和管理核心
- FIFO特性
- 严格保证先进先出顺序(某些高级队列支持优先级)
- 容量控制
- 可以设置最大消息数和存储大小限制
- 状态管理
- 维护消息的可见状态(待处理/处理中/已完成)
- 死信队列
- 处理失败消息的特殊队列
- 生产者(Producer)
- 发送消息的应用程序
- 主要职责
- 消息构建:创建符合规范的消息结构
- 路由选择:确定消息应发送到那个队列/主题
- 错误处理:处理发送失败的情况(重试/记录等)
- 流量控制:根据消费者能力调节发送速率
- 消费者(Consumer)
- 接收并处理消息的应用程序
- 主要功能
- 消息获取:主动拉取或被动接收消息
- 消息确认:处理成功后发送ACK,失败时NACK
- 并发控制:管理处理线程/协程数量
- 幂等处理:确保重复消息不会导致异常
- 交换机(Exchange)
- 直连交换机(Direct Exchange)
- 工作原理:将消息路由到Binding Key与Routing Key完全匹配的队列
- 使用场景:点对点精确消息传递
- 特点:完全匹配路由键,一个消息通常只路由到一个队列(除非多个队列绑定相同路由键)
- 扇出交换机(Fanout Exchange)
- 工作原理:将消息路由到所有绑定到该交换机的队列,忽略路由键
- 使用场景:广播消息
- 特点:不处理路由键,消息会发送到所有绑定的队列,性能最高
- 主题交换机(Topic Exchange)
- 工作原理:基于通配符匹配规则将消息路由到匹配的队列
- 使用场景:基于模式的消息路由
- 特点:路由键可以使用通配符(*匹配一个单词,#匹配零个或多个单词)
- 头交换机(Headers Exchange)
- 工作原理:基于消息头(Headers)而非路由键进行匹配
- 使用场景:基于消息属性的复杂路由
- 特点:忽略路由键,使用headers属性匹配,可以指定
x-match
为all(所有header必须匹配)或any
(任一header匹配)
- 直连交换机(Direct Exchange)
- 代理(Broker)
- 核心功能
- 消息路由
- 根据规则将消息分发到正确队列
- 持久化存储
- 将消息写入磁盘防止丢失
- 访问控制
- 管理生产者和消费者的权限
- 监控统计
- 收集消息流量和处理指标
- 集群管理
- 再多节点间协调消息分发
核心特性
- 异步通信
- 非阻塞操作
- 生产者发送后立即返回,不等待消费者处理
- 回调机制
- 可选择性设置处理完成的通知回调
- 延迟消息
- 支持定时/延迟投递功能
- 事务支持
- 与业务操作组成分布式事务
- 非阻塞操作
- 解耦
- 接口简化
- 生产者和消费者只需与Broker交互
- 协议中立
- 不同系统可使用不同协议通信
- 独立演进
- 双方可独立升级不影响对方
- 多语言支持
- 不同语言客户端可互通
- 接口简化
- 流量控制
- 缓冲机制
- 吸收突发流量峰值
- 速率限制
- 控制消费者处理速度
- 负载均衡
- 再多消费者间分配消息
- 弹性扩展
- 根据负载动态增减资源
- 缓冲机制
- 可靠性
- 持久化
- 消息写入磁盘存储
- 复制机制
- 多副本防止单点故障
- 确认机制
- 消费者显示确认处理完成
- 重试策略
- 失败消息自动重试
- 死信处理
- 无法处理的消息特殊处理
- 持久化
- 扩展性
- 水平扩展
- 可添加更多Broker节点
- 分区机制
- 大队列分割为多个分区
- 消费者组
- 多消费者并行处理
- 无状态设计
- 方便动态扩容
- 水平扩展
常见消息队列模式
- 点对点
- 工作流程
- 生产者发送消息到指定队列
- 单个消费者从队列获取消息
- 消息处理完成后从队列移除
- 如果有多个消费者,消息会被均衡分配
- 关键特性
- 消息的独占性消费
- 自动负载均衡
- 严格的顺序保证
- 临时队列支持(请求响应模式)
- 工作流程
- 发布/订阅
- 工作流程
- 生产者发布消息到特定主题
- Broker将消息复制到所有订阅者队列
- 每个订阅者独立接收完成消息副本
- 消息持久化根据配置决定
- 关键特性
- 一对多消息分发
- 消费者独立消费进度
- 可选择持久化订阅
- 灵活的路由策略(主题匹配/通配符)
- 变体模式
- 扇出:无条件广播给所有订阅者
- 主题路由:基于主题匹配的智能路由
- 头路由:基于消息头的路由
- 工作流程
安装rabbitMQ
这里为了方便,也是迎合潮流,选择在docker中安装rabbitMQ
- 安装docker
- 详情见我的另一篇文章https://blog.youkuaiyun.com/bugnotfound/article/details/146439513
- 拉取RabbitMQ镜像
- 这里可以选择最新版和指定版本,如果要查看版本可以去官方镜像仓库查看https://hub.docker.com/_/rabbitmq/
- 如果要拉取最新版本直接可以使用
docker pull rabbitmq:latest
- 执行完命令后通过
docker images
命令来查看是否下载成功 - 下面我会以最新版来进行安装(其实是为了偷懒,将版本号换成了latest)
- 启用rabbitMQ容器
docker run -d --name rabbitmq -p 5672:5672 -p 15672:15672 rabbitmq:latest
- 这里使用了docker的端口映射,将容器的5672映射到了物理机的5672端口,将容器的15672映射到了物理机的15672端口
- 其中5672端口是rabbitMQ用于消息接收,15672是用于控制面板
- 使用
docker ps
命令可以查看rabbitMQ是否正常启动
- 开启web管理页面
- 使用
docker exec -it rabbitmq /bin/bash
命令进入到容器 - 使用
rabbitmq-plugins enable rabbitmq_management
开启web管理页面插件
- 使用
- 访问rabbitMQ控制面板
http://主机ip:15672
- 默认的账号和密码都是guest