跳转到内容

Topic 命名最佳实践

本节汇总 MQTT Topic 设计和管理的综合最佳实践,帮助售前工程师建立系统化的 Topic 设计知识。学习完成后,您将能够:

  • 设计专业、规范的 MQTT Topic 命名体系
  • 避免常见的 Topic 设计陷阱
  • 提供 Topic 架构的咨询建议
  • 在实际项目中实施 Topic 管理规范

在开始本节之前,请确保:

  • 理解 Topic 结构和层级
  • 理解通配符的使用
  • 有实际 MQTT 项目经验
黄金法则: Topic 设计应该像 API 设计一样认真对待
1. 使用斜杠分隔层级
✅ factory/zone1/environment/temperature
❌ factory-zone1-environment-temperature
2. 使用小写字母
✅ sensors/temperature
❌ Sensors/Temperature
3. 层级控制在 3-5 层
✅ factory/zone1/temperature (3层)
⚠️ factory/buildingA/floor1/room101/desk3/temperature (6层)
4. 避免以斜杠开头或结尾
✅ factory/zone1/temperature
❌ /factory/zone1/temperature
5. 避免空格和特殊字符
✅ factory/zone1/temperature
❌ factory/zone 1/temperature

通用模式

{domain}/{location}/{device_type}/{sensor_type}
域 (domain): 项目或场景名称
位置 (location): 物理或逻辑位置
设备类型 (device_type): 设备类别
传感器类型 (sensor_type): 数据类型或指示

实际示例

工厂场景:
factory/zone1/temperature
factory/zone1/machine_003/vibration
factory/control/fan_01/set
智能家居:
home/livingroom/light/status
home/kitchen/temperature
home/bedroom/curtain/set
设备管理:
devices/esp32_001/status
devices/esp32_001/config
devices/shelly_002/relay/power

将不同功能的消息分离到不同的 Topic 层次:

数据 Topic (Data):
{domain}/{location}/data/{sensor}
用途: 传感器上报数据
发布者: ESP32
订阅者: Node-RED, 数据库
控制 Topic (Control):
{domain}/{location}/control/{actuator}
用途: 下发控制命令
发布者: Node-RED, 手机App
订阅者: 执行设备
状态 Topic (Status):
{domain}/{location}/status/{device}
用途: 设备状态报告
发布者: 所有设备
订阅者: 仪表板, 监控系统

为什么要分离

原因说明
安全性可以为控制和数据设置不同的 ACL
可读性通过 Topic 名称即可知道消息性质
性能订阅者可以只订阅需要的数据类别
维护消息分类明确,易于排查问题
  • Topic 结构支持按区域筛选
  • Topic 结构支持按设备类型筛选
  • 控制命令和数据分离
  • 在线状态有独立 Topic
  • 配置 Topic 和数据 Topic 分离
  • 预留了扩展空间(不少于 2 个空闲层级)
  • Topic 最深层级有意义(不是通用名称)
  • 控制 Topic 需要使用高 QoS
  • 敏感数据 Topic 有访问控制
  • 系统 Topic ($SYS) 不暴露给客户端
  • 不支持通配符发布
  • ACL 已配置,限制通配符订阅范围
❌ 错误: 所有数据在同一层级
temperature
humidity
light
status
✅ 正确: 层级化组织
factory/zone1/environment/temperature
factory/zone1/environment/humidity
factory/zone1/status
❌ 错误: Topic 中包含动态数据
devices/esp32_001/192.168.1.100/status (IP 会变)
factory/2024-03-15/temperature (日期会变)
✅ 正确: 动态数据放在 payload 中
Topic: devices/esp32_001/status
Payload: {"ip":"192.168.1.100","status":"online"}
❌ 错误: 层级过深
company/factory/building-a/floor-3/room-301/
desk-5/sensor-001/environment/temperature
✅ 正确: 适度层级
factory/zone3/temperature
详细位置信息放在 payload 或设备注册表中

Anti-Pattern 4: Client-Specific Topic Names

Section titled “Anti-Pattern 4: Client-Specific Topic Names”
❌ 错误: 在 Topic 中使用不标准化的名称
johns_sensor/temp
my_device_123/temperature
✅ 正确: 使用规范命名
factory/zone1/temperature
devices/esp32_001/temperature
# 数据
factory/{zone}/environment/temperature
factory/{zone}/environment/humidity
# 控制
factory/{zone}/control/hvac/set
# 状态
factory/{zone}/status/hvac
# 完整环境数据 (JSON)
factory/{zone}/environment
Payload: {"temp":26.5,"hum":62,"lux":450}
# 或单独 Topic
factory/{zone}/environment/temperature
factory/{zone}/environment/humidity
factory/{zone}/environment/light
# 设备状态
devices/{device_id}/status
Payload: {"status":"online","ip":"192.168.1.100"}
# 设备配置
devices/{device_id}/config
Payload: {"interval":30,"threshold":28}
# 设备告警
devices/{device_id}/alarm
Payload: {"type":"high_temp","value":35}
# mosquitto.conf ACL 示例
# 允许传感器设备发布数据
user sensor_user
topic write factory/+/environment/+
topic write devices/+/status
# 允许仪表板订阅
user dashboard_user
topic read factory/#
topic read devices/+/status
# 管理员读写
user admin
topic readwrite #
Terminal window
# 验证 Topic 结构是否合理
# 1. 检查层级数量
mosquitto_sub -h localhost -t "factory/#" -v | \
awk -F'/' '{print NF-1 " " $0}' | sort -n
# 2. 检查一致性
mosquitto_sub -h localhost -t "#" -v | \
awk -F'/' '{print $1}' | sort | uniq -c
# 3. 检查是否有空格或特殊字符
mosquitto_sub -h localhost -t "#" -v | \
grep -E '[[:space:]]|[^a-zA-Z0-9/_]'

本节要点总结:

  1. 命名规范:小写字母、斜杠分层、3-5 层深度
  2. 分离原则:数据/控制/状态 Topic 分离管理
  3. 避免反模式:扁平结构、Topic 中包含动态数据、过深嵌套
  4. 预留扩展:Topic 设计考虑未来业务扩展
  5. 安全 ACL:配置 Topic 级别的访问控制