使用Amazon ECS Exec用于调试 - Amazon ECS
AWS 文档中描述的 AWS 服务或功能可能因区域而异。要查看适用于中国区域的差异,请参阅中国的 AWS 服务入门

本文属于机器翻译版本。若本译文内容与英语原文存在差异,则一律以英文原文为准。

使用Amazon ECS Exec用于调试

与Amazon ECS Exec,您可以直接与容器交互,而无需首先与主机容器操作系统交互、打开入站端口或管理 SSH 密钥。您可以使用ECS Exec在中运行命令或获取 shell 到运行在Amazon EC2实例或AWS Fargate。这样,就可以更轻松地收集诊断信息并快速排查错误。例如,在开发上下文中,您可以使用ECS Exec轻松与容器中的各种流程进行交互,并排除应用程序故障。而且,在生产场景中,您可以使用它来获得对容器的破玻璃访问以调试问题。

您可以在正在运行的 Linux 容器中使用弹性云服务器执行Amazon ECSAPI、AWS Command Line Interface(AWS CLI),AWS软件开发工具包或AWS CopilotCLI。有关使用弹性云服务器执行的详细信息以及视频演练,请使用AWS CopilotCLI,请参阅副驾驶 Github 文档

您还可以使用ECS Exec以维护更严格的访问控制策略和审核容器访问。通过选择性地启用此功能,您可以控制谁可以运行命令,以及他们可以在哪些任务上运行这些命令。通过每个命令及其输出的日志,您可以使用ECS Exec来审核运行了哪些任务,您可以使用CloudTrail来审核访问容器的用户。

Architecture

ECS Exec利用AWS Systems Manager(SSM)会话管理器与正在运行的容器建立连接,并使用AWS Identity and Access Management(IAM) 策略来控制对正在运行的容器中运行的命令的访问。这是通过将必要的 SSM 代理二进制文件绑定到容器中来实现的。这些区域有:Amazon ECS或者AWS Fargate代理负责启动SSM核心代理以及应用程序代码。有关更多信息,请参阅 。Systems Manager会话管理器

您可以审核哪个用户访问容器AWS CloudTrail并将每个命令(及其输出)记录到Amazon S3或者Amazon CloudWatch Logs。要使用自己的加密密钥对本地客户端和容器之间的数据进行加密,必须提供AWS Key Management Service(AWS KMS) 键。

使用注意事项ECS Exec

对于本主题,您应熟悉使用ECS Exec:

  • ECS Exec仅在 Linux 容器上受支持。

  • ECS Exec当前不支持使用AWS 管理控制台。

  • 如果您使用的是接口Amazon VPC使用的终端节点Amazon ECS,则必须创建接口Amazon VPC的 终端节点Systems Manager会话管理器。有关更多信息,请参阅 创建Systems Manager终端节点

  • 无法为现有任务启用弹性云服务器执行。它只能为新任务启用。

  • 当用户在容器上使用ECS Exec,则这些命令作为root用户。这些区域有:SSM代理及其子进程以 root 用户身份运行,即使您为容器指定用户 ID 也是如此。

  • 这些区域有:SSM代理要求容器文件系统能够写入,以便创建所需的目录和文件。因此,使根文件系统只读使用readonlyRootFilesystem不支持任务定义参数或任何其他方法。

  • 用户可以运行容器上下文中可用的所有命令。以下操作可能会导致孤立进程和僵尸进程:终止容器的主进程、终止命令代理和删除依赖关系。要清理僵尸进程,我们建议将initProcessEnabled标志添加到您的任务定义中。

  • 在启动时SSM之外的会话execute-command操作,则会导致会话未被记录,并根据会话限制进行计数。我们建议通过拒绝ssm:start-session操作,使用IAM策略。有关更多信息,请参阅 限制对 “启动会话” 操作的访问

  • ECS Exec将使用一些 CPU 和内存。在任务定义中指定 CPU 和内存资源分配时,您需要适应这一点。

