AQ Tech Blog

オブザーバビリティに対応したContainer Insightsを活用したECSコンテナの自動アラーム作成

作成者: yasuhiro.kawai|2025年01月20日

概要

クラウドインテグレーション部クラウドソリューション2課の
川井です。

2024年12月2日から6日に開催されたAWS re:Invent 2024の中でも、特に注目を集めたアップデートは、Amazon Aurora DSQL サーバーレス分散SQLデータベースだったと感じています。
これにより、これまでグローバルに分散し強整合性を備えたマルチリージョンのデータベースといえば、Google CloudのCloud Spannerでしたが、 AWSでも利用可能になるうということで、大きな話題となったと思います。

しかし、私個人として注目したのは、今回の記事でご紹介する、Amazon CloudWatch Container Insights(以降、Container Insights)に関するアップデートです。
これにより、Amazon EC2やAmazon Fargateで実行されるAmazon Elastic Container Service(以降、ECS)のオブザーバビリティが大幅に強化されました。

こちらのアップデートの詳細内容は公式ドキュメントをご覧ください。
Amazon CloudWatch Container Insights が Amazon ECS のオブザーバビリティを強化
Container Insights with enhanced observability now available in Amazon ECS

オブザーバビリティが強化されたContainer Insightsの導入により、クラスターからコンテナレベルまでの詳細なメトリクスが提供され、問題の切り分けやトラブルシューティングが迅速に行えるようになりました。

特に、コンテナレベルでのメトリクス収集機能は画期的です。これまでECSでは、クラスターやサービスレベルのメトリクスは記録できましたが、コンテナ単位のメトリクスを記録するには、メトリクスフィルターを作成し情報を収集する必要がありました。

今回のアップデートによって、そのような手間が不要になり、さらにコンテナーによって使用されているCPUユニットの合計の割合をコンテナ単位で記録できるようになった点は、運用設定効率の向上につながる大きな利点です。

そのため、この新しい機能を活用して、ECSのメトリクスアラートの自動作成をしてみたいと思います。

構成概要

メトリクスアラートの作成には、「オブザーバビリティが強化されたContainer Insights」によって追加されたメトリクスを活用し、コンテナ単位のCPUユニット合計の割合を基にしたAmazon CloudWatch Alarmを作成します。

また、このアラームの作成は、コンテナの起動に連動してアラームが自動で作成する構成で進めていきます。
具体的には、以下の3つのステップで進めていきます。

※ECSのクラスターやタスク定義などは既に作成されたものを使い進めていきますので、クラスターなどの作成はステップから省略していますので、ご了承ください。

1. Container Insightsを有効化
先ず、ECSクラスターで「オブザーバビリティが強化されたContainer Insights」を有効化し、コンテナ単位での詳細なメトリクス収集を出来るようにします。
これにより、クラスターからコンテナレベルまでの可視性が向上し、個別のコンテナに対するリソース使用状況の監視が可能になります。

2. アラーム作成の自動化
次に、コンテナの起動イベントをトリガーとして、アラームを自動的に作成する仕組みを構築します。
このプロセスには以下の2つの主要な構成要素を含みます。

○ Amazon EventBridgeを利用したトリガー設定
ECSでコンテナが起動した際に発生するイベントをAmazon EventBridge(以降、EventBrige)で検知します。このイベントには、対象となるコンテナの情報が含まれており、これを後続の処理に渡します。

○ AWS Step Functionsによるアラーム作成
EventBridgeで検知したイベントをAWS Step Functions(以降、Step Functions)に渡し、Amazon CloudWatchのPutMetricAlarm操作を実行してアラームを作成します。
この際、CPUユニットの使用割合が指定した閾値を超えた場合に通知を行う条件を設定します。

3. CPU使用率メトリクスの確認
最後に、コンテナ単位で記録されるCPUユニットの使用割合のメトリクスを確認します。Container Insightsによって収集される詳細なメトリクスを活用し、コンテナの状態やリソース消費状況を把握します。コンテナ単位のメトリクスを活用してアラームが適切に作成できているかを確認します。


これらのステップを通じて、コンテナが起動したタイミングでアラームが作成される構成を実装していきます。

Container Insightsを有効化

先ずは「オブザーバビリティが強化されたContainer Insights」を有効化していきます。
ECSのコンソール画面で作成しています既存のクラスターを選択して、以下画像の赤枠の「クラスターを更新」へと進めていきます。

現状は、Amazon CloudWatchモニタリングの箇所を見て頂くと分かりますが、Container Insights自体は有効化しています。
また、タスクは実行していませんのでコンテナは1つも起動していない状態です。

