与影子交互 - Amazon IoT Core
Amazon Web Services 文档中描述的 Amazon Web Services 服务或功能可能因区域而异。要查看适用于中国区域的差异,请参阅中国的 Amazon Web Services 服务入门

与影子交互

本主题介绍了 Amazon IoT 为处理影子而提供的三种方法的关联消息。这些方法包括:

UPDATE

创建影子(如果不存在),或使用消息正文中提供的状态信息更新现有影子的内容。Amazon IoT 记录每次更新的时间戳,以指示上次更新状态的时间。在影子的状态发生变化时,Amazon IoT 将 /delta 消息发送到所有 MQTT 订阅者,其中包含 desiredreported 状态之间的差异。收到 /delta 消息的设备或应用程序可以根据该差异执行操作。例如,设备可以将其状态更新为所需的状态,或者应用程序可以更新其 UI 以反映设备的状态变化。

GET

检索包含影子的完整状态的当前影子文档,包括元数据。

DELETE

删除影子及其所有内容。您无法恢复删除的影子,但您可以创建具有相同名称的新影子。请注意,删除影子不会将其版本号重置为 0。

协议支持

Amazon IoT 支持 MQTT 和基于 HTTPS 的 REST API 协议以与影子进行交互。Amazon IoT 为 MQTT 发布和订阅操作提供一组保留的请求和响应主题。设备和应用程序应在发布请求主题之前订阅响应主题,以获取有关 Amazon IoT 如何处理请求的信息。有关更多信息,请参阅 Device Shadow MQTT 主题Device Shadow REST API

请求和报告状态

在使用 Amazon IoT 和影子设计 IoT 解决方案时,您应该确定请求更改的应用程序或设备以及实施更改的应用程序或设备。通常,设备实施更改并向影子报告更改,而应用程序和服务响应并请求影子中的更改。您的解决方案可能有所不同,但本主题中的示例假定客户端应用程序或服务请求影子中的更改,而设备执行更改并向影子报告更改。

更新影子

应用程序或服务可以使用 UpdateThingShadow API 或发布到 /update 主题以更新影子的状态。更新仅影响请求中指定的字段。

在客户端请求状态更改时更新影子

在客户端使用 MQTT 协议请求影子中的状态更改时

  1. 客户端应具有当前影子文档,以便它可以确定要更改的属性。有关如何获取当前影子文档的信息,请参阅 /get 操作。

  2. 客户端订阅以下 MQTT 主题:

    • $aws/things/thingName/shadow/name/shadowName/update/accepted

    • $aws/things/thingName/shadow/name/shadowName/update/rejected

    • $aws/things/thingName/shadow/name/shadowName/update/delta

    • $aws/things/thingName/shadow/name/shadowName/update/documents

  3. 客户端使用包含影子的所需状态的状态文档发布 $aws/things/thingName/shadow/name/shadowName/update 请求主题。只需在文档中包含要更改的属性。以下是具有所需状态的文档的示例。

    { "state": { "desired": { "color": { "r": 10 }, "engine": "ON" } } }
  4. 如果更新请求有效,Amazon IoT 将在影子中更新所需的状态并在以下主题上发布消息:

    • $aws/things/thingName/shadow/name/shadowName/update/accepted

    • $aws/things/thingName/shadow/name/shadowName/update/delta

    /update/accepted 消息包含一个 /accepted 响应状态文档 影子文档,而 /update/delta 消息包含一个 /delta 响应状态文档 影子文档。

  5. 如果更新请求无效,Amazon IoT 将在 $aws/things/thingName/shadow/name/shadowName/update/rejected 主题中发布一条消息,其中包含描述错误的 错误响应文档 影子文档。

在客户端使用 API 请求影子中的状态更改时

  1. 客户端调用 UpdateThingShadow API 并将 请求状态文档 状态文档作为其消息正文。

  2. 如果请求有效,Amazon IoT 将返回 HTTP 成功响应代码和 /accepted 响应状态文档 影子文档以作为其响应消息正文。

    Amazon IoT 还会向 $aws/things/thingName/shadow/name/shadowName/update/delta 主题发布一条 MQTT 消息,其中包含订阅它的任何设备或客户端的 /delta 响应状态文档 影子文档。

  3. 如果请求无效,Amazon IoT 将返回 HTTP 错误响应代码 错误响应文档 和以作为其响应消息正文。

