一、MQTT协议介绍

1、概览

2、特点

  • 开放消息协议,简单易实现
  • 发布订阅模式,一对多消息发布
  • 基于TCP/IP网络连接
  • 1字节固定报头,2字节心跳报文,报文结构紧凑
  • 消息QoS支持,可靠传输保证

3、应用

  • MQTT协议广泛应用于物联网、移动互联网、智能硬件、车联网、电力能源等领域。
  • 物联网M2M通信,物联网大数据采集
  • Android消息推送,WEB消息推送
  • 移动即时消息,例如Facebook Messenger
  • 智能硬件、智能家具、智能电器
  • 车联网通信,电动车站桩采集
  • 智慧城市、远程医疗、远程教育
  • 电力、石油与能源等行业市场

4、MQTT基于主题(Topic)消息路由

MQTT协议基于主题(Topic)进行消息路由,主题(Topic)类似URL路径,例如:

chat/room/1
sensor/10/temperature
sensor/+/temperature
$SYS/broker/metrics/packets/received
$SYS/broker/metrics/#

主题(Topic)通过'/'分割层级,支持'+', '#'通配符:

'+': 表示通配一个层级,例如a/+,匹配a/x, a/y
'#': 表示通配多个层级,例如a/#,匹配a/x, a/b/c/d

订阅者与发布者之间通过主题路由消息进行通信,例如采用mosquitto命令行发布订阅消息:

mosquitto_sub -t a/b/+ -q 1
mosquitto_pub -t a/b/c -m hello -q 1

订阅者可以订阅含通配符主题,但发布者不允许向含通配符主题发布消息。

5、MQTT V3.1.1协议报文

报文结构

  • 固定报头(Fixed header)
  • 可变报头(Variable header)
  • 报文有效载荷(Payload)

固定报头

+----------+-----+-----+-----+-----+-----+-----+-----+-----+
| Bit      |  7  |  6  |  5  |  4  |  3  |  2  |  1  |  0  |
+----------+-----+-----+-----+-----+-----+-----+-----+-----+
| byte1    |   MQTT Packet type    |         Flags         |
+----------+-----------------------+-----------------------+
| byte2... |   Remaining Length                            |
+----------+-----------------------------------------------+

报文类型

类型名称

类型值

报文说明

CONNECT

1

发起连接

CONNACK

2

连接回执

PUBLISH

3

发布消息

PUBACK

4

发布回执

PUBREC

5

QoS2消息回执

PUBREL

6

QoS2消息释放

PUBCOMP

7

QoS2消息完成

SUBSCRIBE

8

订阅主题

SUBACK

9

订阅回执

UNSUBSCRIBE

10

取消订阅

UNSUBACK

11

取消订阅回执

PINGREQ

12

PING请求

PINGRESP

13

PING响应

DISCONNECT

14

断开连接

PUBLISH发布消息

PUBLISH报文承载客户端与服务器间双向的发布消息。 PUBACK报文用于接收端确认QoS1报文,PUBREC/PUBREL/PUBCOMP报文用于QoS2消息流程。

PINGREQ/PINGRESP心跳

客户端在无报文发送时,按保活周期(KeepAlive)定时向服务端发送PINGREQ心跳报文,服务端响应PINGRESP报文。PINGREQ/PINGRESP报文均2个字节。

MQTT消息QoS

MQTT发布消息QoS保证不是端到端的,是客户端与服务器之间的。订阅者收到MQTT消息的QoS级别,最终取决于发布消息的QoS和主题订阅的QoS。

发布消息的 QoS

主题订阅的 QoS

接收消息的 QoS

0

0

0

0

1

0

0

2

0

1

0

0

1

1

1

1

2

1

2

0

0

2

1

1

2

2

2

QoS 0 - 最多分发一次

当 QoS 为 0 时,消息的分发依赖于底层网络的能力。发布者只会发布一次消息,接收者不会应答消息,发布者也不会储存和重发消息。消息在这个等级下具有最高的传输效率,但可能送达一次也可能根本没送达。

mqtt怎么订阅多个主题 Python mqtt批量订阅_emqx

Qos 1 - 至少分发一次

当 QoS 为 1 时,可以保证消息至少送达一次。MQTT 通过简单的 ACK 机制来保证 QoS 1。发布者会发布消息,并等待接收者的 PUBACK 报文的应答,如果在规定的时间内没有收到 PUBACK 的应答,发布者会将消息的 DUP 置为 1 并重发消息。接收者接收到 QoS 为 1 的消息时应该回应 PUBACK 报文,接收者可能会多次接受同一个消息,无论 DUP 标志如何,接收者都会将收到的消息当作一个新的消息并发送 PUBACK 报文应答。

