天天看點

2.1 QoS 服務品質等級

文章目錄

  • ​​什麼是服務品質?​​
  • ​​QoS = 0 – 最多發一次​​
  • ​​QoS = 1 – 最少發一次​​
  • ​​QoS = 2 – 保證收一次​​
  • ​​設定QoS​​
  • ​​服務品質降級​​
  • ​​QoS=1通訊時的注意事項​​
  • ​​QoS=2通訊時的注意事項​​
  • ​​小結​​

什麼是服務品質?

在之前的課程裡我們提到過,一個物聯網系統中有些資訊非常重要,我們需要確定這類重要資訊可以準确無誤的發送和接收,而有些資訊則相對不那麼重要,這類資訊如果在傳輸中丢失不會影響系統的運作。

MQTT服務品質(Quality of Service 縮寫 QoS)正是用于告知物聯網系統,哪些資訊是重要資訊需要準确無誤的傳輸,而哪些資訊不那麼重要,即使丢失也沒有問題。

MQTT協定有三種服務品質級别:

QoS = 0 – 最多發一次

QoS = 1 – 最少發一次

QoS = 2 – 保證收一次

以上三種不同的服務品質級别意味着不同的MQTT傳輸流程。對于較為重要的MQTT消息,我們通常會選擇QoS>0的服務級别(即QoS 為1或2)。

另外這裡提到的“發”與“收”有兩種可能。一種是用戶端釋出消息時,将消息發送給服務端。一種是用戶端訂閱了某一主題消息後,服務端将消息發送給用戶端。是以釋出消息和接收消息的可能是服務端也可能是用戶端。

為了避免為您造成混淆,我們在本節教程後面的描述中将使用“發送端”來描述發送MQTT消息的裝置,而使用“接收端”來描述接收MQTT消息的裝置。

接下來我們仔細看一下這三種服務品質級别的具體含義。

QoS = 0 – 最多發一次

0是服務品質QoS的最低級别。當QoS為0級時,MQTT協定并不保證所有資訊都能得以傳輸。也就是說,QoS=0的情況下,MQTT服務端和用戶端不會對消息傳輸是否成功進行确認和檢查。消息能否成功傳輸全看網絡環境是否穩定。

也就是說,在QoS為0時。發送端一旦發送完消息後,就完成任務了。發送端不會檢查發出的消息能否被正确接收到。

在網絡環境穩定的情況下,資訊傳輸一般是不會出現問題的。但是在環境不穩定的情況下,可能會在傳輸過程中出現MQTT消息丢失的情況。

QoS = 1 – 最少發一次

當QoS級别為1時,發送端在消息發送完成後,會檢查接收端是否已經成功接收到了消息。但是發送端是如何實作這一檢查的呢?請看下圖:

2.1 QoS 服務品質等級

發送端将消息發送給接收端後,會等待接收端的确認。接收端成功接收消息後,會發送一條确認封包PUBACK給發送端。如果發送端收到了這條PUBACK确認封包,那麼它就知道消息已經成功接收。

2.1 QoS 服務品質等級

假如過了一段時間後,發送端沒有收到PUBACK封包,那麼發送端會再次發送消息,然後再次等待接收端的PUBACK确認封包。是以,當QoS=1時,發送端在沒有收到接收端的PUBACK确認封包以前,會重複發送同一條消息。

是以QoS = 1時,每一條消息都至少傳輸一次。

另外請您回憶一下PUBLISH封包的内容。

2.1 QoS 服務品質等級

當發送端重複發送一條消息時,PUBLISH封包中的dupFlag會被設定為True(如上圖黑色橫線所标注的部分)。這是為了告訴接收端,此消息為重複發送的消息。

QoS = 2 – 保證收一次

MQTT服務品質最進階是2級,即QoS = 2。當MQTT服務品質為2級時,MQTT協定可以確定接收端隻接收一次消息。

如下圖所示,QoS=2的收發相對更加複雜。發送端需要接收端進行兩次消息确認。是以,2級MQTT服務品質是最安全的服務級别,也是最慢的服務級别。

下面我們來分步看一下Q0S=2時的消息發送和接收基本流程。

2.1 QoS 服務品質等級
2.1 QoS 服務品質等級

接收端收到QoS為2的消息後,會傳回PUBREC封包作為應答。

2.1 QoS 服務品質等級

發送端收到PUBREC封包後,會把此封包進行存儲,并且傳回PUBREL封包作為應答。

2.1 QoS 服務品質等級