使用 ECS Exec 的先决条件

在您开始使用之前ECS Exec,请确保您已完成以下操作:

  • 安装和配置 AWS CLI。有关更多信息,请参阅 AWS CLI

  • 安装会话管理器插件AWS CLI。有关更多信息,请参阅 。安装会话管理器插件AWS CLI

  • ECS Exec具有版本要求,具体取决于您的任务是否托管在Amazon EC2或者AWS Fargate:

    • 如果您使用的是Amazon EC2,必须使用Amazon ECS优化 AMI,该 AMI 在 2021 年 1 月 20 日之后发布,其代理版本为1.50.2或更多。有关更多信息,请参阅 。亚马逊弹性云服务器优化 AMI

    • 如果您使用的是AWS Fargate,则必须使用平台版本1.4.0或更高。有关更多信息,请参阅 。远盖特长;平台版本

启用和使用ECS Exec

所需的 IAM 权限ECS Exec

这些区域有:ECS Exec要求执行任务IAM角色授予容器之间通信所需的权限SSM代理 (execute-command代理)和SSM服务。有关更多信息,请参阅 。Amazon ECStaskIAM角色。您应向任务添加以下权限IAM角色并包含任务IAM角色。有关更多信息,请参阅 。添加和删除IAM策略

对您的任务使用以下策略IAM角色添加所需的SSM权限。

