目录

一、持久会话(Persistent Session)
1.为什么需要持久会话?
要从 MQTT 代理接收消息,客⼾端需要连接到代理并订阅其感兴趣的主题。如果客⼾端与代理之间 的连接在⾮持久会话期间中断,这些主题将会丢失,客⼾端需要在重新连接时重新订阅。对于资源 受限的客⼾端来说,每次连接中断后重新订阅都会造成负担。为了避免此问题,客⼾端可以在连接 到代理时请求持久会话。持久会话会将与客⼾端相关的所有信息保存在代理上。客⼾端在与代理建 ⽴连接时提供的 clientId ⽤于标识会话。
2. 概念
持久会话(Persistent Session)用于在客户端断开连接后,保留会话状态和消息队列。 这样,设备重新上线后,可以自动恢复之前的订阅和未接收消息。
3. 关键字段:Clean Session
在 MQTT 3.1.1 协议中,客户端连接报文(CONNECT)中包含:
| 参数 | 类型 | 说明 |
| Clean Session | 布尔值 | 是否在连接时清理会话数据 |
| 值 | 含义 | 会话处理 |
| TRUE | 清除旧会话 | 断开即丢弃订阅与未接收消息 |
| FALSE | 保持持久会话 | 断开后 Broker 继续保存状态 |
在 MQTT 5.0 中,字段改名为
Clean Start,并增加了Session Expiry Interval(会话过期时间)。
4. 持久会话保存内容
当 Clean Session = false 时,Broker 会保存:
| 项目 | 描述 |
| 订阅列表 | 该客户端的所有订阅 Topic |
| 未确认的 QoS1/QoS2 消息 | 待确认或未完成的消息 |
| 离线期间的新消息 | 当客户端离线时仍推送到队列中 |
| 会话状态标识 | 用于客户端重连时恢复上下文 |
5. 持久会话流程图
+-----------+ +-----------+
| Client | | Broker |
+-----------+ +-----------+
| CONNECT (CleanSession=false)
|---------------------------->|
|<----------- CONNACK --------|
断开连接
X
重新连接
| CONNECT (相同 ClientID, CleanSession=false)
|---------------------------->|
|<-- CONNACK (Session Present=1)
| 表示恢复旧会话及离线消息
如何开始或结束持久会话?
-
当客户端连接到代理时,它可以请求持久会话。客户端使用cleanSession 标志来告知代理它需要哪种类型的会话:
-
当清理会话标志设置为 true 时,客⼾端不需要持久会话。如果客⼾端因任何原因断开连接,则 之前持久会话中排队的所有信息和消息都将丢失。
-
当清理会话标志设置为 false 时,代理会为客⼾端创建⼀个持久会话。所有信息和消息都会保留, 直到客⼾端下次请求清理会话为⽌。如果清理会话标志设置为 false,并且代理已为客⼾端提供了可 ⽤的会话,则会使⽤现有会话并将之前排队的消息传递给客⼾端。
客户端如何知道会话是否已经存储?
⾃ MQTT 3.1.1 起,来⾃代理的 CONNACK 消息包含⼀个会话存在标志。该标志告知客⼾端先前建⽴ 的会话在代理上是否仍然可⽤。
6. 应用场景
| 场景 | 说明 |
| IoT 设备掉线恢复 | 智能锁在断网后重新上线时,仍能接收到离线期间的开锁指令 |
| 移动客户端重连 | App 断线重连后能恢复之前的订阅和消息状态 |
| 长连接应用 | 设备不频繁上线下线,适合保持长时会话 |
二、队列消息(Queued Messages)
1. 概念
队列消息是 Broker 在客户端 离线期间缓存的 QoS≥1 消息, 当客户端重新连接时,这些消息会被“补发”。
2. 工作机制
-
客户端连接时
Clean Session=false。 -
客户端订阅了某个 Topic。
-
客户端离线,Broker 收到新的发布消息(QoS1 或 QoS2)。
-
Broker 将消息缓存到该客户端的离线队列。
-
客户端重连时,Broker 自动将消息重新发

最低0.47元/天 解锁文章
2137

被折叠的 条评论
为什么被折叠?