更新画面に進んでいきますと、新たに「オブザーバビリティが強化された Container Insights」という項目が、追加されていますので選択して更新します。

更新すると、Amazon CloudWatchモニタリングの箇所が「オブザーバビリティが強化されたContainer Insights」に変更されます。

これで、「オブザーバビリティが強化されたContainer Insights」の有効化が完了しました。
この状態でコンテナを起動すればコンテナ単位のメトリクスが記録されていきます。

アラーム作成の自動化(Step Functions作成)

EventBridgeのターゲット先であるStep Functionsから作成していくのですが、先ずは、Step Functionsを作成する上で必要なリソースを作成していきます。

▢ IAMロール作成

※ロールの権限は、本来最小権限の原則(Least Privilege Principle)に従って付与することが推奨されています。
これはセキュリティのベストプラクティスとして、必要以上の権限を避けることでリスクを最小限に抑えるためです。
ただし、本記事では検証を目的としているため、簡便性を優先し、より広い権限を一時的に付与しています。
実運用の際には、必ず必要最小限の権限でロールを設定して頂ければと思います。

Step Functionsで設定するIAMロールおよびIAMポリシーには、以下の設定を適用します。
なお、名前などのその他の設定については、各自の判断で自由に設定してください。

◦ IAMロール
{
"Version": "2012-10-17",
"Statement": [
{
"Sid": "",
"Effect": "Allow",
"Principal": {
"Service": "states.amazonaws.com"
},
"Action": "sts:AssumeRole"
}
]
}
◦ IAMポリシー
{
"Version": "2012-10-17",
"Statement": [
{
"Action": [
"lambda:InvokeFunction",
"cloudwatch:*",
"logs:*"
],
"Effect": "Allow",
"Resource": "*"
}
]
}

ポリシーには、CloudWatch Alarm作成権限と、CloudWatch Logsへのログ格納権限を設定しています。

また、Lambdaの実行権限も含まれていますが、本自動作成機能には直接関係がないため、必要不可欠な権限ではありません。
これはコンテナ停止(削除)時にコンテナが起動した際に作成されたアラームを削除する際に必要とした権限となります。

▢ Amazon SNS作成

※アクセスポリシーの権限も、本来最小権限の原則(Least Privilege Principle)に従って付与することが推奨されています。
本記事では検証を目的としているため、簡便性を優先し、より広い権限を一時的に付与しています。

続いて、Amazon Cloudwatch Alarmのアクションに設定するAmazon SNSの作成します。

◦ トピック作成

Amazon SNSのコンソール画面でトピックの作成へと進んでいきます。
メッセージの順序保証や重複削除は必要ないため、トピックのタイプはスタンダードで設定します。
また、その他の設定もデフォルトのままで問題ありませんので、そのままで作成していきます。

◦ サブスクリプションの設定

トピックを作成した後は、サブスクリプションの設定をしていきます。
今回の設定では、プロトコルをEメールでエンドポイントは自分のメールアドレスを設定していきます。

▢ Amazon Cloudwatch Logs作成

※ログの格納先であるAmazon Cloudwatch Logsの作成は省略します。

▢ Step Functions作成

必要なリソースを作成しましたので、Step Functionsのコンソール画面を開き、「ステートマシン」→「ステートマシンの作成」の順に進みます。
テンプレート選択画面で「空白(Blank)」を選択します。

選択しますと、以下のようなデザイン画面のタブが表示されますので、次にアクション一覧から「PutMetricAlarm」を選択し、矢印の位置までドラッグ&ドロップします。


設定画面のタブに移動して、以下の設定します。

ステートマシン名: test-create-alarm(任意の名前)
タイプ: 標準
実行ロール: 作成したロールを指定
ログレベル: ALL(ログ記録はすべてのイベントで有効)
CloudWatch ロググループ: 作成したロググループを指定

ログレベルは、各自で自由に設定して頂いて問題ありません。

最後にコード画面のタブに移動しましたら、以下のコードを入力してステートマシンの作成を選択していきます。

「オブザーバビリティが強化されたContainer Insights」によって収集されるコンテナ単位のCPUユニットの合計の割合のメトリクスは「ContainerCpuUtilization」として記録されます。
そして、名前空間には「ECS/ContainerInsights」が使用されますので、これらを指定しています。

また、Dimensionsには「ContainerName」 「TaskId」 「ClusterName」 「TaskDefinitionFamily」の値が必要になります。
以下の「オブザーバビリティが強化されたContainer Insights」で記録されたメトリクス画面を見て頂くとお分かり頂けますが、厳密には「TaskDefinitionFamily」ではなく「ServiceName」でも問題ありません。

