可靠地要求设备执行单个操作并确认状态的一个请求实体。
IoT 解决方案应该能以这样的方式与设备进行交互:解决方案或是使用该解决方案的人,可以可靠地要求设备执行某个动作。更进一步的,这样的交互需要在会出现间隙性中断的网络环境中进行,并通常需要使用资源非常有限的设备。
IoT 解决方案使用"命令"设计来要求设备执行操作,并通过利用一个简单的概念确保可靠的交互:除非被确认为成功,否则任何请求的操作都不会被视为成功。
下图中显示的"命令"设计可以提供此功能:
(PPTx)
值得注意的是,“命令"设计并不是“反向遥测”。相反,“命令"设计解决了需要在远程位置运行的设备上可靠地触发操作的解决方案所固有的挑战。
实施此设计时,请考虑以下问题:
由于命令的执行实际上导致设备中状态的改变,因此”设备状态副本“设计是在 IoT 解决方案中执行命令的首选方法。在"设备状态副本"设计不适合或超过某些实现限制的情况下,请考虑"命令"设计并定制化实现控制。
每个命令都应具有解决方案唯一的类型,并且每个命令消息应包含全局唯一的消息 ID。命令消息的 ID 允许解决方案跟踪不同命令的状态,通过命令类型可以诊断不同命令类别的潜在问题。消息应该是幂等的,不允许在不知道设备和请求者的情况下被丢失或重复。
当某些命令的运行时间超过正常范围时,简单的返回“SUCCESS”或“FAILURE”命令完成消息是不足够的。相反,解决方案应该至少利用三个命令状态:“SUCCESS”,“FAILURE”和“RUNNING”。设备应在预期的时间间隔内返回“RUNNING”,直到命令完成。通过使用在预期间隔上报告的“RUNNING”状态,解决方案可以确定长时间运行的命令在什么时候事实上已经失败了。
当解决方案中的命令需要人为批准才能在设备执行操作之前,应该在解决方案中添加人为工作流(human-workflow)组件。该组件将拦截特定类型的命令,并在将它们实际发送到设备之前将它们排队等待人工批准。
如果解决方案有一些可能需要回退的命令,那么大部分时候从解决方案本身来管理回滚是更容易的,而不是期望每个设备理解并记住回滚注意事项。例如,向设备发送命令以便将执行器(actuator)从当前报告的位置0°移动到 45°的位置。设备成功执行了该命令。在稍后的时刻,解决方案要求设备返回到先前的状态,先前的状态通常更容易在解决方案本身中进行跟踪,而不是期望每个设备跟踪其先前的状态。这种情况的回滚将由解决方案来执行,即向设备发送命令以将其位置改变为0°。
如果在没有与服务器连接的情况下也需要回滚的话,那解决方案可以利用网关来记录设备的先前状态并执行基于这些值的回滚。
组件向设备发出启动电机的请求,并通过服务质量(Quality of Service)以保证命令传达。
组件将命令请求消息发送到设备订阅的commands/deviceID主题:
{
"cmd": "MOTOR_1_ON",
"tid": "CAFED00D",
"status": "REQUEST"
}
该组件同时跟踪消息的事务 ID “CAFED00D”,该消息已发布但未完成。
设备从主题commands/deviceID接收消息,启动motor 1,并对组件订阅的主题commands/deviceID/ack进行确认响应。该组件在一段时间后收到以下确认:
{
"tid": "CAFED00D",
"status": "SUCCESS"
}
设备不再跟踪命令请求。组件将SUCCESS值映射到`CAFED00D’的事务 ID,并从未完成的请求列表中删除该事务,表示该命令已完成。 “FAILURE”的结果可能表示需要调查物理设备问题。
组件向设备发出请求以启动电机,但设备处于离线状态
组件将命令请求消息发送到设备订阅的commands/deviceID主题:
{
"cmd": "MOTOR_1_ON",
"tid": "CAFED00D",
"status": "REQUEST"
}
该组件还跟踪“CAFED00D”的消息事务 ID,该消息已发布且未完成。 设备处于离线状态,但未收到消息。
在一段设定的时间之后,组件将基于线性或退避(back-off)时间段,并使用相同的事务 ID重新发送命令请求消息,同时跟踪重试状态。经过一定次数的重试后,组件将确定设备没有收到命令,或者无法回复,并采取适当的措施。