{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Action": [ "ssmmessages:CreateControlChannel", "ssmmessages:CreateDataChannel", "ssmmessages:OpenControlChannel", "ssmmessages:OpenDataChannel" ], "Resource": "*" } ] }

可选的任务定义更改

如果您设置了任务定义参数initProcessEnabledtrue,这将启动容器内的 init 进程,从而删除找到的任何僵尸 SSM 代理子进程。以下是示例。

{ "taskRoleArn": "ecsTaskRole", "networkMode": "awsvpc", "requiresCompatibilities": [ "EC2", "FARGATE" ], "executionRoleArn": "ecsTaskExecutionRole", "memory": ".5 gb", "cpu": ".25 vcpu", "containerDefinitions": [ { "name": "amazon-linux", "image": "amazonlinux:latest", "essential": true, "command": ["sleep","3600"], "linuxParameters": { "initProcessEnabled": true } } ], "family": "ecs-exec-task" }

启用ECS Exec为您的任务和服务

您可以启用ECS Exec功能,方法是指定--enable-execute-command标志使用以下值之一时AWS CLI命令:create-serviceupdate-servicestart-task,或者run-task

例如,如果您运行以下命令,则ECS Exec功能为新创建的服务启用。有关创建服务的更多信息,请参阅。create-service

aws ecs create-service \ --cluster cluster-name \ --task-definition task-definition-name \ --enable-execute-command \ --service-name service-name --desired-count 1

为任务启用弹性云服务器执行后,可以运行以下命令,确认任务是否可以使用。如果lastStatus属性ExecuteCommandAgent被列为RUNNINGenableExecuteCommand属性设定为true,那么您的任务就绪。

aws ecs describe-tasks \ --cluster cluster-name \ --tasks task-id

以下输出代码段是您可能会看到的内容的示例。

{ "tasks": [ { ... "containers": [ { ... "managedAgents": [ { "lastStartedAt": "2021-03-01T14:49:44.574000-06:00", "name": "ExecuteCommandAgent", "lastStatus": "RUNNING" } ] } ], ... "enableExecuteCommand": true, ... } ] }

使用 运行命令ECS Exec

在您确认ExecuteCommandAgent正在运行,则可以使用以下命令在容器上打开交互式 shell。如果您的任务包含多个容器,则必须使用--container标记。Amazon ECS仅支持启动交互式会话,因此您必须使用--interactive标记。

以下命令将运行一个交互式/bin/sh命令对名为container-name用于一个 ID 为task-id

aws ecs execute-command --cluster cluster-name \ --task task-id \ --container container-name \ --interactive \ --command "/bin/sh"

使用日志记录和审计ECS Exec

在任务和服务中启用日志记录和审核

Amazon ECS提供了一个默认配置,用于运行日志记录命令ECS Exec通过将日志发送到CloudWatch Logs使用awslogs日志驱动程序,在您的任务定义中配置。如果要提供自定义配置,AWS CLI支持--configuration标志create-clusterupdate-cluster命令。同样重要的是要知道容器图像需要scriptcat以便将命令日志正确上传到Amazon S3或者CloudWatch Logs。有关创建集群的更多信息,请参阅。create-cluster

注意

此配置仅处理execute-command会话。它不会影响应用程序的日志记录。

以下示例创建一个服务,然后将输出记录到您的CloudWatch Logs名为的 LogGroupcloudwatch-log-group-name和您的Amazon S3名为的存储桶s3-bucket-name

aws ecs create-cluster \ --cluster-name cluster-name \ --configuration executeCommandConfiguration="{ \ kmsKeyId=string, \ logging=OVERRIDE, \ logConfiguration={ \ cloudWatchLogGroupName=cloudwatch-log-group-name, \ cloudWatchEncryptionEnabled=true, \ s3BucketName=s3-bucket-name, \ s3EncryptionEnabled=true, \ s3KeyPrefix=demo \ } \ }"

这些区域有:logging属性决定日志记录功能的行为ECS Exec:

  • NONE:禁用日志记录

  • DEFAULT:日志将发送到配置的awslogs驱动程序(如果未配置驱动程序,则不会保存任何日志。)

  • OVERRIDE:日志将发送到所提供的Amazon CloudWatch LogsLogGroup、Amazon S3存储桶,或同时兼有

所需的 IAM 权限Amazon CloudWatch Logs或者Amazon S3日志系统

要启用日志记录,请执行Amazon ECS任务角色需要具有其他权限。这些附加权限可以作为内联策略添加到任务角色。它们是不同的,具体取决于您是否将日志定向到Amazon CloudWatch Logs或者Amazon S3。

Amazon CloudWatch Logs

以下示例内联策略添加所需的Amazon CloudWatch Logs权限。

{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Action": [ "logs:DescribeLogGroups" ], "Resource": "*" }, { "Effect": "Allow", "Action": [ "logs:CreateLogStream", "logs:DescribeLogStreams", "logs:PutLogEvents" ], "Resource": "arn:aws:logs:region:account-id:log-group:/aws/ecs/cloudwatch-log-group-name:*" } ] }
Amazon S3

以下示例内联策略添加所需的Amazon S3权限。

{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Action": [ "s3:GetBucketLocation" ], "Resource": "*" }, { "Effect": "Allow", "Action": [ "s3:GetEncryptionConfiguration" ], "Resource": "arn:aws:s3:::s3-bucket-name" }, { "Effect": "Allow", "Action": [ "s3:PutObject" ], "Resource": "arn:aws:s3:::s3-bucket-name/*" } ] }

IAM使用您自己的 KMS 客户主密钥 (CMK) 进行加密所需的权限

默认情况下,在本地客户端和容器之间传输的数据使用 TLS 1.2 加密AWS提供。要使用您自己的 CMK 进一步加密数据,您必须创建 CMK 并将kms:Decrypt任务的权限IAM角色。您的容器将使用此权限解密数据。有关创建 CMK 的更多信息,请参阅。创建密钥

您需要将以下内联策略添加到您的任务 IAM 角色,该角色需要AWS KMS权限。有关更多信息,请参阅 所需的 IAM 权限ECS Exec

{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Action": [ "kms:Decrypt" ], "Resource": "kms-key-arn" } ] }

对于使用您自己的 CMK 进行加密的数据,使用execute-command操作必须被授予kms:GenerateDataKey权限。

以下针对您的用户或组的示例策略包含使用您自己的 CMK 所需的权限。您必须指定 CMK 的 Amazon 资源名称 (ARN)。

{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Action": [ "kms:GenerateDataKey" ], "Resource": "kms-key-arn" } ] }

使用IAM策略限制访问ECS Exec

您可以使用下面的一个或多个值来限制用户对执行命令 API 操作的访问。IAM策略条件密钥:

  • aws:ResourceTag/clusterTagKey

  • ecs:ResourceTag/clusterTagKey

  • aws:ResourceTag/taskTagKey

  • ecs:ResourceTag/taskTagKey

  • ecs:container-name

  • ecs:cluster

  • ecs:task

  • ecs:enable-execute-command

使用以下示例IAM策略,用户可以在任务中运行的容器中运行命令,这些容器中的标记具有environment键和development值,并在名为cluster-name

{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Action": "ecs:ExecuteCommand", "Resource": "arn:aws:ecs:region:aws-account-id:task/cluster-name/*", "Condition": { "StringEquals": { "ecs:ResourceTag/environment": "development" } } } ] }

使用以下IAM策略示例,用户无法使用execute-command当容器名称为production-app

{ "Version": "2012-10-17", "Statement": [ { "Effect": "Deny", "Action": [ "ecs:ExecuteCommand" ], "Resource": "*", "Condition": { "StringEquals": { "ecs:container-name": "production-app" } } } ] }

使用以下IAM策略,用户只能在禁用弹性云服务器执行时启动任务。

{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Action": [ "ecs:RunTask", "ecs:StartTask", "ecs:CreateService", "ecs:UpdateService" ], "Resource": "*", "Condition": { "StringEquals": { "ecs:enable-execute-command": "false" } } } ] }
注意

由于execute-commandAPI 操作仅包含请求中的任务和集群资源,仅评估群集和任务标签。

限制对 “启动会话” 操作的访问

在启动时SSM会话是可能的,这可能会导致会话无法记录。在弹性云服务器执行以外开始的会话也会计入会话配额。我们建议通过拒绝ssm:start-session操作直接为您的Amazon ECS使用的任务IAM策略。您可以拒绝访问所有Amazon ECS任务或基于所使用的标记的特定任务。

以下是示例IAM策略,拒绝访问ssm:start-session操作,用于具有指定集群名称的所有区域中的任务。您可以选择包含通配符和cluster-name

{ "Version": "2012-10-17", "Statement": [ { "Effect": "Deny", "Action": "ssm:StartSession", "Resource": "arn:aws:ecs:*:111122223333:task/cluster-name/*" } ] }

以下是示例IAM策略,拒绝访问ssm:start-session对标记键标记的所有区域中的资源执行操作Task-Tag-Key和标签值Exec-Task

{ "Version": "2012-10-17", "Statement": [ { "Effect": "Deny", "Action": "ssm:StartSession", "Resource": "*", "Condition": { "StringEquals": { "aws:ResourceTag/Task-Tag-Key": "Exec-Task" } } } ] }

排查弹性云服务器执行的相关问题

以下是故障排除说明,帮助诊断使用弹性云服务器执行时出现错误的原因。

使用验证Amazon ECS执行检查器

这些区域有:Amazon ECS执行检查器脚本提供了一种方法来验证和验证Amazon ECS群集和任务符合使用弹性云服务器执行功能的先决条件。该工具需要最新版本的AWS CLI并且jq可以使用。有关更多信息,请参阅 。Amazon ECS执行检查器(位于 GitHub 上)。

调用时出错execute-command

如果The execute command failed错误发生,以下是可能的原因。

  • 任务没有所需的权限。验证用于启动任务的任务定义是否具有任务IAM角色定义,并且该角色具有所需权限。有关更多信息,请参阅 所需的 IAM 权限ECS Exec

  • 由于速度较慢或网络延迟,SSM 代理未连接。等待,然后尝试execute-command再次执行操作。