

# Amazon ECS での IAM ロールのベストプラクティス
<a name="security-iam-roles"></a>

Amazon ECS が必要とするロールは、タスク定義の起動タイプと使用する機能によって異なります。ロールを共有するのではなく、テーブルに個別のロールを作成することをお勧めします。


| ロール | 定義 | 必要な場合 | 詳細情報 | 
| --- | --- | --- | --- | 
| タスク実行ロール | このロールにより、Amazon ECS がお客様に代わって他の AWS サービスを利用できるようにします。 |  タスクは AWS Fargate または外部インスタンスホストされています。また、 [\[See the AWS documentation website for more details\]](http://docs.aws.amazon.com/ja_jp/AmazonECS/latest/developerguide/security-iam-roles.html) タスクは、AWS Fargate または Amazon EC2 インスタンスでホストされています。また、 [\[See the AWS documentation website for more details\]](http://docs.aws.amazon.com/ja_jp/AmazonECS/latest/developerguide/security-iam-roles.html)  | [Amazon ECS タスク実行IAM ロール](task_execution_IAM_role.md) | 
| タスクロール | このロールにより、(コンテナ上の) アプリケーションコードが他の AWS サービスを使用できるようになります。 | アプリケーションは、Amazon S3 などの他の AWS サービスにアクセスします。 | [Amazon ECS タスクの IAM ロール](task-iam-roles.md) | 
| コンテナインスタンスのロール | このロールにより、EC2 インスタンスまたは外部インスタンスをクラスターに登録できます。 | タスクは Amazon EC2 インスタンスまたは外部インスタンスでホストされています。 | [Amazon ECS コンテナインスタンスの IAM ロール](instance_IAM_role.md) | 
| Amazon ECS Anywhere ロール | このロールにより、外部インスタンスが AWS API にアクセスできるようになります。 | タスクは外部インスタンスでホストされています。 | [Amazon ECS Anywhere IAM ロール](iam-role-ecsanywhere.md) | 
| Amazon ECS CodeDeploy ロール | このロールにより、CodeDeploy はサービスを更新できます。 | CodeDeploy のブルー/グリーンデプロイタイプを使用して、サービスをデプロイします。 | [Amazon ECS CodeDeploy IAM ロール](codedeploy_IAM_role.md) | 
| Amazon ECS EventBridge ロール | このロールにより、EventBridge はサービスを更新できます。 | EventBridge のルールとターゲットを使用してタスクをスケジュールします。 | [Amazon ECS EventBridge IAM ロール](CWE_IAM_role.md) | 
| Amazon ECS インフラストラクチャロール | このロールにより、Amazon ECS はクラスター内のインフラストラクチャリソースを管理できます。 |  [\[See the AWS documentation website for more details\]](http://docs.aws.amazon.com/ja_jp/AmazonECS/latest/developerguide/security-iam-roles.html) | [Amazon ECS インフラストラクチャ IAM ロール](infrastructure_IAM_role.md) | 

## タスクロール
<a name="security-iam-task-role"></a>

タスクロールを割り当てることをお勧めします。このロールは、それが実行されている Amazon EC2 インスタンスのロールと区別することができます。各タスクにロールを割り当てることは、最小権限アクセスの原則に沿っており、アクションとリソースをよりきめ細かく制御できます。

タスクロールをタスク定義に追加すると、Amazon ECS コンテナエージェントはタスク用の固有の認証情報 ID (例: `12345678-90ab-cdef-1234-567890abcdef`) を持つトークンを自動的に作成します。その後、このトークンとロール認証情報はエージェントの内部キャッシュに追加されます。エージェントは、コンテナ内の環境変数 `AWS_CONTAINER_CREDENTIALS_RELATIVE_URI` に認証情報 ID の URI (例: `/v2/credentials/12345678-90ab-cdef-1234-567890abcdef`) を入力します。

Amazon ECS コンテナエージェントの IP アドレスに環境変数を追加し、結果の文字列に対して `curl` コマンドを実行することで、コンテナ内から一時的なロール認証情報を手動で取得できます。

```
curl 169.254.170.2$AWS_CONTAINER_CREDENTIALS_RELATIVE_URI
```

予想される出力は次のようになります。

```
{
	"RoleArn": "arn:aws:iam::123456789012:role/SSMTaskRole-SSMFargateTaskIAMRole-DASWWSF2WGD6",
	"AccessKeyId": "AKIAIOSFODNN7EXAMPLE",
	"SecretAccessKey": "wJalrXUtnFEMI/K7MDENG/bPxRfiCYEXAMPLEKEY",
	"Token": "IQoJb3JpZ2luX2VjEEM/Example==",
	"Expiration": "2021-01-16T00:51:53Z"
}
```

新しいバージョンの AWS SDK では、AWS API 呼び出しを行うと、これらの認証情報が `AWS_CONTAINER_CREDENTIALS_RELATIVE_URI` 環境変数から自動的に取得されます。認証情報を更新する方法については、rePost の「[AWS 認証情報の更新](https://repost.aws/questions/QUgcf1EIOPS7GZNboeAiyO9Q/renewing-aws-credentials)」を参照してください。

出力には、シークレットアクセスキー ID で構成されるアクセスキーペアと、アプリケーションが AWS リソースにアクセスするために使用するシークレットキーが含まれます。また、認証情報が有効であることを確認するために AWS が使用するトークンも含まれています。デフォルトでは、タスクロールを使用してタスクに割り当てられた認証情報は6 時間有効です。その後は、Amazon ECS コンテナエージェントによって自動的にローテーションされます。

## タスク実行ロール
<a name="security-iam-roles-task-execution"></a>

タスク実行ロールは、ユーザーに代わって特定の AWS API アクションを呼び出すためのアクセス許可を Amazon ECS コンテナエージェントに付与するのに使用されます。たとえば、AWS Fargate を使用する場合、Fargate には Amazon ECR からイメージをプルして CloudWatch Logs にログを書き込むことができる IAM ロールが必要です。IAM ロールは、イメージプルシークレットなど、AWS Secrets Manager に保存されているシークレットをタスクが参照する場合にも必要です。

**注記**  
認証されたユーザーとしてイメージをプルする場合、[Docker Hub のプルレート制限](https://www.docker.com/pricing/resource-consumption-updates)が変更されても、影響を受ける可能性は低くなります。詳細については、[「コンテナインスタンスのプライベートレジストリの認証」](https://docs.aws.amazon.com/AmazonECS/latest/developerguide/private-auth-container-instances.html)を参照してください。  
Amazon ECR と Amazon ECR パブリックを使用することで、Docker によって課せられる制限を回避できます。Amazon ECR からイメージをプルすると、ネットワークのプル時間を短縮し、トラフィックが VPC を離れる際のデータ転送の変更を減らすのにも役立ちます。

**重要**  
Fargate を使用するときは、`repositoryCredentials` を使用してプライベートイメージレジストリの認証を行う必要があります。Amazon ECS コンテナエージェントの環境変数である `ECS_ENGINE_AUTH_TYPE` および `ECS_ENGINE_AUTH_DATA` を設定したり、Fargate でホストされているタスクの `ecs.config` ファイルを変更したりすることはできません。詳細については、「[タスクのプライベートレジストリの認証](https://docs.aws.amazon.com/AmazonECS/latest/developerguide/private-auth.html)」を参照してください。

## コンテナインスタンスのロール
<a name="security-iam-roles-ec2-container-instance"></a>

`AmazonEC2ContainerServiceforEC2Role` 管理 IAM ポリシーには以下のアクセス許可が含まれています。最小権限を付与する標準のセキュリティアドバイスに従って、`AmazonEC2ContainerServiceforEC2Role` 管理ポリシーをガイドとして使用できます。ユースケースの管理ポリシーで付与されているアクセス許可が不要な場合、カスタムポリシーを作成し、必要なアクセス許可のみを追加します。
+ `ec2:DescribeTags` – (オプション) Amazon EC2 インスタンスに関連付けられているタグをプリンシパルが記述できるようになります。このアクセス許可は、リソースタグの伝播をサポートするために Amazon ECS コンテナエージェントによって使用されます。詳細については、「[リソースのタグ付け方法](ecs-using-tags.md#tag-resources)」を参照してください。
+ `ecs:CreateCluster` – (任意) プリンシパルが Amazon ECS クラスターを作成できるようになります。このアクセス許可は、Amazon ECS コンテナエージェントによって `default` クラスターが存在しない場合、このクラスタを作成するために使用されます。
+ `ecs:DeregisterContainerInstance` – (任意) プリンシパルがクラスターから Amazon ECS コンテナインスタンスを登録解除できるようになります。Amazon ECS コンテナエージェントはこの API 操作を呼び出しませんが、このアクセス許可は後方互換性を確保するために維持されます。
+ `ecs:DiscoverPollEndpoint` – (必須) このアクションは、Amazon ECS コンテナエージェントが更新のポーリングに使用するエンドポイントを返します。
+ `ecs:Poll` – (必須) Amazon ECS コンテナエージェントが Amazon ECS コントロールプレーンと通信し、タスクの状態の変更を報告できるようになります。
+ `ecs:RegisterContainerInstance` – (必須) プリンシパルがコンテナインスタンスをクラスターに登録できるようになります。このアクセス許可は、Amazon ECS コンテナエージェントが Amazon EC2 インスタンスをクラスターに登録し、リソースタグの伝播をサポートするために使用されます。
+ `ecs:StartTelemetrySession` – (任意) Amazon ECS コンテナエージェントが Amazon ECS コントロールプレーンと通信し、各コンテナおよびタスクのヘルス情報とメトリクスをレポートできるようになります。

  このアクセス許可は必須ではありませんが、コンテナインスタンスのメトリクスがスケールアクションを開始できるようにし、ヘルスチェックコマンドに関連するレポートを受信できるようにするために、これを追加することをお勧めします。
+ `ecs:TagResource` – (任意) Amazon ECS コンテナエージェントが、作成時にクラスターにタグ付けしたり、コンテナインスタンスがクラスターに登録されたときにタグ付けしたりできるようになります。
+ `ecs:UpdateContainerInstancesState` — プリンシパルが Amazon ECS コンテナインスタンスのステータスを変更できるようにします。このアクセス許可は、スポットインスタンスのドレイン用に Amazon ECS コンテナエージェントによって使用されます。
+ `ecs:Submit*` – (必須) これには API アクション `SubmitAttachmentStateChanges`、`SubmitContainerStateChange`、および `SubmitTaskStateChange` が含まれています。これらは、Amazon ECS コンテナエージェントによって使用され、各リソースの状態変化を Amazon ECS コントロールプレーンに報告します。`SubmitContainerStateChange` アクセス許可は、Amazon ECS コンテナエージェントによって使用されなくなりますが、後方互換性を確保するために維持されます。
+ `ecr:GetAuthorizationToken` – (オプション) プリンシパルに認可トークンの取得を許可します。認可トークンは IAM 認証情報を表し、IAM プリンシパルによってアクセスされる Amazon ECR レジストリへのアクセスに使用できます。受け取る認可トークンは 12 時間有効です。
+ `ecr:BatchCheckLayerAvailability` – (任意) コンテナイメージが Amazon ECR プライベートリポジトリにプッシュされると、各イメージレイヤーに対してすでにプッシュされているかどうかが確認されます。その場合、そのイメージレイヤーはスキップされます。
+ `ecr:GetDownloadUrlForLayer` – (任意) コンテナイメージが Amazon ECR プライベートリポジトリからプルされると、この API が、まだキャッシュされていない各イメージレイヤーに対して 1 回呼び出されます。
+ `ecr:BatchGetImage` – (任意) コンテナイメージが Amazon ECR プライベートリポジトリからプルされると、この API が 1 回呼び出されてイメージマニフェストが取得されます。
+ `logs:CreateLogStream` – (任意) プリンシパルが、指定したロググループの CloudWatch Logs ログストリームを作成できるようになります。
+ `logs:PutLogEvents` – (任意) プリンシパルが、指定したログストリームにログイベントのバッチをアップロードできるようになります。

## サービスリンクロール
<a name="security-iam-roles-service-linked"></a>

Amazon ECS のサービス連動ロールを使用して、Amazon ECS サービスに他のサービス API を代理で呼び出す許可を付与できます。Amazon ECS には、ネットワークインターフェイスの作成と削除、ターゲットグループへのターゲットの登録と登録解除を行う許可が必要です。また、スケーリングポリシーの作成と削除に必要な許可も必要です。これらの許可は、サービスにリンクされたロールによって付与されます。このロールは、サービスを初めて使用するときに、ユーザーに代わって作成されます。

**注記**  
サービスにリンクされたロールを誤って削除してしまった場合は、ロールを再作成できます。手順については、[「サービスにリンクされたロールの作成」](https://docs.aws.amazon.com/AmazonECS/latest/developerguide/using-service-linked-roles.html#create-service-linked-role)を参照してください。

## ロールの推奨事項
<a name="security-iam-roles-recommendations"></a>

タスクの IAM ロールとポリシーを設定するときは、以下を行うことをお勧めします。

### Amazon EC2 メタデータへのアクセスをブロックする
<a name="security-iam-roles-recommendations-ec2-metadata"></a>

Amazon EC2 インスタンスでタスクを実行する場合、Amazon EC2 メタデータへのアクセスをブロックして、それらのインスタンスに割り当てられたロールをコンテナが継承しないようにすることを強くお勧めします。アプリケーションが AWS API アクションを呼び出す必要がある場合は、代わりに IAM ロールをタスクに使用してください。

**ブリッジ**モードで実行されているタスクが Amazon EC2 メタデータにアクセスしないようにするには、次のコマンドを実行するか、インスタンスのユーザーデータを更新します。インスタンスのユーザーデータを更新する方法の詳細については、この[AWS サポート記事](https://aws.amazon.com/premiumsupport/knowledge-center/ecs-container-ec2-metadata/)を参照してください。タスク定義ブリッジモードについて詳しくは、「[タスク定義ネットワークモード](https://docs.aws.amazon.com/AmazonECS/latest/developerguide/task_definition_parameters.html#network_mode)」を参照してください。

```
sudo yum install -y iptables-services; sudo iptables --insert FORWARD 1 --in-interface docker+ --destination 169.254.169.254/32 --jump DROP
```

再起動後もこの変更が持続するようにするには、Amazon マシンイメージ (AMI) 固有の次のコマンドを実行します。
+ Amazon Linux 2

  ```
  sudo iptables-save | sudo tee /etc/sysconfig/iptables && sudo systemctl enable --now iptables
  ```
+ Amazon Linux

  ```
  sudo service iptables save
  ```

`awsvpc` ネットワークモードを使用するタスクでは、`/etc/ecs/ecs.config` ファイル内の環境変数 `ECS_AWSVPC_BLOCK_IMDS` を `true` に設定します。

`host` ネットワーク内で実行されているコンテナが Amazon EC2 メタデータにアクセスできないように、`ecs-agent config` ファイルの `ECS_ENABLE_TASK_IAM_ROLE_NETWORK_HOST` 変数を `false` に設定する必要があります。

### `awsvpc` ネットワークモードを使用する
<a name="security-iam-roles-recommendations-awsvpc-networking-mode"></a>

`awsvpc` ネットワークモードを使用して、異なるタスクの間、またはタスクと Amazon VPC 内で実行される他のサービスとの間のトラフィックの流れを制限します。これにより、セキュリティの追加レイヤーが追加されます。`awsvpc` ネットワークモードは、Amazon EC2 で実行されるタスクをタスクレベルでネットワーク分離します。これは AWS Fargate のデフォルトモードであり、タスクにセキュリティグループを割り当てるのに使用できる唯一のネットワークモードです。

### 最終アクセス時間情報を使用してロールを絞り込む
<a name="security-iam-roles-recommendations-iam-access-advisor-refine-roles"></a>

一度も使用されていないか、しばらく使用されていないアクションは、削除することをお勧めします。そうすることで、望ましくないアクセスが発生するのを防ぐことができます。これを行うには、IAM によって提供される最終アクセス時間情報を確認し、使用されたことがない、または最近使用されていないアクションを削除します。これを行うには、次のステップに従ってください。

次のコマンドを実行して、参照されたポリシーの最終アクセス情報を示すレポートを生成します。

```
aws iam generate-service-last-accessed-details --arn arn:aws:iam::123456789012:policy/ExamplePolicy1
```

出力に表示されていた `JobId` を使用して、次のコマンドを実行します。これを実行すると、レポートの結果を表示できます。

```
aws iam get-service-last-accessed-details --job-id 98a765b4-3cde-2101-2345-example678f9
```

詳細については、「[最終アクセス情報を使用して AWS のアクセス許可を調整する](https://docs.aws.amazon.com/IAM/latest/UserGuide/access_policies_last-accessed.html)」を参照してください。

### AWS CloudTrail に不審なアクティビティがないか監視する
<a name="security-iam-roles-recommendations-cloudtrail-monitoring"></a>

AWS CloudTrail に不審なアクティビティがないか監視することができます。ほとんどの AWS API 呼び出しは AWS CloudTrail イベントとして記録されます。これらは AWS CloudTrail Insights によって分析され、`write` API 呼び出しに関連する疑わしい動作があればアラートが表示されます。これには、呼び出しの急増が含まれる場合があります。これらのアラートには、異常なアクティビティが発生した時間や、API に寄与した上位のアイデンティティ ARN などの情報が含まれます。

IAM ロールが割り当てられているタスクが実行するアクションは、AWS CloudTrail でイベントの `userIdentity` プロパティを調べることで特定できます。次の例では、`arn` に引き受けたロールの名前 `s3-write-go-bucket-role` が含まれ、その後にタスクの名前 `7e9894e088ad416eb5cab92afExample` が続きます。

```
"userIdentity": {
    "type": "AssumedRole",
    "principalId": "AROA36C6WWEJ2YEXAMPLE:7e9894e088ad416eb5cab92afExample",
    "arn": "arn:aws:sts::123456789012:assumed-role/s3-write-go-bucket-role/7e9894e088ad416eb5cab92afExample",
    ...
}
```

**注記**  
ロールを引き受けるタスクが Amazon EC2 コンテナインスタンスで実行されると、リクエストは Amazon ECS コンテナエージェントによって、`/var/log/ecs/audit.log.YYYY-MM-DD-HH` フォーマットのアドレスにあるエージェントの監査ログに記録されます。詳細については、「[タスクの IAM ロール ログ](https://docs.aws.amazon.com/AmazonECS/latest/developerguide/logs.html#task_iam_roles-logs)」 と 「[証跡のインサイトイベントの記録](https://docs.aws.amazon.com/awscloudtrail/latest/userguide/logging-insights-events-with-cloudtrail.html)」を参照してください。