AWS IoT Greengrass Core 软件的 OTA 更新 - AWS IoT Greengrass

AWS IoT Greengrass Version 1 于 2023 年 6 月 30 日进入延长使用寿命阶段。有关更多信息,请参阅 AWS IoT Greengrass V1维护策略。在此日期之后,AWS IoT Greengrass V1 不再发布更新来提供新功能、功能增强、错误修复或安全补丁。在 AWS IoT Greengrass V1 上运行的设备不会受到干扰,并且将继续运行并连接到云。我们强烈建议您迁移到 AWS IoT Greengrass Version 2,从而添加重要的新功能支持更多平台

AWS IoT Greengrass Core 软件的 OTA 更新

AWS IoT Greengrass Core 软件包中包含可执行 AWS IoT Greengrass 软件无线 (OTA) 更新的更新代理。您可以使用 OTA 更新在一个或多个核心上安装最新版本的 AWS IoT Greengrass Core 软件或 OTA 更新代理软件。通过 OTA 更新,您的核心设备无需物理连接。

我们建议您尽可能使用 OTA 更新。这提供了一种可用于跟踪更新状态和更新历史记录的机制。如果更新失败,则 OTA 更新代理回滚到以前的软件版本。

注意

使用 apt 安装 AWS IoT Greengrass Core 软件时,不支持 OTA 更新。对于这些安装,建议您使用 apt 升级软件。有关更多信息,请参阅 从 APT 存储库安装 AWS IoT Greengrass Core 软件

OTA 更新可以更高效地执行以下操作:

  • 修复安全漏洞。

  • 解决软件稳定性问题。

  • 部署新的或改进的功能。

此功能与 AWS IoT 作业集成。

要求

以下要求适用于 AWS IoT Greengrass 软件的 OTA 更新。

  • Greengrass 核心的本地存储必须至少有 400 MB 的可用磁盘空间。OTA 更新代理的需求是 AWS IoT Greengrass Core 软件运行时使用需求的大约三倍。有关更多信息,请参阅 Amazon Web Services 一般参考 中 Greengrass 核心的服务限额

  • Greengrass Core 必须具有到 AWS Cloud 的连接。

  • 必须使用证书和密钥正确配置和预置 Greengrass Core 以便对 AWS IoT Core 和 AWS IoT Greengrass 进行身份验证。有关更多信息,请参阅 X.509 证书

  • Greengrass Core 不能配置为使用网络代理。

    注意

    从 AWS IoT Greengrass v1.9.3 开始,将 MQTT 流量配置为使用端口 443 而不是默认端口 8883 的核心支持 OTA 更新。但是,OTA 更新代理不支持通过网络代理进行更新。有关更多信息,请参阅 通过端口 443 或网络代理进行连接

  • 无法在包含 AWS IoT Greengrass Core 软件的分区中启用可信引导。

    注意

    您可以在启用了可信引导的分区上安装和运行 AWS IoT Greengrass Core 软件,但这不支持 OTA 更新。

  • AWS IoT Greengrass 必须具有对包含 AWS IoT Greengrass Core 软件的分区的读/写权限。

  • 如果您使用 init 系统来管理 Greengrass Core,则必须配置 OTA 更新以与 init 系统集成。有关更多信息,请参阅 与初始化系统集成

  • 您必须创建用于对 AWS IoT Greengrass 软件更新构件的 Amazon S3 URL 进行预签名的角色。此签署人角色允许 AWS IoT Core 代表您访问存储在 Amazon S3 中的软件更新构件。有关更多信息,请参阅 OTA 更新的 IAM 权限

OTA 更新的 IAM 权限

当 AWS IoT Greengrass 发布 AWS IoT Greengrass Core 软件的新版本时,AWS IoT Greengrass 更新存储在用于 OTA 更新的 Amazon S3 中的软件构件。

您的 AWS 账户 必须包含可用于访问这些构件的 Amazon S3 URL 签署人角色。该角色必须具有允许对目标 AWS 区域 中存储桶执行 s3:GetObject 操作的权限策略。该角色还必须具有信任策略,允许 iot.amazonaws.com 作为可信实体代入角色。