なお、Resourceの箇所はAmazon CloudWatch Alarmを作成するために必要な設定ですので変更はできません。
一方で「AlarmName」 「Statistic」 「Threshold」 などの設定については、自由に設定して頂いて問題ありません。
そして「AlarmActions」については、作成したAmazon SNSのARNを指定します。

※AlarmNameやDimensionsなど、イベントデータに基づいた動的な値の取得方法は、Amazon ECS Fargateのタスク状態変更に伴うイベントの詳細については、以下の公式ドキュメントをご参照ください。
Amazon ECS task state change events

※Step Functionsで使用する組み込み関数については以下の公式ドキュメントをご参照ください。
Step Functions ワークフローの Amazon States Language の組み込み関数

{
"StartAt": "CreateCloudWatchAlarm",
"States": {
"CreateCloudWatchAlarm": {
"Type": "Task",
"Resource": "arn:aws:states:::aws-sdk:cloudwatch:putMetricAlarm",
"Parameters": {
"AlarmName.$": "States.Format('test-app-container-{}', $.detail.containers[0].runtimeId)",
"MetricName": "ContainerCpuUtilization",
"Namespace": "ECS/ContainerInsights",
"Statistic": "Average",
"Period": 300,
"EvaluationPeriods": 1,
"Threshold": 80,
"ComparisonOperator": "GreaterThanOrEqualToThreshold",
"Dimensions": [
{
"Name": "ContainerName",
"Value.$": "$.detail.containers[0].name"
},
{
"Name": "TaskId",
"Value.$": "States.ArrayGetItem(States.StringSplit($.detail.taskArn, '/'), 2)"
},
{
"Name": "ClusterName",
"Value.$": "States.ArrayGetItem(States.StringSplit($.detail.clusterArn, '/'), 1)"
},
{
"Name": "TaskDefinitionFamily",
"Value.$": "States.ArrayGetItem(States.StringSplit(States.ArrayGetItem(States.StringSplit($.detail.taskDefinitionArn, '/'), 1), ':'), 0)"
}
],
"AlarmActions": [
"arn:aws:sns:ap-northeast-1:1234567890:test-ecs-alarm"
]
},
"End": true
}
}
}

これで、Step Functionsの作成は完了しました。続いてEventBridgeを作成します。


アラーム作成の自動化(EventBridge作成)

次に、コンテナの起動イベントをトリガーとするEventBridgeを作成していきます。先ずは、IAMロールの作成です。

▢ IAMロール作成

※ロールの権限については、Step Functionsの所で前述していますが「最小権限の原則(Least Privilege Principle)」に従うことが推奨されます。
本記事では検証を目的としているため、簡便性を優先し、より広い権限を一時的に付与しています。実運用の際には、必ず必要最小限の権限でロールを設定頂くようお願い致します。

EventBridgeで設定するIAMロールおよびIAMポリシーには、以下の設定を適用します。
なお、名前などのその他の設定については、各自の判断で自由に設定してください。

◦ IAMロール
{
"Version": "2012-10-17",
"Statement": [
{
"Sid": "",
"Effect": "Allow",
"Principal": {
"Service": "events.amazonaws.com"
},
"Action": "sts:AssumeRole"
}
]
}
◦ IAMポリシー
{
"Version": "2012-10-17",
"Statement": [
{
"Action": [
"states:*"
],
"Effect": "Allow",
"Resource": "*"
}
]
}

ポリシーには、Step Functionsが実行できる権限を設定しています。


▢ イベントルールの作成

IAMロールを作成しましたので、続いてはイベントルールを作成していきます。
EventBridgeのコンソール画面で「ルール」→「ルール作成」と進んでいきます。
ルールの詳細を定義画面に進みますので、以下の設定を行います。

名前: ecs-events-launch(任意の名前)
説明: 必要あれば記載する
イベントパス: default
ルールタイプ: イベントパターンを持つルール

続いて、イベントパターンの構築画面では、以下のイベントパターンを入力します。

"desiredStatus"と"lastStatus"の起動状態のステータスが「RUNNING」になったイベントを検知して起動するイベントパターンを入力しています。
"clusterArn"は自身のクラスターのARNに変更してください。

{
"detail": {
"clusterArn": ["arn:aws:ecs:ap-northeast-1:123456789012:cluster/test-fargate-cluster"],
"desiredStatus": ["RUNNING"],
"lastStatus": ["RUNNING"]
},
"detail-type": ["ECS Task State Change"],
"source": ["aws.ecs"]
}