当设备在 /desired 主题上收到 /update/delta 状态时,它将在设备中进行所需的更改。然后,它向 /update 主题发送一条消息,以向影子报告其当前状态。

在设备报告其当前状态时更新影子

在设备使用 MQTT 协议向影子报告其当前状态时

  1. 在更新影子之前,设备应订阅以下 MQTT 主题:

    • $aws/things/thingName/shadow/name/shadowName/update/accepted

    • $aws/things/thingName/shadow/name/shadowName/update/rejected

    • $aws/things/thingName/shadow/name/shadowName/update/delta

    • $aws/things/thingName/shadow/name/shadowName/update/documents

  2. 设备向 $aws/things/thingName/shadow/name/shadowName/update 主题发布一条消息以报告其当前状态,例如,在该示例中。

    { "state": { "reported" : { "color" : { "r" : 10 }, "engine" : "ON" } } }
  3. 如果 Amazon IoT 接受更新,它将向 $aws/things/thingName/shadow/name/shadowName/update/accepted 主题发布一条消息,其中包含 /accepted 响应状态文档 影子文档。

  4. 如果更新请求无效,Amazon IoT 将在 $aws/things/thingName/shadow/name/shadowName/update/rejected 主题中发布一条消息,其中包含描述错误的 错误响应文档 影子文档。

在设备使用 API 向影子报告其当前状态时

  1. 设备调用 UpdateThingShadow API 并将 请求状态文档 状态文档作为其消息正文。

  2. 如果请求有效,Amazon IoT 将更新影子并返回 HTTP 成功响应代码以及 /accepted 响应状态文档 影子文档以作为其响应消息正文。

    Amazon IoT 还会向 $aws/things/thingName/shadow/name/shadowName/update/delta 主题发布一条 MQTT 消息,其中包含订阅它的任何设备或客户端的 /delta 响应状态文档 影子文档。

  3. 如果请求无效,Amazon IoT 将返回 HTTP 错误响应代码 错误响应文档 和以作为其响应消息正文。

乐观锁

您可以使用状态文档版本来确保正在更新的设备的影子文档为最新版本。当您为更新请求提供版本时,如果状态文档的当前版本与提供的版本不符,该服务将显示 HTTP 409 冲突响应代码并拒绝请求。

例如:

初始文档:

{ "state": { "desired": { "colors": [ "RED", "GREEN", "BLUE" ] } }, "version": 10 }

更新:(版本不匹配;该请求将被拒绝)

{ "state": { "desired": { "colors": [ "BLUE" ] } }, "version": 9 }

结果:

{ "code": 409, "message": "Version conflict", "clientToken": "426bfd96-e720-46d3-95cd-014e3ef12bb6" }

更新:(版本匹配;请求将被接受)

{ "state": { "desired": { "colors": [ "BLUE" ] } }, "version": 10 }

最终状态:

{ "state": { "desired": { "colors": [ "BLUE" ] } }, "version": 11 }

检索影子文档

您可以使用 GetThingShadow API 或订阅并发布到 /get 主题以检索影子文档。这会检索完整的影子文档,包括 desiredreported 状态之间的任何增量。无论设备还是客户端发出请求,该任务的流程都是相同的。

使用 MQTT 协议检索影子文档

  1. 在更新影子之前,设备或客户端应订阅以下 MQTT 主题:

    • $aws/things/thingName/shadow/name/shadowName/get/accepted

    • $aws/things/thingName/shadow/name/shadowName/get/rejected

  2. 设备或客户端使用空消息正文向 $aws/things/thingName/shadow/name/shadowName/get 主题发布一条消息。

  3. 如果请求成功,Amazon IoT 将向 $aws/things/thingName/shadow/name/shadowName/get/accepted 主题发布一条消息,并在消息正文中包含 /accepted 响应状态文档

  4. 如果请求无效,Amazon IoT 将向 $aws/things/thingName/shadow/name/shadowName/get/rejected 主题发布一条消息,并在消息正文中包含 错误响应文档

