Mqtt協議規範

轉載:http://blog.itpub.net/28624388/viewspace-1176994/

MQTT(Message Queue Telemetry Transport),遙測傳輸協議,提供訂閱/發佈模式,更爲簡約、輕量,易於使用,針對受限環境(帶寬低、網絡延遲高、網絡通信不穩定),可以簡單概括爲物聯網打造,官方總結特點如下:

1.使用發佈/訂閱消息模式,提供一對多的消息發佈,解除應用程序耦合。
2. 對負載內容屏蔽的消息傳輸。
3. 使用 TCP/IP 提供網絡連接。
4. 有三種消息發佈服務質量:
    “至多一次”,消息發佈完全依賴底層 TCP/IP 網絡。會發生消息丟失或重複。這一級別可用於如下情況,環境傳感器數據,丟失一次讀記錄無所謂,因爲不久後還會有第二次發送。
    “至少一次”,確保消息到達,但消息重複可能會發生。
    “只有一次”,確保消息到達一次。這一級別可用於如下情況,在計費系統中,消息重複或丟失會導致不正確的結果。
5. 小型傳輸,開銷很小(固定長度的頭部是 2 字節),協議交換最小化,以降低網絡流量。
6. 使用 Last Will 和 Testament 特性通知有關各方客戶端異常中斷的機制。 

                                                                                         
消息格式


                                                                                                                                                                                                                             
一:固定頭部
MQTT的消息包含着一個有兩個字節大小的固定頭部
bit76543210
byte 1Message TypeDUP flagQoS levelRETAIN
byte 2Remaining Length
二:消息類型(Message Tpe)

消息類型(4-7),使用4位二進制表示,可代表16種消息類型:

MnemonicEnumerationDescription
Reserved0Reserved----保留待用
CONNECT1Client request to connect to Server----客戶端連接請求
CONNACK2Connect Acknowledgment----連接反饋
PUBLISH3Publish message-----發佈消息
PUBACK4Publish Acknowledgment-----發佈反饋
PUBREC5Publish Received (assured delivery part 1)----發佈消息被接收
PUBREL6Publish Release (assured delivery part 2)
PUBCOMP7Publish Complete (assured delivery part 3)----發佈消息完成
SUBSCRIBE8Client Subscribe request----客戶端訂閱
SUBACK9Subscribe Acknowledgment----訂閱反饋
UNSUBSCRIBE10Client Unsubscribe request----客戶端解除訂閱
UNSUBACK11Unsubscribe Acknowledgment----接觸訂閱反饋
PINGREQ12PING Request-------心跳檢測
PINGRESP13PING Response----心跳反饋
DISCONNECT14Client is Disconnecting----客戶端斷開連接
Reserved15Reserved----保留待用

三:DUP flag(打開標誌)

保證消息可靠傳輸,默認爲0,只佔用一個字節,表示第一次發送。不能用於檢測消息重複發送等。只適用於客戶端或服務器端嘗試重發PUBLISH, PUBREL, SUBSCRIBE 或 UNSUBSCRIBE消息,注意需要滿足以下條件:

 當QoS > 0
 消息需要回復確認 

此時,在可變頭部需要包含消息ID。當值爲1時,表示當前消息先前已經被傳送過。

四:QoS(Quality of Service,服務質量)

使用兩個二進制表示PUBLISH類型消息:

QoS valuebit 2bit 1Description
000至多一次發完即丟棄<=1
101至少一次需要確認回覆>=1
210只有一次需要確認回覆=1
311待用,保留位置

五:RETAIN(保持)

僅針對PUBLISH消息。不同值,不同含義:

1:表示發送的消息需要一直持久保存(不受服務器重啓影響),不但要發送給當前的訂閱者,並且以後新來的訂閱了此Topic name的訂閱者會馬上得到推送。

備註:新來乍到的訂閱者,只會取出最新的一個RETAIN flag = 1的消息推送。

0:僅僅爲當前訂閱者推送此消息。