ターゲットを選択画面では、ターゲットには作成したStep Functionsを指定します。
そして、実行ロールも作成したIAMロールを指定して「次へ」と進みます。


後は、タグの設定画面と作成画面と進んで、設定内容が問題なければイベントルールを作成します。


イベントルールの作成が完了したら、コンテナを起動してCPU使用率のメトリクスでアラームが作成されることを確認していきます。

CPU使用率メトリクスの確認

先ず、コンテナを起動していきます。ECSコンソール画面でクラスターを選択して、サービスの更新へと進んでいきます。
ここで必要なタスクを2と設定して、2台のコンテナを起動していきます。

コンテナが2台実行中となりました。各タスク番号は以下になります。

4057429d689d0a139b59d47fb8c2a5f
e3c7263c4c844755935e1a3e3b8665ab

コンテナが起動しましたので、設定したEventBrigeとStep functionsが起動したのか確認してみます。

先ずは、EventBrigeのモニタリング画面で確認してみますと、18時50分前後にMatchしているEventが2つ確認できます。

そして、Step Functionsの実行画面も確認してみますと、こちらも18時50分前後に2つ実行が成功してるステートマシンがあります。

両方の起動を確認できましたので、アラームが作成されているか確認します。
CloudWatchのアラームを確認したところ、2つのアラームが作成されています。
作成された時間も18時53分前後と、Step Functionsの実行後のタイミングであることから、問題ないように思われます。

では、Container Insightsでコンテナ単位のメトリクスを確認していきます。

Container Insightsの画面を確認すると、クラスターやサービスと共に、コンテナの使用率という項目が確認できます。
アラームが2つ作成されていることが、こちらの画面から確認することができます。

コンテナの箇所を選択すると、コンテナ単位の詳細情報が確認できます。赤枠のコンテナ名を確認すると先程実行状態になったタスクのタスク番号とコンテナ名のタスク番号の箇所が一致しています。

補足ですが、コンテナ名は test-app-containerにruntimeIDを組み合わせた名前で設定しています。そして、runtimeIDはタスク番号とコンテナ番号の組み分わせで構成されています。
runtimeIDは一意な番号となります。そのため、アラーム名にruntimeIDを入れることで、どのコンテナのアラームなのか分かるようになるので、このような設定にしています。

また、クラスターの箇所を選択すればクラスター単位の詳細情報が確認することができます。

では、最後にコンテナ単位のCPUユニット合計の割合を活用してアラームが適切に作成できているかを確認します。
アラーム自体は問題なく作成できていることは確認できてはいますが、アラーム画面で再度確認します。アラーム名を確認すると、先程実行状態になったタスクのタスク番号とアラーム名のタスク番号の箇所が一致していますので、コンテナ単位のアラームが問題なく作成されていることが確認できました。
条件箇所もContainerCpuUtilizationを使っているので、CPUユニット合計の割合を活用しています。

データが取得できているかどうかも確認してみます。アラームの1つを選択して確認すると、少し分かりずらいですが、ContainerCpuUtilizationという青い線が確認できますので、データの取得もできていると思われます。


以上、オブザーバビリティに対応したContainer Insightsを活用してECSコンテナの自動アラームを作成してみました。

※アラームで設定したContainerCpuUtilizationメトリクスですが、公式ドキュメントに以下のように記載されています。
Amazon ECS Container Insights with enhanced observability metrics

使用しているディメンションセットによって指定されたリソース内のコンテナーによって使用されているCPUユニットの合計割合。
このメトリックは、タスク定義でCPU予約が定義されているコンテナに対してのみ収集されます。

単位: パーセント

CPUユニットの合計割合をパーセント単位で取得しており、これはCPU使用率のメトリクスとほぼ同等の値を示していると考えられます。
ただし、完全に一致するかどうかは保証できませんので、設定時には必ず詳細を確認いただけますようお願い致します。

まとめ

今回は、12月にアップデートされたばかりのContainer Insightsを使用して、コンテナ単位のメトリクス取得の容易さを実感しました。
やはり、コンテナ単位で詳細なメトリクスが簡単に取得できるようになった点は、運用効率を飛躍的に向上させる革新的な機能だと感じます。
今後もこの機能を活用し、さらに効率的で透明性の高い運用を目指していきたいと思います。

では、また別の記事を執筆しますので、引き続きよろしくお願いいたします。
ありがとうございました。


クラウドインテグレーション部
クラウドソリューション2課
川井 康敬