物联网通讯协议之MQTT协议详解(V3.1.1)

一、MQTT协议简介

MQTT(Message Queuing Telemetry Transport,消息队列遥测传输协议),是一种基于发布/订阅(publish/subscribe)模式的"轻量级"通讯协议,该协议构建于TCP/IP协议上,由IBM在1999年发布。MQTT最大优点在于,可以以极少的代码和有限的带宽,为连接远程设备提供实时可靠的消息服务。作为一种低开销、低带宽占用的即时通讯协议,使其在物联网、小型设备、移动应用等方面有较广泛的应用。

MQTT协议通常作为连接云服务器的通道,比如阿里云、京东云等厂商用就将mqtt作为连接其云服务器的底层通信协议。为了保证数据的安全,通常还需要在mqtt上面加上一层安全传输协议(SSL)。

二、MQTT的通信原理

MQTT的主要角色:

  • 客户端(Client)
  • 服务器(Broker)
  • 消息发布者(Publisher)
  • 消息订阅者(subscriber)

MQTT Broker 也称为 MQTT 消息服务器,它可以是运行了 MQTT 消息服务器软件的一台服务器或一个服务器集群。MQTT Broker 负责接收来自客户端的网络连接,并处理客户端的订阅/取消订阅(Subscribe/Unsubscribe)、消息发布(Publish)请求,同时也会将客户端发布的消息转发给其他订阅者。broker在转发消息的同时也可以主动下发消息给订阅了相应主题的订阅者。

MQTT客户端(Client)既可以发布消息,也可以订阅消息,所以MQTT客户端的身份可以是消息发布者(Publisher),也可以是消息订阅者(subscriber)。同一个客户端也可以订阅自己发布的消息。

MQTT的这种通信模型类似于古老的邮局,订阅者和发布者相当于订阅报纸的用户,服务器就相当于邮局,邮局负责将用户订阅的报纸、杂志送到用户手里,用户也可以通过邮局寄送(发布)邮件到其他用户。
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-muW4AvZW-1607504325398)(3E4082888815408BBC6EAD2827B206CD)]

三、MQTT数据帧格式

MQTT数据包结构由三部分组成:

  1. 固定报头
  2. 可变报头
  3. 消息内容
    [外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-DxrZr5D6-1607504325400)(385FC1875FB34F4994530272868E953B)]

3.1、固定报头

每一个MQTT消息都包含固定报头。
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-Rb4DFcbn-1607504325402)(CE508F415249454ABDB2083C13708858)]
MQTT Control Packet type一共4bit,指明了MQTT数据包的类型,其定义如下:

NameValueDirection of flowDescription
Reserved0ForbiddenReserved
CONNECT1Client to ServerClient request to connect to Server
CONNACK2Server to ClientConnect acknowledgment
PUBLISH3Client to Server or Server to ClientPublish message
PUBACK4Client to Server or Server to ClientPublish acknowledgment
PUBREC5Client to Server or Server to ClientPublish received (assured delivery part 1)
PUBREL6Client to Server or Server to ClientPublish release (assured delivery part 2)
PUBCOMP7Client to Server or Server to ClientPublish complete (assured delivery part 3)
SUBSCRIBE8Client to ServerClient subscribe request
SUBACK9Server to ClientSubscribe acknowledgment
UNSUBSCRIBE10Client to ServerUnsubscribe request
UNSUBACK11Server to ClientUnsubscribe acknowledgment
PINGREQ12Client to ServerPING request
PINGRESP13Server to ClientPING response
DISCONNECT14Client to ServerClient is disconnecting
Reserved15ForbiddenReserved

从表格中可以看出,MQTT消息的发布、订阅,以及MQTT连接的建立、心跳的保持都是由客户端主动发起的,服务器端只负责响应这些消息。

3.2、Flags

Bit3-Bit0通常在发布消息(Publish)的过程中使用,表示MQTT的消息质量(Qos)、Dup、Retain特征。

  • DUP = Duplicate delivery of a PUBLISH Control Packet
  • QoS = PUBLISH Quality of Service
  • RETAIN = PUBLISH Retain flag