使用 REST API 检索影子文档

  1. 设备或客户端使用空消息正文调用 GetThingShadow API。

  2. 如果请求有效,Amazon IoT 将返回 HTTP 成功响应代码以及 /accepted 响应状态文档 影子文档以作为其响应消息正文。

  3. 如果请求无效,Amazon IoT 将返回 HTTP 错误响应代码和 错误响应文档 以作为其响应消息正文。

删除影子数据

可以使用两种方法删除影子数据:您可以在影子文档中删除特定的属性,也可以完全删除影子。

  • 要从影子中删除特定的属性,请更新影子,但将您要删除的属性的值设置为 null。将从影子文档中删除值为 null 的字段。

  • 要删除整个影子,请使用 DeleteThingShadow API 或发布到 /delete 主题。

请注意,删除影子不会将其版本号重置为 0。

从影子文档中删除属性

使用 MQTT 协议从影子中删除属性

  1. 设备或客户端应具有当前影子文档,以便它可以确定要更改的属性。有关如何获取当前影子文档的信息,请参阅 检索影子文档

  2. 设备或客户端订阅以下 MQTT 主题:

    • $aws/things/thingName/shadow/name/shadowName/update/accepted

    • $aws/things/thingName/shadow/name/shadowName/update/rejected

  3. 设备或客户端使用将 $aws/things/thingName/shadow/name/shadowName/update 值分配给要删除的影子属性的状态文档以发布 null 请求主题。只需在文档中包含要更改的属性。以下是删除 engine 属性的文档的示例。

    { "state": { "desired": { "engine": null } } }
  4. 如果更新请求有效,Amazon IoT 将在影子中删除指定的属性,在 $aws/things/thingName/shadow/name/shadowName/update/accepted 主题中发布一条消息,并在消息正文中包含 /accepted 响应状态文档 影子文档。

  5. 如果更新请求无效,Amazon IoT 将在 $aws/things/thingName/shadow/name/shadowName/update/rejected 主题中发布一条消息,其中包含描述错误的 错误响应文档 影子文档。

使用 REST API 从影子中删除属性

  1. 设备或客户端使用 请求状态文档null 值分配给要删除的影子属性的以调用 UpdateThingShadow API。仅在文档中包含要删除的属性。以下是删除 engine 属性的文档的示例。

    { "state": { "desired": { "engine": null } } }
  2. 如果请求有效,Amazon IoT 将返回 HTTP 成功响应代码和 /accepted 响应状态文档 影子文档以作为其响应消息正文。

  3. 如果请求无效,Amazon IoT 将返回 HTTP 错误响应代码 错误响应文档 和以作为其响应消息正文。

删除影子

注意

将设备的影子状态设置为 null 并不会删除影子。在下次更新时,影子版本将会增加。

删除设备的影子并不会删除事物对象。删除事物对象并不会删除相应设备的影子。

删除影子不会将其版本号重置为 0。

使用 MQTT 协议删除影子

  1. 设备或客户端订阅以下 MQTT 主题:

    • $aws/things/thingName/shadow/name/shadowName/delete/accepted

    • $aws/things/thingName/shadow/name/shadowName/delete/rejected

  2. 设备或客户端使用空消息缓冲区发布 $aws/things/thingName/shadow/name/shadowName/delete

  3. 如果删除请求有效,Amazon IoT 将删除影子,在 $aws/things/thingName/shadow/name/shadowName/delete/accepted 主题中发布一条消息,并在消息正文中包含简短的 /accepted 响应状态文档 影子文档。以下是接受的删除消息的示例:

    { "version": 4, "timestamp": 1591057529 }
  4. 如果更新请求无效,Amazon IoT 将在 $aws/things/thingName/shadow/name/shadowName/delete/rejected 主题中发布一条消息,其中包含描述错误的 错误响应文档 影子文档。

使用 REST API 删除影子

  1. 设备或客户端使用空消息缓冲区调用 DeleteThingShadow API。

  2. 如果请求有效,Amazon IoT 将在消息正文中返回 HTTP 成功响应代码以及 /accepted 响应状态文档 和简短 /accepted 响应状态文档 影子文档。以下是接受的删除消息的示例:

    { "version": 4, "timestamp": 1591057529 }
  3. 如果请求无效,Amazon IoT 将返回 HTTP 错误响应代码 错误响应文档 和以作为其响应消息正文。