权限策略

对于角色权限,您可以使用 AWS 托管策略或创建自定义策略。

  • 使用 AWS 托管策略

    GreengrassOTAUpdateArtifactAccess 托管策略由 AWS IoT Greengrass 提供。如果您希望允许访问 AWS IoT Greengrass 现在和将来支持的所有 Amazon Web Services 区域,请使用此策略。

  • 创建自定义策略

    如果您要明确指定部署核心的 Amazon Web Services 区域,则应创建自定义策略。以下示例策略允许访问六个区域中的 AWS IoT Greengrass 软件更新。

    { "Version": "2012-10-17", "Statement": [ { "Sid": "AllowAccessToGreengrassOTAUpdateArtifacts", "Effect": "Allow", "Action": [ "s3:GetObject" ], "Resource": [ "arn:aws:s3:::us-east-1-greengrass-updates/*", "arn:aws:s3:::us-west-2-greengrass-updates/*", "arn:aws:s3:::ap-northeast-1-greengrass-updates/*", "arn:aws:s3:::ap-southeast-2-greengrass-updates/*", "arn:aws:s3:::eu-central-1-greengrass-updates/*", "arn:aws:s3:::eu-west-1-greengrass-updates/*" ] } ] }
信任策略

附加到角色的信任策略必须允许 sts:AssumeRole 操作并将 iot.amazonaws.com 定义为委托人。这允许 AWS IoT Core 代入该角色作为可信实体。以下是示例策略文档:

{ "Version": "2012-10-17", "Statement": [ { "Sid": "AllowIotToAssumeRole", "Action": "sts:AssumeRole", "Principal": { "Service": "iot.amazonaws.com" }, "Effect": "Allow" } ] }

此外,启动 OTA 更新的用户必须具有使用 greengrass:CreateSoftwareUpdateJobiot:CreateJob 的权限,并可以使用 iam:PassRole 来传递签署人角色的权限。以下为 IAM policy 示例:

{ "Version": "2012-10-17", "Statement": [ { "Action": [ "greengrass:CreateSoftwareUpdateJob" ], "Effect": "Allow", "Resource": "*" }, { "Effect": "Allow", "Action": [ "iot:CreateJob" ], "Resource": "*" }, { "Effect": "Allow", "Action": [ "iam:PassRole" ], "Resource": "arn-of-s3-url-signer-role" } ] }

注意事项

在对 Greengrass 核心软件启动 OTA 更新之前,要注意该操作对 Greengrass 组中设备的影响,不仅影响核心设备,还会影响在本地连接至该核心的客户端设备:

  • 核心在更新期间会关闭。

  • 在核心上运行的任何 Lambda 函数都将关闭。如果这些函数写入到本地资源,除非正常关闭,否则它们可能会导致这些资源的状态不正确。

  • 在核心的停机时间内,与 AWS Cloud 的所有连接都将丢失。客户端设备通过核心路由的消息将丢失。

  • 凭证缓存会丢失。

  • 容纳 Lambda 函数的待处理工作的队列将丢失。

  • 长时间生存的 Lambda 函数将丢失其动态状态信息,并且将丢弃所有待处理工作。

OTA 更新期间保留以下状态信息:

  • Core 配置文件

  • Greengrass 组配置

  • 本地影子

  • Greengrass 日志

  • OTA 更新代理日志

Greengrass OTA 更新代理

Greengrass OTA 更新代理是设备上的软件组件,可处理在云中创建和部署的更新任务。OTA 更新代理在与 AWS IoT Greengrass Core 软件相同的软件包中分发。代理位于 /greengrass-root/ota/ota_agent/ggc-ota。它将日志写入到 /var/log/greengrass/ota/ggc_ota.txt

注意

greengrass-root 表示在您的设备上安装 AWS IoT Greengrass Core 软件的路径。通常,这是 /greengrass 目录。