假如服務器收到一個空消息體(zero-length payload)、RETAIN = 1、已存在Topic name的PUBLISH消息,服務器可以刪除掉對應的已被持久化的PUBLISH消息。


六:QoS level決定的消息流

QoS level爲Quality of Service level的縮寫,翻譯成中文,服務質量等級。

MQTT 3.1協議在"4.1 Quality of Service levels and flows"章節中,僅僅討論了客戶端到服務器的發佈流程,不太完整。因爲決定消息到達率,能夠提升發送質量的,應該是服務器發佈PUBLISH消息到訂閱者這一消息流方向。

QoS level 0

至多發送一次,發送即丟棄。沒有確認消息,也不知道對方是否收到。

ClientMessage and directionServer
QoS = 0PUBLISH 
---------->
Action: Publish message to subscribers then Forget
Reception: <=1

針對的消息不重要,丟失也無所謂。

網絡層面,傳輸壓力小。

QoS level 1

所有QoS level 1都要在可變頭部中附加一個16位的消息ID。

SUBSCRIBE和UNSUBSCRIBE消息使用QoS level 1。

針對消息的發佈,Qos level 1,意味着消息至少被傳輸一次。

發送者若在一段時間內接收不到PUBACK消息,發送者需要打開DUB標記爲1,然後重新發送PUBLISH消息。因此會導致接收方可能會收到兩次PUBLISH消息。針對客戶端發佈消息到服務器的消息流:

ClientMessage and directionServer
QoS = 1
DUP = 0
Message ID = x

Action: Store message

PUBLISH 
---------->
Actions:
  • Store message

  • Publish message to subscribers
  • Delete message

Reception: >=1
Action: Discard messagePUBACK 
<----------
Message ID = x

針對服務器發佈到訂閱者的消息流:

ServerMessage and directionSubscriber
QoS = 1
DUP = 0
Message ID = x
PUBLISH 
---------->
Actions:
  • Store message

  • Make message available                       
Reception: >=1

PUBACK 
<----------
Message ID = x

發佈者(客戶端/服務器)若因種種異常接收不到PUBACK消息,會再次重新發送PUBLISH消息,同時設置DUP標記爲1。接收者以服務器爲例,這可能會導致服務器收到重複消息,按照流程,broker(服務器)發佈消息到訂閱者(會導致訂閱者接收到重複消息),然後發送一條PUBACK確認消息到發佈者。

在業務層面,或許可以彌補MQTT協議的不足之處:重試的消息ID一定要一致接收方一定判斷當前接收的消息ID是否已經接受過

但一樣不能夠完全確保,消息一定到達了。

QoS level 2

僅僅在PUBLISH類型消息中出現,要求在可變頭部中要附加消息ID。

級別高,通信壓力稍大些,但確保了僅僅傳輸接收一次。

先看協議中流程圖,Client -> Server方向,會有一個總體印象:

ClientMessage and directionServer
QoS = 2
DUP = 0
Message ID = x

Action: Store message

PUBLISH 
---------->
Action(a) Store message

or

Actions(b):
  • Store message ID
  • Publish message to subscribers
 PUBREC 
<----------
Message ID = x
Message ID = xPUBREL 
---------->
Actions(a):
  • Publish message to subscribers
  • Delete message

or

Action(b): Delete message ID
Action: Discard messagePUBCOMP 
<----------
Message ID = x

Server -> Subscriber

ServerMessage and directionSubscriber
QoS = 2
DUP = 0
Message ID = x
PUBLISH 
---------->
Action: Store message
 PUBREC 
<----------
Message ID = x
Message ID = xPUBREL 
---------->
Actions:
  • Make message available                       

PUBCOMP 
<----------
Message ID = x

Server端採取的方案a和b,都包含了何時消息有效,何時處理消息。兩個方案二選一,Server端自己決定。但無論死採取哪一種方式,都是在QoS level 2協議範疇下,不受影響。若一方沒有接收到對應的確認消息,會從最近一次需要確認的消息重試,以便整個(QoS level 2)流程打通。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章