前言
MQTT 是 IBM 於 1998 年設計和開發的工作在 TCP/IP 協議簇上是基於 TCP 協議的應用層協議。MQTT 采用輕量級的發布/訂閱范式進行消息傳輸,旨在為低帶寬和不穩定的網絡環境中的物聯網設備提供可靠的網絡服務,設備需要連結在消息中間件 (MQTT Broker)上進行消息通信。
眾多物聯網協議中,MQTT 以其開放、輕量、節能、通用等特點,被越來越多的企業所接受,已經成為物聯網通信協議的事實標准。但由於所在行業特殊性或其他種種原因,在物聯網行業中有大量同樣基於 TCP/IP 的通信協議:有形成規模的標准的行業協議如電力、道路交通、工控協議,也有公司、項目甚至是個人開發的私有協議。無論新舊項目都有可能遇到無法使用 MQTT 協議的困境。
物聯網傳統私有 TCP 協議存在的問題
TCP 協議通信涉及網絡編程,客戶端與服務端軟件都需要應對和處理復雜的網絡環境、業務邏輯和組件架構問題,實際開發中每個組件都需要在均衡性能和穩定性的同時兼顧安全性易用性,為開發帶來了很大難度。
加之私有 TCP 協議由於較為小眾或者具備較強的行業專一性導致用戶較少,往往缺乏一個優秀的客戶端和服務端軟件,隨着業務的發展設備數量增多通信流量超出預期和功能需求增改,整個業務中潛在的問題將會被放大:
- 服務端單機性能較差,水平擴展難度較大,服務能力限制了業務增長;
 - 在服務端/客戶端增改功能難度較大,限制了應用層功能需求發展;
 - 缺少可靠的運維體系,運維管理存在不准確、不及時的問題。
 
EMQ X 作為一款優秀的開源 MQTT Broker,在支持高性能、大規模標准 MQTT 協議百萬設備接入、支持集群水平拓展的基礎上,拓展了私有 TCP 協議接入並集成大量開箱即用的功能:多種方式的認證鑒權、發布訂閱 ACL 控制,規則引擎消息處理、消息存儲與橋接,完備的監控運維系統、外部 REST API 控制調用等。
在高性能、高拓展性的基礎上,EMQ X 打通了上層應用程序對設備連接/通信整個生命周期控制和數據交互通道,使得用戶可以快速完成物聯網應用開發。
目前 EMQ X 通過服務端適配/設備側適配的方式,提供完整的私有 TCP 接入方案:
- 服務端適配:針對既有私有 TCP 協議,在不改動舊網設備的情況下調整服務器功能增加對的適配插件,適配后設備可以無縫遷移連接到 EMQ X;
 - 設備側適配:針對新設備,根據 EMQ 提供的 EMQ 私有 TCP 協議規范 和接入 SDK 在設備側開發調整,適配后設備可以無縫遷移連接至 EMQ X。
 
私有 TCP 協議設備接入示例
EMQ X TCP 私有協議接入的連接在應用層抹平了與 MQTT 連接的差異,以 emqx-tcp 插件為例,部分配置項如下:
## 上行主題。上行消息到 EMQ 系統中的消息主題
##
## 占位符:
##   - %c: 接入客戶端的 ClientId
##   - %u: 接入客戶端的 Username
tcp.proto.up_topic = tcp/%c/up
## 下行主題。客戶端接入成功后, emqx-tcp 會訂閱
## 該主題,以接收 EMQ 系統向該類型的客戶端下
## 發的消息。
##
## 占位符:(同上)
tcp.proto.dn_topic = tcp/%c/dn
 
        從配置項中我們可以看出私有 TCP 協議接入的通信模式:
- 客戶端的上行消息將發布到 
tcp/%c/up主題,EMQ X 中其他客戶端包括應用程序訂閱該主題即可接收到私有 TCP 協議設備信息; - 通過 EMQ X 內置的 REST API 或任意客戶端向 
tcp/%c/dn發布消息即可送達該客戶端。 
由此我們與建立了私有 TCP 協議客戶端建立了雙向通信,同時客戶端接入前可以使用 EMQ X 內置的認證鑒權組件進行認證,消息抵達的時候亦可使用發布訂閱 ACL 組件進行訪問控制。整個環節中,規則引擎、消息橋接、持久化組件配置相關規則后也可以處理該部分數據。
服務端適配
EMQ 為客戶提供的私有化付費開發定制服務中包括私有 TCP 協議接入適配項目。
服務端適配針對既有私有 TCP 協議,在不改動舊網設備的情況下調整服務器功能,適配后設備可以無縫遷移連接到 EMQ X。EMQ X 系統分層中連接層負責處理服務端 Socket 連接與 MQTT 協議編解碼,其功能如下:
- 基於 eSockd 框架的異步 TCP 服務端
 - TCP Acceptor 池與異步 TCP Accept
 - TCP/SSL, WebSocket/SSL 連接支持
 - 最大並發連接數限制
 - 基於 IP 地址(CIDR)訪問控制
 - 基於 Leaky Bucket 的流控
 - MQTT 協議編解碼
 - MQTT 協議心跳檢測
 - MQTT 協議報文處理
 

