PahoMQTT连线中断恢复之后无法收到消息
条目 | 说明 |
---|---|
库名 | paho.mqtt.c |
版本 | 1.3.12 |
github | https://github.com/eclipse/paho.mqtt.c.git |
问题 | 启用cleansession 和automaticReconnect 后,连接中断恢复之后无法收到之前订阅的主题的消息。 |
问题原因
cleansession
和automaticReconnect
被设置为1。
当连线中断恢复之后之前的session状态信息(QoS和订阅topic)被清空。
因此在MQTT客户端没有重新订阅的情况下,无法接收到消息。
解决方案
automaticReconnect和cleansession都不变
调用int MQTTAsync_setConnected (MQTTAsync handle, void *context, MQTTAsync_connected *co)
设置MQTTAsync_connected
回调函数。
在重新建立连接后在typedef void MQTTAsync_connected(void *context, char *cause)
回调函数中重新订阅topic。
automaticReconnect不变
将cleansession
设置为0,可以确保重连之后session状态信息不会被清空,这样之前订阅的topic仍在,可以接收到消息。
cleansession不变
将automaticReconnect
设置0,然后在连线中断之后使用外部线程来重新建立连接,此时会重新订阅,接收消息。
相关资料
根据paho.mqtt.c的文档,MQTTAsync.h
节选:
typedef struct
{
/** The eyecatcher for this structure. must be MQTC. */
...
/**
* This is a boolean value. The cleansession setting controls the behaviour
* of both the client and the server at connection and disconnection time.
* The client and server both maintain session state information. This
* information is used to ensure "at least once" and "exactly once"
* delivery, and "exactly once" receipt of messages. Session state also
* includes subscriptions created by an MQTT client. You can choose to
* maintain or discard state information between sessions.
*
* When cleansession is true, the state information is discarded at
* connect and disconnect. Setting cleansession to false keeps the state
* information. When you connect an MQTT client application with
* MQTTAsync_connect(), the client identifies the connection using the
* client identifier and the address of the server. The server checks
* whether session information for this client
* has been saved from a previous connection to the server. If a previous
* session still exists, and cleansession=true, then the previous session
* information at the client and server is cleared. If cleansession=false,
* the previous session is resumed. If no previous session exists, a new
* session is started.
*/
int cleansession;
/**
* Reconnect automatically in the case of a connection being lost. 0=false, 1=true
*/
int automaticReconnect;
...
} MQTTAsync_connectOptions;
cleansession
cleansession
是一个boolean值,取值范围为0或1。
根据MQTT协议,当建立连接后MQTT客户端和服务器会共同维护一个session状态信息。该设置用于控制MQTT客户端和服务器在连接和断开时关于session的行为。
该session状态信息是为了确保消息按照QoS(至少一次、确定一次、最多一次)指定的方式接收,因此该session状态信息也包含了客户端建立的订阅topic。
当cleansession=1
时,session状态信息在连接或断开时会被丢弃;反之则会保留。
当使用MQTTAsync_connect()
建立连接后,MQTT客户端会使用客户端ID和服务器地址来标识session,而服务器会检查是否有这个MQTT客户端的session信息(之前连接保存的):
- 如果session信息还在并且
cleansession=1
,则MQTT客户端和服务器都会清空之前的session信息; - 如果session信息还在并且
cleansession=0
,则恢复之前的session; - 如果没有该MQTT客户端对应的session信息,则新建session。
automaticReconnect
该参数指定在连线丢失之后是否会自动重连。
该参数取值范围为0或1,0表示不会自动重连,1表示会。
- 原文作者:生如夏花
- 原文链接:https://blduan.top/post/%E5%BC%80%E6%BA%90%E4%B8%89%E6%96%B9/pahomqtt%E8%BF%9E%E7%BA%BF%E4%B8%AD%E6%96%AD%E6%81%A2%E5%A4%8D%E4%B9%8B%E5%90%8E%E6%97%A0%E6%B3%95%E6%94%B6%E5%88%B0%E6%B6%88%E6%81%AF/
- 版权声明:本作品采用知识共享署名-非商业性使用-禁止演绎 4.0 国际许可协议进行许可,非商业转载请注明出处(作者,原文链接),商业转载请联系作者获得授权。