第 21 章

安全部署

EMQX 安全部署:host_network 的風險、對外暴露、Rate Limit、TLS 要求、管理面防護與最小權限原則。

為什麼要學這個

你的 EMQX 負責整個家的 MQTT 訊息,而它同時也是攻擊者最想碰的入口之一:只要有人能連線、能做驗證或訂閱,就可能竊取感測資料或操控裝置。Woow EMQX 用 host_network 模式直接把連接埠開在主機上,安全界線比「容器只在模擬網路」更薄,更需要你手工守住。

讀完這章,你會把 EMQX 的防護想成一層一層:驗證擋住誰能連,ACL 擋住誰能發布與訂閱,Rate Limit 擋住風暴,TLS 擋住竊聽,以及管理面(Dashboard)不要被別人直連。最後落在一句原則——最小權限(least privilege)。

核心概念

EMQX 的安全涵蓋四段通道:Client → Listener(有沒有 TLS、驗證)、Authentication → Authorization(誰能連、誰能做什麼)、資源保護(Limit、Blacklist、Flapping Detect),以及 管理面(Dashboard 與 API 的存取)。

Woow add-on 因為 host_network,五個連接埠(1883、8083、8084、8883、18083)都直接開在主機上。若 Home Assistant 主機只在可信的內網,風險尚可;但一旦經由路由器開埠、DMZ 或對外部提供任何服務,這些監聽埠就可能被公網掃描。安全部署的核心,是「只暴露你需要的監聽器」。

官方 security checklist 也提醒一個容易被忽略的事實:EMQX 若還沒設定 Authentication,預設會允許所有 client 連線。所以「先設驗證」不是加分題,是啟動前就必須完成的事。

名詞對照

英文中文一句話
Host Network主機網路模式add-on 直接使用主機的連接埠
Exposure暴露面可被外部觸及的監聽端口範圍
Rate Limit速率限制限制連線與發布速度,防資源耗盡
TLS傳輸加密加密 client 與 broker 之間的流量
Least Privilege最小權限只給帳號做它該做的事的權限
API Key介面金鑰REST API 用的驗證憑證,非 Dashboard 密碼

安全首步是「把預設值換掉」:Dashboard 的 admin/public 公開值誰都查得到,啟用後第一件改變它;API key 與 MQTT client 憑證也一律用佔位符(如 <你的密碼>、YOUR_TOKEN)表示,不印內網資訊。

動手做

  1. 改掉預設管理密碼

    第一次登入 Dashboard 時若系統要求,就把 public 換成自己的強密碼。即使沒被要求,也去 Dashboard 的使用者設定手動改,避免任何人用公開預設值登入。

  2. 設定 Authentication

    到 Access Control → Authentication,建立一組驗證(建議 Password-Based → Built-in Database),建立正式使用者取代預設匿名連線。公開監聽之前,至少要有「匿名不得連」。

  3. 用 Authorization 限縮 ACL

    到 Access Control → Authorization,為每個使用者的 Allow 規則依最小權限撰寫:Home Assistant 需發布與訂閱哪些主題、Z2M 需要哪些,一一列出具體主題,不要放 # 全放行。

  4. 加上 Rate Limit 與檢視 Listener

    到 Management → Listeners 頁,為對外監聽設 Rate Limit(如 max connections per second);並確認 18083(Dashboard)沒有直接暴露,最好只留在內網或加認證。

以上不涵蓋 TLS 設定:若你的流量會跨不可信網段,還需要再為 8883(MQTTS)與 8084(WSS)配置憑證。詳細做法留在第 8 章的 Listener/TLS。

host_network 與對外暴露

Woow add-on 的 host_network 代表它直接用 Home Assistant 主機的連接埠:1883(MQTT)、8083(MQTT over WebSocket)、8084(WSS,MQTT over secure WebSocket)、8883(MQTTS)、18083(Dashboard)。沒有容器層的私網隔離。

風險來自「誰能觸及這些埠」。若主機固定在可信內網,威脅較低;但若你在路由器開啟對外連線,或把主機放到 DMZ、或使用 ngrok 公開 1883,那就把 broker 推向公網。此時:

  • 只開放必要的 Listener,不要一次把五個埠都曝光。
  • 明文 1883 盡量留置內網或過渡用途;對外請優先使用加密的 8883/8084。
  • Dashboard(18083)只限可信網路,最好用 HTTPS 且只允許你需要的帳號。