您可以通过手动执行二进制文件或通过作为 init 脚本的一部分(如 systemd 服务文件)集成来启动 OTA 更新代理。如果您手动执行二进制文件,则应以 root 用户身份运行。在启动时,OTA 更新代理从 AWS IoT Core 侦听 AWS IoT Greengrass 软件更新作业并按顺序执行它们。OTA 更新代理将忽略所有其他 AWS IoT 作业类型。

以下摘录显示了用于启动、停止和重新启动 OTA 更新代理的系统服务文件示例:

[Unit] Description=Greengrass OTA Daemon [Service] Type=forking Restart=on-failure ExecStart=/greengrass/ota/ota_agent/ggc-ota [Install] WantedBy=multi-user.target

作为更新目标的核心不能运行 OTA 更新代理的两个实例。这样做会导致两个代理处理相同的任务,因此产生冲突。

与初始化系统集成

在 OTA 更新期间,OTA 更新代理将重新启动核心设备上的二进制文件。如果二进制文件正在运行,在更新期间,当 init 系统监控 AWS IoT Greengrass Core 软件或代理的状态时,这可能会导致冲突。为了帮助将 OTA 更新机制与您的 init 监控策略集成,您可以编写在更新前后运行的 shell 脚本。例如,您可以使用 ggc_pre_update.sh 脚本,在设备关闭之前备份数据或停止进程。

要告诉 OTA 更新代理运行这些脚本,您必须在 config.json 文件中包含 "managedRespawn" : true 标志。以下摘录显示了此设置:

{ "coreThing": { … }, "runtime": { … }, "managedRespawn": true … }

使用 OTA 更新的托管 Respawn

以下要求适用于 managedRespawn 设置为 true 的 OTA 更新:

  • /greengrass-root/usr/scripts 目录中必须存在以下 shell 脚本:

    • ggc_pre_update.sh

    • ggc_post_update.sh

    • ota_pre_update.sh

    • ota_post_update.sh

  • 脚本必须返回成功的返回代码。

  • 脚本必须由 root 拥有,并且只能由 root 执行。

  • ggc_pre_update.sh 脚本必须停止 Greengrass 进程守护程序。

  • ggc_post_update.sh 脚本必须启动 Greengrass 进程守护程序。

注意

由于 OTA 更新代理管理自己的进程,因此 ota_pre_update.shota_post_update.sh 脚本无需停止或启动 OTA 服务。

OTA 更新代理运行来自 /greengrass-root/usr/scripts 的脚本。该目录树应如下所示:

<greengrass_root> |-- certs |-- config | |-- config.json |-- ggc |-- usr/scripts | |-- ggc_pre_update.sh | |-- ggc_post_update.sh | |-- ota_pre_update.sh | |-- ota_post_update.sh |-- ota

如果将 managedRespawn 设置为 true,则 OTA 更新代理在软件更新前后检查 /greengrass-root/usr/scripts 目录中的这些脚本。如果脚本不存在,则更新失败。AWS IoT Greengrass 不会验证这些脚本的内容。作为最佳实践,请验证您的脚本是否正常运行,并针对错误发出相应的退出代码。

对于 AWS IoT Greengrass Core 软件的 OTA 更新:
  • 开始更新之前,代理运行 ggc_pre_update.sh 脚本。使用此脚本执行需要在 OTA 更新代理启动 AWS IoT Greengrass Core 软件更新之前运行的命令,例如备份数据或停止任何正在运行的进程。以下示例是一个用于停止 Greengrass 进程守护程序的简单脚本。

    #!/bin/bash set -euo pipefail systemctl stop greengrass
  • 完成更新后,代理运行 ggc_post_update.sh 脚本。使用此脚本执行在 OTA 更新代理启动 AWS IoT Greengrass Core 软件更新后需要运行的命令,例如重新启动进程。以下示例是一个启动 Greengrass 进程守护程序的简单脚本。

    #!/bin/bash set -euo pipefail systemctl start greengrass