當接收端收到PUBREL封包後,會應答發送端一條PUBCOMP封包。至此,一次QoS2的MQTT消息傳輸就結束了。

以上是QoS=2時的MQTT通訊基本過程。這裡我們隻給您列出了基本流程,而沒有過多的講解MQTT協定是如何控制接收端隻接收一次消息。這麼做是因為本教程的重點是MQTT應用。關于QoS=2的MQTT服務端内部控制機制,我們在實際開發MQTT物聯網的過程中是不會涉及到的。

是以您隻需要牢記一點,那就是QoS=2可以保證接收端隻收一次消息。

設定QoS

了解了QoS的含義後,我們該如何在MQTT通訊中設定QoS呢?下面我們來分别講解用戶端在釋出消息和訂閱消息時如何設定QoS。

釋出消息

如下圖所示,用戶端釋出資訊時,PUBLISH資料包中專有一個資訊為qos。該資訊正是用于設定用戶端釋出MQTT消息的QoS等級。

2.1 QoS 服務品質等級

訂閱消息

同樣的,在用戶端訂閱MQTT主題時,SUBSCRIBE資料包中也同樣有一個資訊用于設定訂閱主題的QoS級别。用戶端正是通過該主題來設定訂閱主題的QoS級别的。

換句話說,無論是釋出(PUBLISH)還是訂閱(SUBSCRIBE),都可以使用資料包中的qos消息設定服務品質級别。

接收端連接配接服務端

另外,要想實作QoS>0的MQTT通訊,用戶端在連接配接服務端時必須要将cleanSession設定為false。如果這一步沒有實作,那麼用戶端是無法實作QoS>0的MQTT通訊。這一點非常關鍵,請您務必要留意。

2.1 QoS 服務品質等級

服務品質降級

講到這裡,不知道有沒有朋友會感到好奇。假如用戶端在釋出和訂閱資訊時使用不同級别的QoS,将會發生什麼情況呢。如下圖所示,假如用戶端A釋出到主題1的消息是采用QoS = 2,然而用戶端B訂閱主題1采用QoS = 1。那麼服務端該如何來應對這一情況呢?

2.1 QoS 服務品質等級

在這種情況下,服務端會使用較低級别來提供服務。如下圖所示,雖然A發送到主題1的消息采用QoS為2,但是服務端發送主題1的消息給B時,采用的QoS為1。這是因為B在訂閱主題1時采用的QoS為1。

2.1 QoS 服務品質等級

下面我們再來看一種情況。

如下圖所示,假如用戶端A釋出主題1消息時使用QoS為0,而用戶端B訂閱主題1消息時使用QoS為1。

2.1 QoS 服務品質等級

在這種情況下,雖然用戶端B訂閱主題1消息時QoS為1,但是由于用戶端A發送主題1消息時QoS為0,是以服務端發送消息給B的QoS為0。

2.1 QoS 服務品質等級

通過以上兩個示例我們可以看到。對于釋出和訂閱消息的用戶端,服務端會主動采用較低級别的QoS來實作消息傳輸。

QoS=1通訊時的注意事項

如想在MQTT通訊中實作服務品質等級為1級(QoS=1),我們要分别對消息的釋出端課接收端進行相應的設定。以下清單中的内容是具體需要采取的措施。

接收端連接配接服務端時cleanSession設定為false

接收端訂閱主題時QoS=1

釋出端釋出消息時QoS=1

QoS=2通訊時的注意事項

小結

  • 若想實作QoS>0,訂閱端連接配接服務端時cleanSession需要設定為false,訂閱端訂閱主題時QoS>0,釋出端釋出消息時的QoS>0。
  • 服務端會選擇釋出消息和訂閱消息中較低的QoS來實作消息傳輸,這也被稱作“服務降級”。
  • QoS = 0, 占用的網絡資源最低,但是接收端可能會出現無法接收消息的情況,是以适用于傳輸重要性較低的資訊。
  • QoS = 1, MQTT會確定接收端能夠接收到消息,但是有可能出現接收端反複接收同一消息的情況。
  • QoS = 2, MQTT會確定接收端隻接收到一次消息。但是QoS為2時消息傳輸最慢,另外消息傳輸需要多次确認,是以所占用的網絡資源也是最多的。此類服務等級适用于重要消息傳輸。
  • 由于QoS1和QoS2都能確定用戶端接收到消息,但是QoS1所占用的資源較QoS2占用資源更小。是以建議使用QoS1來實作網絡資源較為珍貴的環境下傳輸重要資訊。

繼續閱讀