功能介绍
会话(Session) 是 MQTT 协议中用于维持客户端与服务端之间“状态”的核心机制。通过管理会话状态,MQTT 能够确保在网络断开重连后,业务消息不丢失、订阅关系无需重建,从而保证通信的连续性和可靠性。
本文将详细阐述 MQTT 3.1.1 和 MQTT 5.0 协议中关于会话状态管理的规范、生命周期及最佳实践。
会话状态定义
在 MQTT 协议中,客户端(Client)与服务端(Server)建立连接后,即开启了一个“会话”。会话不仅存在于网络连接存活期间;根据配置,它还可以在网络连接断开后继续保留。一个持久化的会话通常包含以下数据:
订阅
持久会话将保留客户端的订阅信息:客户端再次连接后会恢复上次订阅的 Topic Filter。
消费进度
对于普通订阅:客户端再次连接后会继续上次消费进度,推送系统中最早一条未消费消息。客户端离线状态下产生的消息仍能正常消费。
会话有效期
MQTT 3.1、3.1.1 通过 clean-session 定义 Session 的生命周期。 当 clean-session = true, Session 的生命周期与传输层生命周期一致。 当 clean-session = false, Session 与传输层生命周期无关。为避免资源浪费,产品定义传输层断开后,Session 最大存续 3 天。

按照 MQTT 5.0 协议,有以下等价语义:
MQTT 3.1、3.1.1 | MQTT 5 | |
clean-session = true | clean-start = true | session-expiry-interval = 0 |
clean-session = false | clean-start = false | session-expiry-interval = 259200(会话保留 3 天) |
超过有效期的会话将被回收,客户端下次连接时会按照首次连接进行处理。
使用场景
移动端应用与即时消息
场景描述: 运行在手机上的 App(如智能家居 App、外卖骑手端、即时通讯软件)。这类应用经常因切换后台、网络切换(4G/Wi-Fi)或屏幕熄灭而导致连接中断。用户希望在重新打开 App 时,能够立即收到离线期间错过的通知或消息。
推荐配置:
MQTT 3.1.1:Clean Session = true
MQTT 5.0:Clean Start = false, Session Expiry Interval = [较长值,如 1 天]
核心价值: 漫游不丢信。利用持久会话机制,服务端会自动缓存 App 离线期间的消息。当用户再次打开 App(重连)时,无需重新订阅 Topic,且能瞬间拉取未读消息,提供流畅的用户体验。
OTA 固件升级
场景描述: 服务端向百万台设备批量发送“升级固件”的指令。由于设备数量巨大,部分设备可能正处于断网或升级中的重启状态。
推荐配置:
MQTT 3.1.1:Clean Session = false
MQTT 5.0:Clean Start = false, Session Expiry Interval = [较长值,如 1 天]
核心价值: 异步解耦。运维人员只需发布一次升级指令,无需关心设备当前是否在线。在线的设备立即收到;离线的设备在下次上线(如重启完成或网络恢复)时收到升级指令。这避免了运维人员反复重试发送指令的痛苦。
低功耗设备
场景描述: 电池供电的设备(如水表、燃气表、农业传感器)。为了省电,设备大部分时间处于深度休眠(断网)状态,每天仅唤醒几次上报数据,随后立即断开。
推荐配置:
MQTT 3.1.1:Clean Session = true
MQTT 5.0:Clean Start = true, Session Expiry Interval = 0
核心价值: 节省资源。此类设备主要行为是“单向上传”,通常不需要接收服务端的下行指令。使用非持久会话模式,确保设备断开后不会有无用状态保留。
实时看板等信息发布设备
场景描述: 运维人员通过浏览器访问的 Web Dashboard(仪表盘)或广告屏、点餐终端、POS 机等信息发布设备。
推荐配置:
MQTT 3.1.1:Clean Session = true
MQTT 5.0:Clean Start = true, Session Expiry Interval = 0
核心价值: 即用即走。这些客户端的信息一般具有很强的时效性,并不关心历史消息。并且它们的 Client ID 通常是随机生成的(如 web_client_uuid)。关闭设备后,该 ID 不会再被使用,没有保留会话状态的必要性。