mqtt怎么订阅多个主题 Python mqtt批量订阅_mqtt_02

QoS 2 - 只分发一次

当 QoS 为 2 时,发布者和订阅者通过两次会话来保证消息只被传递一次,这是最高等级的服务质量,消息丢失和重复都是不可接受的。使用这个服务质量等级会有额外的开销。

发布者发布 QoS 为 2 的消息之后,会将发布的消息储存起来并等待接收者回复 PUBREC 的消息,发送者收到 PUBREC 消息后,它就可以安全丢弃掉之前的发布消息,因为它已经知道接收者成功收到了消息。发布者会保存 PUBREC 消息并应答一个 PUBREL,等待接收者回复 PUBCOMP 消息,当发送者收到 PUBCOMP 消息之后会清空之前所保存的状态。

当接收者接收到一条 QoS 为 2 的 PUBLISH 消息时,他会处理此消息并返回一条 PUBREC 进行应答。当接收者收到 PUBREL 消息之后,它会丢弃掉所有已保存的状态,并回复 PUBCOMP。

无论在传输过程中何时出现丢包,发送端都负责重发上一条消息。不管发送端是 Publisher 还是 Broker,都是如此。因此,接收端也需要对每一条命令消息都进行应答。

mqtt怎么订阅多个主题 Python mqtt批量订阅_mqtt怎么订阅多个主题 Python_03

MQTT会话(Clean Session)

MQTT客户端向服务器发起CONNECT请求时,可以通过'Clean Session'标志设置会话。

'Clean Session'设置为0,表示创建一个持久会话,在客户端断开连接时,会话仍然保持并保存离线消息,直到会话超时注销。

'Clean Session'设置为1,表示创建一个新的临时会话,在客户端断开时,会话自动销毁。

MQTT连接保活心跳

MQTT客户端向服务器发起CONNECT请求时,通过KeepAlive参数设置保活周期。

客户端在无报文发送时,按KeepAlive周期定时发送2字节的PINGREQ心跳报文,服务端收到PINGREQ报文后,回复2字节的PINGRESP报文。

服务端在1.5个心跳周期内,既没有收到客户端发布订阅报文,也没有收到PINGREQ心跳报文时,主动心跳超时断开客户端TCP连接。

emqx 消息服务器默认按最长 2.5 心跳周期超时设计。

MQTT遗愿消息(Last Will)

MQTT客户端向服务器端CONNECT请求时,可以设置是否发送遗愿消息(Will Message)标志,和遗愿消息主题(Topic)与内容(Payload)。

MQTT客户端异常下线时(客户端断开前未向服务器发送DISCONNECT消息),MQTT消息服务器会发布遗愿消息。

MQTT保留消息(Retained Message)

MQTT客户端向服务器发布(PUBLISH)消息时,可以设置保留消息(Retained Message)标志。保留消息(Retained Message)会驻留在消息服务器,后来的订阅者订阅主题时仍可以接收该消息。

例如mosquitto命令行发布一条保留消息到主题'a/b/c':

mosquitto_pub -r -q 1 -t a/b/c -m 'hello'

之后连接上来的MQTT客户端订阅主题'a/b/c'时候,仍可收到该消息:

$ mosquitto_sub -t a/b/c -q 1
hello

保留消息(Retained Message)有两种清除方式:

  1. 客户端向有保留消息的主题发布一个空消息:
mosquitto_pub -r -q 1 -t a/b/c -m ''

 参看:协议介绍 | EMQX 4.3 文档

二、基于EMQX 搭建 MQTT服务端步骤:

机器 127.0.0.1   系统版本:Centos 6.7    CPU架构:amd64

cd /usr/local/mqtt
wget https://www.emqx.com/zh/downloads/broker/4.3.8/emqx-centos6-4.3.8-amd64.zip
unzip emqx-centos6-4.3.8-amd64.zip
cd emqx
./bin/emqx start
EMQ X Broker 4.3.8 is started successfully!

以上就成功启动EMQ X Broker。

查看状态

[root@10 emqx]# ./bin/emqx_ctl status
Node 'emqx@127.0.0.1' 4.3.8 is started

停止Broker

./bin/emqx stop

三、MQTT客户端

MQTT X:跨平台 MQTT 5.0 桌面客户端工具

MQTTX/README-CN.md at main · emqx/MQTTX · GitHub

四、MQTT管理界面

http://127.0.0.1:18083/#/    admin   public