1. DUP Flag

如果DUP标识被设置为0,标识这是服务端或客户端第一次尝试发送MQTT PUBLISH包。如果DUP标识被设置为1,标识这可能是在重复发送早前尝试发送过的数据包。所有QoS为0的消息DUP标识必须也设置为0。

2. Qos

Qos表示发布消息的质量,0表示来自客户端的消息至最多达一次,1表示消息最少到达一次,2表示消息只到达1次。
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-t5nPIi9S-1607504325405)(CD730AF8188B40BAA05642AE3F86F36A)]

3. Retain

如果客户端Publish数据包中的Retain位设置为1,服务器会将这条消息存储,并在下一次客户端订阅该消息时自动将该topic发送给订阅者。如果Publish数据包的Retain位设置为0,客户端在重新订阅该消息的时候,服务器不会主动发送数据给订阅者。

我们可以使用Mqtt.fx做个测试,首先连接一个免费的broker(broker.hivemq.com),然后向Broker Publish一条主题为TopicA的消息,Qos设置为1,Retain设置为1,点击发布。之后我们断开并重新连接Broker,分别订阅主题TopicA和主题TopicB,这时我们会发现TopicA会接收到我们上次发送的那条消息,而TopicB没有任何消息到达。

四、Clean Session和Will Flag

MQTT客户端在连接服务器的时候(CONNECT)需要指明是否清除回话(Clean Session)和遗嘱消息(Will Flag)。在Connect过程中,这两个字段都位于第8个字节:
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-R1oBHSor-1607504325404)(5BA99A80EC2748C59AE738C198194C89)]

4.1、Clean Sesson

Clean Session为0表示不清除上一次的会话信息,这种情况下服务器会保存上一次和客户端的连接信息。比如当连接重新建立之后,服务器会发送上一次没有收到PUBACK的消息到客户端。

Clean Session为1表示清除上一次的会话信息,每一重新连接都会建立一个新的Session。

客户端会话状态的构成:

  • 已经发送到服务端,但没有收到确认的QoS 1和QoS 2消息
  • 接收到的从服务端QoS 2消息,还没有收到确认的

服务端会话状态的构成:

  • 即使会话状态为空,会话本身也必须存在。
    客户端的订阅。
  • 发送到客户端的但没有得到确认的QoS 1和QoS 2消息。
  • 等待发送到客户端的QoS 1和QoS 2消息。
  • 从客户端收到的QoS 2消息,但还没有确认的。
  • 可选项,等待发送到客户端的QoS 0消息。

4.2、Will Flag

Will Flag表示是否设置遗嘱消息,当客户端和服务器之间因为某些原因正常或者异常断开时,服务器必须发布响应的遗嘱消息到客户端,如果客户端在发送Connect请求时删除了遗嘱消息,则服务器不需要发送遗嘱消息。

遗嘱消息对应的Topic也包含Qos、Retain等字段,Qos的同样表示消息的质量等级,Retain表示服务器在发布遗嘱消息后是否需要保留。

详细内容请参考MQTT协议3.1.2.5章的内容。

举个例子,在客户端 A 进行连接时候,遗嘱消息设定为”offline“,客户端 B 订阅这个遗嘱主题。当 A 异常断开时,客户端 B 会收到这个”offline“的遗嘱消息,从而知道客户端 A 离线了。

五、使用wireshark分析MQTT协议

下图抓取了MQTT的CONNECT、CONNACK、PING、PINGREQ、PINGRESP、PUBLISH、DISCONNECT的过程。
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-zghSsP72-1607504325409)(367C5132B53E479DAA077D236F9B7EA5)]

wireshark是可以直接解析mqtt协议的,我们点击Publish message一栏,可以得到如下信息
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-gS1307JS-1607504325411)(2316810051E543DEB0C8453160517BCA)]

六、MQTT客户端源代码获取

官网地址:http://mqtt.org/

MQTTv3.1.1下载地址:https://os.mbed.com/teams/mqtt/code/MQTTPacket/

  • 4
    点赞
  • 19
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值