圖 1 EMQ X 功能架構圖 圖中紅框部分即為私有 TCP/UDP 協議層
在當下架構設計中,要適配特定的私有 TCP 協議,僅需在連接層拓展相應的協議編解碼和報文處理功能。用戶以插件的形式擴展 EMQ X 協議適配器后,即可讓私有協議 TCP 設備無需經過網關/代理服務器直接接入 EMQ X,讓項目開發使用充分享受 EMQ X 帶來的便利。
設備側適配:EMQ 私有 TCP 協議規范
設備側適配針對新設備,根據 EMQ 提供的 EMQ 私有 TCP 協議規范 和接入 SDK 在設備側開發調整,適配后設備可以無縫遷移連接至 EMQ X。
經過多個成熟項目的私有 TCP 協議開發定制經驗上,EMQ 推出一個通用的、基於 TCP 私有協議的接入規范 EMQ 私有 TCP 協議規范,相較於 MQTT 協議更加輕量,為私有 TCP 接入提供了完整的解決方案。
EMQ X TCP 包含一個私有 TCP 協議標准和對應的接入插件 emqx-tcp,整個規范設計原則如下:
- 輕量: 盡量減少頭部、控制字段的字節大小;
 - 簡潔: 私有 TCP 協議,主要功能定位在透傳上層應用/協議的數據報文。所以功能應當簡潔,專注透明傳輸即可;
 - 可靠: 保證消息有序可達。
 
規范中的 emqx-tcp 作為一個靠近端側的一個接入模塊,按照其功能邏輯和整個系統的關系,將整個消息交換的過程可以分成三個部分:終端側,平台側和其它側:
|<-- Terminal -->|<--------- Broker Side --------->|<---  Others  --->|
|<-    Side    ->|                                 |<--    Side    -->|
+---+                                                PUB  +-----------+
| D |  INCOMING  +----------+    PUB     +---------+   -->| subscriber|
| E |----------->|          |----------->|         |--/   +-----------+
| V |            | emqx-tcp |            |  EMQ X  |
| I |<-----------|          |<-----------|         |<--   +-----------+
| C |  OUTGOING  +----------+    PUB     +---------+   \--| publisher |
| E |                                                PUB  +-----------+
+---+
 
        - 終端側,通過 EMQ X TCP 定義的 TCP 私有協議進行接入,然后實現數據的上報,或者接收下行的消息。
 - 平台側,主體是 emqx-tcp 接入插件和 EMQ X 系統。emqx-tcp 負責報文的編解碼,代理訂閱下行主題。實現將上行消息轉為 EMQ X 系統中的 MQTT 消息 PUBLISH 到整個系統中;將下行的 MQTT 消息轉化為 TCP 私有協議的報文結構,下發到終端。
 - 其它側,可以對 2 中出現的上行的 PUBLISH 消息的主題進行訂閱,以接收上行消息。或對發布消息到具體的下行的主題,以發送數據到終端側。
 
兩種適配方式的比較
目前 EMQ X TCP 協議規范及 emqx-tcp 插件是隨 **EMQ X Enterprise ** 分發的,EMQ X 企業版用戶可以自由使用該部分功能,依據 EMQ 私有 TCP 協議規范 進行設備側的驅動、通信開發,從設備側適配私有 TCP 協議接入。
但實際物聯網項目中設備側的協議多種多樣,舊項目或行業相關的項目使用有其他私有 TCP 協議規范的時候 emqx-tcp 插件並不能直接適用,此時就需要從服務端來進行適配。
EMQ X TCP 協議規范 及 emqx-tcp 插件更多價值是建立在諸多項目經驗上,為企業私有 TCP 協議定制提供一個成熟方案。
EMQ 對私有 TCP 協議接入適配的僅在 EMQ X 企業版支持,適配后交付 EMQ X Enterprise 與對應的功能插件,開源用戶如具備 Erlang 開發經驗亦可自行開發實現。
歡迎各位用戶下載試用 EMQ X Enterprise,在私有 TCP 協議接入定制包括其他私有化定制方面有任何需求可以同 EMQ 聯系:
- EMQ X Enterprise 下載試用:https://www.emqx.io/downloads
 - 聯系 EMQ:[contact@emqx.io
 
