內容簡介:之前我們寫了一篇ESP8266AT指令的說明文檔,在客戶端連接上伺服器之後,接下來便是網路通信。為此我們又寫了這一片MQTT協議的說明文檔,更加深層次的講述了通信的原理。此文檔只是我們在調試過程中的一些小結和經驗,所以並不是規範的設計手冊。如果想要使用瞭解MQTT協議,一定是要仔細看到他的 ...
內容簡介:之前我們寫了一篇ESP8266AT指令的說明文檔,在客戶端連接上伺服器之後,接下來便是網路通信。為此我們又寫了這一片MQTT協議的說明文檔,更加深層次的講述了通信的原理。此文檔只是我們在調試過程中的一些小結和經驗,所以並不是規範的設計手冊。如果想要使用瞭解MQTT協議,一定是要仔細看到他的手冊的。如果發現文中有寫錯的地方也希望指出,我們會改正,並且在我們的公眾號“眼湖雲”中更新。
圖片沒法貼上來,所以需要結合手冊來看。
我們的網路通信通過三部分,網關(ESP8266),MQTT協議,伺服器。
在通過ESP8266連接上伺服器之後,下麵就要通過MQTT進行通信。MQTT協議最新的版本是MQTT-3.1.1-CN,這個可以上網去下載,不過我們建議將MQTT-3.1protocol-Specific中文版也下載下來,兩份一起看,比較詳細。還有MQTT的源碼,網上也有的下載。
簡單點來說,MQTT協議就是將你要發送的內容按照它的規定組成一串字元串,然後發送出去,至於伺服器接收到了怎麼解析就不是我們玩嵌入式的人管的了。
MQTT協議一共有14個消息類型:
1.客戶端請求連接到伺服器; 2.連接確認; 3.發佈消息;4.發佈確認;5.發佈信息收到;6.發佈信息分發;7.發佈完成 ;8.客戶端訂閱請求;9.訂閱確認;10.客戶端取消訂閱請求;
11.取消訂閱確認;12.ping請求;13.ping響應;14.客戶端正在斷開連接;
而他們的發送格式都是一樣的,一共有三部分組成:
固定報頭,可變報頭,有效載體
具體的每一種的意思可以查看手冊,我們這裡只用到其中的三種,分別是1,3,8。接下來我們講講這三種消息類型。
一、客戶端請求連接伺服器。
客戶端連接到伺服器之後,客戶端發送給伺服器的第一個報文(第一個字元串,也就是消息類型)必須是第一個消息類型,也就是上面列出來的第一個消息類型,客戶端請求連接到伺服器(connect)。
那麼我們該送什麼樣的字元串呢,其實手冊上已經列了出來怎麼發送,它的格式都是定死的。
我們給出一個字元串,也就是經過MQTT協議後將要發出去的字元串:
0x10 0x2d 0x00 0x04 ‘M’ ‘Q’ ‘T’ ‘T’ 0x04 0xc2 0x0b 0xb8 0x00 0x10
‘4’ ‘0’ ‘F’ ‘’0 ‘6’ ‘0’ ‘0’ ‘0’ ‘5’ ‘0’ ‘8’ ‘0’ ‘4’ ‘0’ ‘5’ ‘0’ 0X00 0X05
‘a’ ‘d’ ‘m’ ‘i’ ‘n’ 0x00 0x08 ‘p’ ‘a’ ‘s’ ‘s’ ‘w’ ‘o’ ‘r’ ‘d’
一共是47個字元。
1.開頭的兩個字元。0x10 0x2d 這兩個位元組就是固定報頭。固定報頭只有兩個位元組,每個位元組八位。每一位都有它代表的意思。
0x10 (0001 0000): 低四位是保留位,預設都是0。
高四位則是代表這個字元串是第一種消息類型,括弧里的1就是它的號碼代,手冊里有詳細的表格。
0x2d (0010 1011): 這個位元組是剩餘長度,也就是這個位元組之後,多有位元組的個數(可變報 頭+有效載體),我們這裡一共47個字元,減去這兩個,就是45個,十 六進位就是0x2d
2.接下來是可變報頭,可變報頭由四個部分組成:協議名,協議級別,連接標誌和保持連接
協議名有六個位元組,也就是接下來的0x00 0x04 ‘M’ ‘Q’ ‘T’ ‘T’
0x00 0x04 這是一組,代表後面的協議名的長度,我們這裡協議名便是MQTT,長度4
協議級別一個位元組 0x04 。這個在手冊中給出了這個固定的數據,也就是這個協議的版本的代表。
連接標誌一個位元組:0xc2 (1100 0010)
每一位的意思手冊上有。
Clean Session:伺服器在斷開連接後,是不是要保存客戶端的信息,我們保存,設為0。
也就是如果我們的ESP8266在發消息時突然斷開了,接著又連了上來,那麼服 務器接著斷開時的狀態接續發送。
Willflag:這裡我們不用這一位,這一位不設置,後面的will QOS 和 will retain都不用設置。
Username 和 password 就是進入你的伺服器的賬號和密碼了。我們這裡用到了,所以這兩位都是1.
最後是保持連接,兩個位元組,0x0b 0xb8。 這個講起來比較多,我們這裡簡單解釋一下,詳細的需要自己看手冊,專門有講解。保持連接也就是心跳,即多長時間檢查一下是否還發消息和是否保持著連接,我們這兩個位元組就是設置的這個時間。
3.接下來就是有效載體,包括客戶端標識符,遺囑主題,遺囑消息,用戶名,密碼
客戶端標識符:0x00 0x10 40F0600050804050 前面兩個位元組就是代表標識符的長度,後面的40F......就是客戶端標識符,代表著哪一個客戶端,這個自己根據自己的設計來決定。
遺囑主題,遺囑消息我們都沒有。
接下來的就是用戶名和密碼。
0X00 0X05 admin 0x00 0x08 password
這個的意思不講也應該知道了,不再說了。
二、第一步的connect完成後,就是請求連接成功了。
接下來就是發佈消息和接收消息,這兩個不再詳細展開,他們的格式都是和上面的第一步一樣的,設置值根據手冊中的數據設置就可以。
簡單解釋一下,客戶端向伺服器傳消息,就是publish,發佈消息,那麼按照發佈消息的消息格式發送就可以。
客戶端想要接收伺服器的消息,就是接收消息了,這個需要在連接成功後就發送給伺服器。意思就是:我們使用的微信,上面有很多的公眾號。但是你怎麼樣才能受到這些公眾號的消息呢,你得先關註這些公眾號。同理,這裡的伺服器有很多的消息,你想要接收那部分的,就需要向伺服器發送那部分消息的公眾號才可以接收。