对于 OTA 更新代理的 OTA 更新,请执行以下操作:
  • 开始更新之前,代理运行 ota_pre_update.sh 脚本。使用此脚本执行需要在 OTA 更新代理更新自身之前运行的命令,例如备份数据或停止任何正在运行的进程。

  • 完成更新后,代理运行 ota_post_update.sh 脚本。使用此脚本执行需要在 OTA 更新代理更新自身后运行的命令,例如重新启动进程。

注意

如果将 managedRespawn 设置为 false,则 OTA 更新代理不运行脚本。

创建 OTA 更新

按照以下步骤在一个或多个核心上执行 AWS IoT Greengrass 软件的 OTA 更新:

  1. 确保您的核心满足 OTA 更新的要求

    注意

    如果您将 init 系统配置为管理 AWS IoT Greengrass Core 软件或 OTA 更新代理,请验证核心上的以下内容:

    • config.json 文件指定 "managedRespawn" : true

    • /greengrass-root/usr/scripts 目录包含以下脚本:

      • ggc_pre_update.sh

      • ggc_post_update.sh

      • ota_pre_update.sh

      • ota_post_update.sh

    有关更多信息,请参阅 与初始化系统集成

  2. 在核心设备终端中,启动 OTA 更新代理。

    cd /greengrass-root/ota/ota_agent sudo ./ggc-ota
    注意

    greengrass-root 表示在您的设备上安装 AWS IoT Greengrass Core 软件的路径。通常,这是 /greengrass 目录。

    不要在核心上启动 OTA 更新代理的多个实例,因为这可能会导致冲突。

  3. 使用 AWS IoT Greengrass API 创建软件更新作业。

    1. 调用 CreateSoftwareUpdateJob API。在此示例过程中,我们使用 AWS CLI 命令。

      以下命令创建一个作业,用于更新核心上的 AWS IoT Greengrass Core 软件。替换示例值,然后运行命令。

      Linux or macOS terminal
      aws greengrass create-software-update-job \ --update-targets-architecture x86_64 \ --update-targets [\"arn:aws:iot:region:123456789012:thing/myCoreDevice\"] \ --update-targets-operating-system ubuntu \ --software-to-update core \ --s3-url-signer-role arn:aws:iam::123456789012:role/myS3UrlSignerRole \ --update-agent-log-level WARN \ --amzn-client-token myClientToken1
      Windows command prompt
      aws greengrass create-software-update-job ^ --update-targets-architecture x86_64 ^ --update-targets [\"arn:aws:iot:region:123456789012:thing/myCoreDevice\"] ^ --update-targets-operating-system ubuntu ^ --software-to-update core ^ --s3-url-signer-role arn:aws:iam::123456789012:role/myS3UrlSignerRole ^ --update-agent-log-level WARN ^ --amzn-client-token myClientToken1

      此命令将返回以下响应。

      { "IotJobId": "GreengrassUpdateJob_c3bd7f36-ee80-4d42-8321-a1da0EXAMPLE", "IotJobArn": "arn:aws:iot:region:123456789012:job/GreengrassUpdateJob_c3bd7f36-ee80-4d42-8321-a1da0EXAMPLE", "PlatformSoftwareVersion": "1.10.1" }
    2. 从响应复制 IoTJobId

    3. 在 AWS IoT Core API 中调用 DescribeJob 以查看任务状态。将示例值替换为您的作业 ID,然后运行命令。

      aws iot describe-job --job-id GreengrassUpdateJob_c3bd7f36-ee80-4d42-8321-a1da0EXAMPLE

      该命令返回一个响应对象,其中包含有关作业的信息,包括 statusjobProcessDetails

      { "job": { "jobArn": "arn:aws:iot:region:123456789012:job/GreengrassUpdateJob_c3bd7f36-ee80-4d42-8321-a1da0EXAMPLE", "jobId": "GreengrassUpdateJob_c3bd7f36-ee80-4d42-8321-a1da0EXAMPLE", "targetSelection": "SNAPSHOT", "status": "IN_PROGRESS", "targets": [ "arn:aws:iot:region:123456789012:thing/myCoreDevice" ], "description": "This job was created by Greengrass to update the Greengrass Cores in the targets with version 1.10.1 of the core software running on x86_64 architecture.", "presignedUrlConfig": { "roleArn": "arn:aws::iam::123456789012:role/myS3UrlSignerRole", "expiresInSec": 3600 }, "jobExecutionsRolloutConfig": {}, "createdAt": 1588718249.079, "lastUpdatedAt": 1588718253.419, "jobProcessDetails": { "numberOfCanceledThings": 0, "numberOfSucceededThings": 0, "numberOfFailedThings": 0, "numberOfRejectedThings": 0, "numberOfQueuedThings": 1, "numberOfInProgressThings": 0, "numberOfRemovedThings": 0, "numberOfTimedOutThings": 0 }, "timeoutConfig": {} } }

    有关问题排查帮助,请参阅故障排除 AWS IoT Greengrass

CreateSoftwareUpdateJob API

您可以使用 CreateSoftwareUpdateJob API 更新核心设备上的 AWS IoT Greengrass Core 软件或 OTA 更新代理软件。此 API 创建一个 AWS IoT 快照作业,在更新可用时通知设备。调用 CreateSoftwareUpdateJob 后,您可以使用其他 AWS IoT 作业命令来跟踪软件更新。有关更多信息,请参阅 AWS IoT 开发人员指南中的作业

以下示例介绍如何使用 AWS CLI 创建用于更新核心设备上的 AWS IoT Greengrass Core 软件的作业:

aws greengrass create-software-update-job \ --update-targets-architecture x86_64 \ --update-targets [\"arn:aws:iot:region:123456789012:thing/myCoreDevice\"] \ --update-targets-operating-system ubuntu \ --software-to-update core \ --s3-url-signer-role arn:aws:iam::123456789012:role/myS3UrlSignerRole \ --update-agent-log-level WARN \ --amzn-client-token myClientToken1

create-software-update-job 命令会返回一个 JSON 响应,其中包含作业 ID、作业 ARN 和更新所安装的软件版本:

{ "IotJobId": "GreengrassUpdateJob_c3bd7f36-ee80-4d42-8321-a1da0EXAMPLE", "IotJobArn": "arn:aws:iot:region:123456789012:job/GreengrassUpdateJob_c3bd7f36-ee80-4d42-8321-a1da0EXAMPLE", "PlatformSoftwareVersion": "1.9.2" }

有关演示如何使用 create-software-update-job 更新核心设备的步骤,请参阅创建 OTA 更新

create-software-update-job 命令包含以下参数:

--update-targets-architecture

核心设备的架构。

有效值:armv7larmv6lx86_64aarch64

--update-targets

要更新的核心。该列表可以包含单个核心的 ARN 和其成员为核心的事物组的 ARN。有关事物组的更多信息,请参阅AWS IoT开发人员指南中的静态事物组

--update-targets-operating-system

核心设备的操作系统。

有效值:ubuntuamazon_linuxraspbianopenwrt

--software-to-update

指定应该更新核心的软件还是 OTA 更新代理软件。

有效值:coreota_agent

--s3-url-signer-role

用于预签名 Amazon S3 URL(链接至 AWS IoT Greengrass 软件更新构件)的 IAM 角色的 ARN。角色的附加权限策略必须允许对目标 AWS 区域 中的存储桶执行 s3:GetObject 操作。角色还必须允许 iot.amazonaws.com 代入角色作为可信实体。有关更多信息,请参阅 OTA 更新的 IAM 权限

--amzn-client-token

(可选)用于进行幂等请求的客户端令牌。请提供一个唯一令牌,以防止因内部重试而创建重复更新。

--update-agent-log-level

(可选)OTA 更新代理生成的日志语句的日志记录级别。默认为 ERROR

有效值:NONETRACEDEBUGVERBOSEINFOWARNERRORFATAL

注意

CreateSoftwareUpdateJob 仅接受对以下受支持的架构和操作系统组合的请求:

  • ubuntu/x86_64

  • ubuntu/aarch64

  • amazon_linux/x86_64

  • raspbian/armv7l

  • raspbian/armv6l

  • openwrt/aarch64

  • openwrt/armv7l