MQTT 主题(Topic)介绍与设计 作者:马育民 • 2026-04-06 14:36 • 阅读:10003 # 介绍 MQTT 主题是发布/订阅模式下的消息路由核心,是 UTF-8 编码的层级字符串(类似文件路径),用于标识消息通道、实现消息精准分发。良好的主题设计直接决定系统扩展性、可维护性与权限管控能力。 # 一、基础 ### 1. 定义 - **Topic Name(发布主题)**:发布时使用,**严禁通配符**,必须精确、唯一。 例:`smart-home/living-room/thermostat/temperature` - **Topic Filter(订阅过滤器)**:订阅时使用,**允许通配符**,用于匹配一类主题。 例:`smart-home/+/thermostat/#` ### 2. 语法与规则 - 分隔符:**斜杠 `/`** 划分层级(如 `a/b/c` 为 3 级) - 编码:**UTF-8**,支持中文(不推荐生产环境) - 大小写敏感:`Home` ≠ `home` - 长度限制:协议无强制限,但 Broker 通常建议 ≤ **64–128 字节** - 禁止:**以 `/` 开头/结尾**、连续 `//`、空格、特殊字符(`#`/`+`/`$` 除外) - 系统保留:以 `$` 开头(如 `$SYS/`)为 Broker 内部使用,**用户不可占用** ### 3. 通配符(仅订阅可用) #### (1)单层通配符 `+` - 匹配**单个完整层级**,必须独占一层 - 例: - `sensor/+/temperature` ✅ 匹配 `sensor/room1/temperature` ❌ 不匹配 `sensor/room1/humidity`、`sensor/room1/bed/temperature` #### (2)多层通配符 `#` - 匹配**当前层级及以下所有子层级** - 必须在**末尾**、前带 `/`、独占一层 - 例: - `factory/area1/#` ✅ 匹配 `factory/area1/machine/status`、`factory/area1/sensor/temp` --- # 二、主题设计原则 ### 1. 清晰性 > 简洁性 - 用**完整英文单词**,拒绝无意义缩写 ✅ 推荐:`home/bedroom/light/01/status` ❌ 不推荐:`home/br/lt/01/st` ### 2. 层级化(2–5 层最佳) 从**通用 → 具体**,结构稳定 推荐模板: `[版本]/[租户/域]/[位置]/[设备类型]/[设备ID]/[功能/属性]/[操作]` ### 3. 全局一致性 - 所有设备/服务遵循同一命名规范 - 温度:`.../temperature`;湿度:`.../humidity`(统一后缀) ### 4. 可扩展 + 版本化 - 加入版本层:`v1/...`、`v2/...`,兼容迭代 - 预留扩展位:避免后期硬改结构 ### 5. 安全与权限友好 - 便于按层级做 ACL(如禁止订阅 `#`、限制 `cmd/` 写入) - 分离**数据上报(tele)**与**控制指令(cmd)** --- # 三、标准层级设计 ### 通用结构(物联网/工业/智能家居) ``` v1/{org}/{location}/{device-type}/{device-id}/{metric}/{operation} ``` - **v1**:协议/结构版本(必加) - **org**:租户/项目/公司(多租户必备) - **location**:地理/逻辑位置(园区/楼层/车间) - **device-type**:设备类型(sensor/gateway/light/motor) - **device-id**:唯一标识(SN/MAC/UUID) - **metric**:属性/测点(temperature/power/status/battery) - **operation**:动作(tele/cmd/evt/err/log) ### 场景示例 #### 1)智能家居 ``` v1/ha/home/living-room/light/001/tele/power # 上报状态 v1/ha/home/living-room/light/001/cmd/power # 下发控制 v1/ha/home/+/+/+/evt/alarm # 全宅告警 ``` #### 2)工业物联网(IIoT) ``` v2/fac/plant1/line2/machine/press-05/tele/pressure v2/fac/plant1/line2/machine/press-05/cmd/start v2/fac/+/+/+/+/err/# # 全厂故障 ``` #### 3)车载/共享设备 ``` v1/car/region3/vehicle/vin-12345/tele/battery v1/car/region3/vehicle/vin-12345/cmd/lock ``` --- # 四、命名规范 ### 1. 字符规则 - 统一**小写**、数字、`-`/`_`(二选一,全局一致) - 禁止:空格、中文、`?`/`!`/`@`/`%`/`&` 等 - 禁止:以 `/` 开头/结尾、连续 `//` ### 2. 后缀约定(推荐) - `/tele` / `/report`:设备上报数据 - `/cmd` / `/set`:平台下发控制 - `/evt` / `/event`:事件(上线/离线/告警) - `/err` / `/fault`:故障/异常 - `/log`:日志 - `/online` / `/offline`:状态 ### 3. 禁止做法 - ❌ 过深:`a/b/c/d/e/f/g/h`(难订阅、难维护) - ❌ 过浅:`temp123`(无法通配、无法权限) - ❌ 动态ID放顶层:`device-123/temp`(无法批量订阅) - ❌ 发布用通配符:`sensor/#`(协议非法) - ❌ 混用大小写:`Sensor/Temp`、`sensor/temp` --- # 五、权限与安全设计(ACL 友好) ### 1. 最小权限原则 - 设备**只写**自己的 `/tele`、`/evt`、`/err` - 设备**只读**自己的 `/cmd` - 平台/应用**只读** `/tele`、`/evt`、`/err`;**只写** `/cmd` ### 2. 典型 ACL 规则(以 EMQX 为例) ``` # 设备只能发布自己的上报主题 publish { topic: "v1/ha/home/+/light/+/tele/#" } # 设备只能订阅自己的控制主题 subscribe { topic: "v1/ha/home/+/light/+/cmd/#" } # 禁止订阅全量 # deny { topic: "#" } ``` --- # 六、常见误区与坑 1. **过度使用 `#`** 大规模下 Broker 性能急剧下降、安全风险高 2. **无版本、无层级** 业务扩展时重构成本极高 3. **设备ID放顶层** `device-01/temp` → 无法批量订阅同类型设备 4. **混用 `cmd`/`tele`** 控制与数据混在一起,权限混乱、易误控 5. **主题过长** 增加网络开销、Broker 匹配耗时 --- # 七、设计检查清单 投产前必验 - [ ] 2–5 层级、从通用到具体 - [ ] 含版本(v1/) - [ ] 含租户/域(多租户) - [ ] 设备类型 + 唯一ID - [ ] 分离 tele/cmd/evt/err - [ ] 全小写、`-`/`_` 统一、无特殊字符 - [ ] 便于通配、便于 ACL 权限 - [ ] 无 `/` 开头结尾、无连续 `//` - [ ] 发布主题无任何通配符 --- ## 八、总结 MQTT 主题本质是**系统的消息 API 架构**。好设计 = **层级清晰 + 全局一致 + 版本化 + 安全可控**。按“**版本→域→位置→类型→ID→属性→动作**”模板落地,可支撑千万级设备、长期迭代不重构。 原文出处:http://malaoshi.top/show_1GW358eY9rtT.html