EMQX 文件的 security checklist 也建議:Proxy Protocol 或 WebSocket 監聽若沒有受信 proxy 覆寫來源 IP,要關閉轉發位址標頭,以免 IP-based 授權被偽造。

Rate Limit 與資源防護

Rate Limit(limiter)是 EMQX 5.0+ 的機制,在入口限速,避免單一 client 或監聽被狂灌。Dashboard 的 Management → Listeners 頁可對每個監聽設值;也能用 emqx.conf 設定。

類型UI 名稱作用超過後的預設行為
bytes_rateData Publish Rate每個 client 每秒發布的 Bytes暫停收取該 client 訊息
messages_rateMessages Publish Rate每個 client 每秒發布的訊息數暫停收取該 client 訊息
max_conn_rateMaximum Connection Rate每次該 listener 每秒可接受的連線數暫停接收新連線

例如 emqx.conf 可這樣對預設 TCP listener 設限(時間單位 s/m/h/d,大小 KB/MB/GB):

listeners.tcp.default {
  bind = "0.0.0.0:1883"
  max_conn_rate = "1000/s"
  messages_rate = "1000/s"
  bytes_rate = "1MB/s"
}

對外暴露時,用 Rate Limit 搭配 Blacklist 與 Flapping Detect,能擋住單一 client 灌爆或反覆重連的濫用。記得把 Flapping 門檻設在正常重連不會誤觸的程度,避免誤鎖正常裝置。

TLS 需求與管理面防護

傳輸跨不可信網時,務必用 TLS:EMQX 的 8883(MQTTS)與 8084(WSS)就是加密監聽。憑證要由受信 CA 或自己的內部 PKI 發行,並在過期前輪替;若要用裝置憑證確認身份,還可搭配 X.509 認證與 mTLS(verify_peer)。

管理面另有幾條硬規則:

  • Dashboard 只用預設密碼是警訊——第一次登入就改,並確認只有需要的人才用得到。
  • REST API 應使用 API Key(system → API Key),並只授與最小角色;EMQX Open Source「不使用 RBAC」,所有 Dashboard 使用者都是管理員。
  • 盡量把 Dashboard 綁在可信介面:localhost、內網,或專用管理網段。

最小權限原則用在每個層面:每個裝置用自己的一組憑證,ACL 只允許需要的主題,不要用萬用字元全放行。防護越細,單一洩漏造成的破口越小。

故障排除

  • 外部掃到 1883 就有人嘗試連:先把監聽關掉或限到內網,再確認「驗證 + ACL」兩個都就位後才考慮公開。
  • Rate Limit 設定後正常 client 被斷:檢查限值的時間單位與數值;並把 Flapping 門檻調到正常重連不會誤觸的程度,避免正常裝置被誤鎖。
  • TLS 連線失敗:檢查憑證鏈、私鍵對應與 CA;如果自簽憑證,需在 client 端把該 CA 加入信任。
  • Dashboard 被公網直接存取:18083 是 HTTP 管理埠,最忌暴露。把它限制在內網或可信連接,並改用 HTTPS 與強密碼。

常見問題

一定要為 MQTT 設 TLS 嗎

視你流量是否跨不可信網。若只是 Home Assistant 與裝置在同一內網互連,內網可信度高,仍記得要用強密碼與 ACL;一旦有對外或跨網需求,就該用 8883/8084 加密。

Rate Limit 會不會拖慢正常使用

若只設在對外監聽、並把限值設得高於正常用量,幾乎無感。它擋的是單一 client 灌爆;正常家庭的訊息量遠低於預設限額,所以不會有感;真的被限速時,再試著調高限值。

Dashboard 密碼改了以後,MQTT 也用同一組嗎

不必。Dashboard 密碼保護管理介面;MQTT client 用的是 Access Control → Authentication 的帳號憑證。兩者是獨立的一套,但都要設強密碼。

Open Source 的 EMQX 有 RBAC 嗎

沒有。EMQX 5.8 Open Source 的 Dashboard 使用者一律是管理員,RBAC(Administrator/Viewer)是 Enterprise 功能。所以在 Open Source 上,管理帳號越少越好,REST API 盡量用最低角色的 API key。

官方來源