15 设备影子与命令控制¶
难度:中级|前置:MQTT、在线状态、状态机|目标:处理离线设备、状态同步和命令回执
为什么不能只“发一条命令”¶
平台下发:
把温度阈值设为 30。
可能发生:
- 设备离线;
- 消息到达但执行失败;
- 设备执行成功但回执丢失;
- 旧命令晚于新命令到达;
- 用户重复点击;
- 设备重启后恢复旧配置。
因此需要区分“希望设备是什么状态”和“设备报告自己是什么状态”。
设备影子¶
- desired:平台期望;
- reported:设备实际报告;
- delta:二者差异;
- version:防止旧更新覆盖新状态。
影子适合最终状态同步,不适合所有瞬时动作。
状态设置与动作命令¶
状态设置¶
重复执行结果相同,更容易幂等。
动作命令¶
可能产生一次性副作用,需要 command_id、回执、超时和幂等。
命令状态¶
Broker 接收成功不等于设备执行成功。回执应关联稳定的 command_id。
版本和顺序¶
设备收到版本 12 后又收到版本 11,应拒绝旧版本。服务器也不能用旧 reported 覆盖新状态。
如果业务只需要同一设备内的顺序,可以按 device_id 分区,不必追求所有设备的全局顺序。
离线命令¶
必须明确策略:
- 离线时立即失败;
- 保存到设备上线后执行;
- 只保留最后一个期望状态;
- 设置命令过期时间;
- 高风险命令禁止离线排队。
自测¶
- desired 和 reported 分别是谁的事实?
- 为什么 reboot 不适合仅用设备影子表达?
- Broker Ack 为什么不能代表设备执行成功?
- 旧版本消息如何避免覆盖新状态?
完成标准¶
- 能解释设备影子的四个核心字段
- 能区分状态设置和动作命令
- 能设计命令状态与回执
- 能定义离线命令策略
下一单元:时序数据与聚合