Docker on EC2環境にcAdvisorを導入してコンテナメトリクス収集【+ CloudWatchメトリクス出力も】

Docker on EC2環境にcAdvisorを導入してコンテナメトリクス収集【+ CloudWatchメトリクス出力も】

2025.11.13

cAdvisor (Container Advisor) はコンテナ監視で活用できるツールです。 稼働中の各コンテナごとのリソース使用状況やパフォーマンス特性を収集・処理する常駐デーモンとして動作します。

今回 cAdvisor を Docker on EC2 環境に導入する機会があったので、実施した手順を本ブログに残します。
また、収集された cAdvisor 情報を CloudWatchメトリクスへ出力するように、 CloudWatchエージェントを構成してみました。 その内容も本記事で紹介します。

前提

今回は Docker on EC2 の題材として 「 Dify コミュニティ版 をデプロイしたEC2インスタンス 」を使います。 Dify はノーコードでAIエージェントを開発できるツールです。 コミュニティ版では Docker Compose によるデプロイ が可能です。

以下のような Docker on EC2 環境が既にあることを前提とします。

sc-2025-11-13_07-21910
前提とするAWS環境/リソース

cadvisor を導入する

Dify は用意されている docker-compose.yaml を立ち上げることで稼働しています。

Dify動作確認
ls docker-compose.yaml -l
# -rw-r--r--. 1 ec2-user ec2-user 66014 Nov 12 23:29 docker-compose.yaml

docker compose up -d
# [+] Running 10/10
#  ✔ Container docker-redis-1          Running
#  ✔ Container docker-db-1             Healthy
#  ✔ Container docker-ssrf_proxy-1     Running
#  ✔ Container docker-sandbox-1        Running
#  ✔ Container docker-plugin_daemon-1  Running
#  ✔ Container docker-worker-1         Running
#  ✔ Container docker-web-1            Running
#  ✔ Container docker-worker_beat-1    Running
#  ✔ Container docker-api-1            Running
#  ✔ Container docker-nginx-1          Running

docker ps --format "table {{.Image}}\t{{.Status}}\t{{.Ports}}"
# IMAGE                                       STATUS                   PORTS
# nginx:latest                                Up 4 minutes             0.0.0.0:80->80/tcp, :::80->80/tcp, 0.0.0.0:443->443/tcp, :::443->443/tcp
# langgenius/dify-plugin-daemon:0.4.0-local   Up 4 minutes             0.0.0.0:5003->5003/tcp, :::5003->5003/tcp
# langgenius/dify-api:1.10.0-rc1              Up 4 minutes             5001/tcp
# langgenius/dify-api:1.10.0-rc1              Up 4 minutes             5001/tcp
# langgenius/dify-api:1.10.0-rc1              Up 4 minutes             5001/tcp
# ubuntu/squid:latest                         Up 5 minutes             3128/tcp
# redis:6-alpine                              Up 5 minutes (healthy)   6379/tcp
# langgenius/dify-web:1.10.0-rc1              Up 5 minutes             3000/tcp
# langgenius/dify-sandbox:0.2.12              Up 5 minutes (healthy)
# postgres:15-alpine                          Up 5 minutes (healthy)   5432/tcp

今回、cAdvisor 導入では新たに docker-compose.override.yaml を作成します。docker-compose.override.yaml は 複数のComposeファイルを使うための機能 で、既存の docker-compose.yaml を上書きせずに設定を追加・変更できます。これにより、元の Dify の構成ファイルはそのままに、cAdvisor コンテナの定義だけを追加できます。[1]

docker-compose.yaml と同じディレクトリに docker-compose.override.yaml を作成します。 コンテナ設定の記載は google/cadvisor #QuickStart - GitHub を参考にしています。

docker-compose.override.yaml
services:
  cadvisor:
    # https://github.com/google/cadvisor/releases からバージョンを確認する
    image: gcr.io/cadvisor/cadvisor:v0.52.1
    container_name: cadvisor
    restart: unless-stopped
    ports:
      - "8080:8080"
    volumes:
      - /:/rootfs:ro
      - /var/run:/var/run:ro
      - /sys:/sys:ro
      - /var/lib/docker/:/var/lib/docker:ro
      - /dev/disk/:/dev/disk:ro
    devices:
      - /dev/kmsg:/dev/kmsg
    privileged: true

再度、 docker compose up -d を実行します。

cAdvisorコンテナ起動
docker compose up -d
# [+] Running 6/6
#  ✔ cadvisor Pulled
#    ✔ 44cf07d57ee4 Pull complete
#    ✔ 8e1b64a25f57 Pull complete
#    ✔ 9f163ef62c30 Pull complete
#    ✔ 4f4fb700ef54 Pull complete
#    ✔ b7db0b79d658 Pull complete
# [+] Running 11/11
#  ✔ Container docker-ssrf_proxy-1     Running
#  ✔ Container docker-redis-1          Running
#  ✔ Container docker-db-1             Running
#  ✔ Container docker-sandbox-1        Running
#  ✔ Container docker-web-1            Running
#  ✔ Container cadvisor                Created
#  ✔ Container docker-plugin_daemon-1  Running
#  ✔ Container docker-worker-1         Running
#  ✔ Container docker-api-1            Running
#  ✔ Container docker-nginx-1          Running
#  ✔ Container docker-worker_beat-1    Running

動作確認

healthz エンドポイントへアクセスして、okが返ってきたら正常稼働しています。

healthzエンドポイント確認
curl http://localhost:8080/healthz
# ok

metrics からコンテナ関連のメトリクスを直接取得できます。

メトリクス取得例
curl -s http://localhost:8080/metrics | grep container_cpu_usage_seconds_total | head -n5
# # HELP container_cpu_usage_seconds_total Cumulative cpu time consumed in seconds.
# # TYPE container_cpu_usage_seconds_total counter
# container_cpu_usage_seconds_total{container_label_com_docker_compose_config_hash="",container_label_com_docker_compose_container_number="",container_label_com_docker_compose_depends_on="",container_label_com_docker_compose_image="",container_label_com_docker_compose_oneoff="",container_label_com_docker_compose_project="",container_label_com_docker_compose_project_config_files="",container_label_com_docker_compose_project_working_dir="",container_label_com_docker_compose_service="",container_label_com_docker_compose_version="",container_label_maintainer="",container_label_org_opencontainers_image_created="",container_label_org_opencontainers_image_description="",container_label_org_opencontainers_image_licenses="",container_label_org_opencontainers_image_ref_name="",container_label_org_opencontainers_image_revision="",container_label_org_opencontainers_image_source="",container_label_org_opencontainers_image_title="",container_label_org_opencontainers_image_url="",container_label_org_opencontainers_image_version="",cpu="total",id="/",image="",name=""} 685.146402 1762992177261
# container_cpu_usage_seconds_total{container_label_com_docker_compose_config_hash="",container_label_com_docker_compose_container_number="",container_label_com_docker_compose_depends_on="",container_label_com_docker_compose_image="",container_label_com_docker_compose_oneoff="",container_label_com_docker_compose_project="",container_label_com_docker_compose_project_config_files="",container_label_com_docker_compose_project_working_dir="",container_label_com_docker_compose_service="",container_label_com_docker_compose_version="",container_label_maintainer="",container_label_org_opencontainers_image_created="",container_label_org_opencontainers_image_description="",container_label_org_opencontainers_image_licenses="",container_label_org_opencontainers_image_ref_name="",container_label_org_opencontainers_image_revision="",container_label_org_opencontainers_image_source="",container_label_org_opencontainers_image_title="",container_label_org_opencontainers_image_url="",container_label_org_opencontainers_image_version="",cpu="total",id="/init.scope",image="",name=""} 3.937916 1762992130750
# container_cpu_usage_seconds_total{container_label_com_docker_compose_config_hash="",container_label_com_docker_compose_container_number="",container_label_com_docker_compose_depends_on="",container_label_com_docker_compose_image="",container_label_com_docker_compose_oneoff="",container_label_com_docker_compose_project="",container_label_com_docker_compose_project_config_files="",container_label_com_docker_compose_project_working_dir="",container_label_com_docker_compose_service="",container_label_com_docker_compose_version="",container_label_maintainer="",container_label_org_opencontainers_image_created="",container_label_org_opencontainers_image_description="",container_label_org_opencontainers_image_licenses="",container_label_org_opencontainers_image_ref_name="",container_label_org_opencontainers_image_revision="",container_label_org_opencontainers_image_source="",container_label_org_opencontainers_image_title="",container_label_org_opencontainers_image_url="",container_label_org_opencontainers_image_version="",cpu="total",id="/inspectorssmplugin",image="",name=""} 0.179176 1762992154210

一応 ブラウザ からも確認できます。

sc-2025-11-13_09-9805
{IPアドレス}:8080/docker 画面

cAdvisor が提供するメトリクスの詳細は こちら(docs/storage/prometheus.md) で確認できます。 CPU使用率、メモリ使用量、ディスクI/O、ネットワーク統計など、80種類以上のコンテナメトリクスが用意されています。

CloudWatchメトリクスへ出力してみる

導入したcAdvisorのメトリクスをCloudWatch Agentで収集し、 CloudWatchメトリクスへ出力してみます。 cAdvisorのメトリクス可視化では Prometheus + Grafana の組み合わせがよく使われますが、 今回は既存のAWS環境に統合しやすいよう、CloudWatch Agent経由でCloudWatchメトリクスへ出力する構成を採用しました。

CloudWatch Agent のインストール

前提として、EC2インスタンスのIAMロールには AmazonSSMManagedInstanceCore および CloudWatchAgentServerPolicy をアタッチしておきます。

CloudShell にて以下コマンドを実行し、CloudWatch Agent をインストールしました。

CloudWatch Agentインストール
instance_id=i-0ff1b565ac9eb1133
aws ssm send-command --output yaml \
  --instance-ids "${instance_id}" \
  --document-name "AWS-ConfigureAWSPackage" \
  --parameters name="AmazonCloudWatchAgent",action="Install"

Prometheusスクレイピング設定の作成

CloudWatch Agent が cAdvisor からメトリクスをスクレイピングするための設定ファイルを作成します。 /opt/aws/amazon-cloudwatch-agent/etc/prometheus.yaml を新規作成しました。

/opt/aws/amazon-cloudwatch-agent/etc/prometheus.yaml
global:
  scrape_interval: 60s
  scrape_timeout: 10s
scrape_configs:
  - job_name: cadvisor
    static_configs:
      - targets:
          - localhost:8080
    relabel_configs:
      - target_label: 'instance'
        replacement: 'test-dify-instance'

このファイルは Configuration - Prometheus に準拠して作成しています。 主な設定内容は以下のとおりです。

  • global > scrape_interval: 60s - 全体のメトリクス収集間隔(60秒)
  • global > scrape_timeout: 10s - 各収集リクエストのタイムアウト時間(10秒)
  • scrape_configs > job_name: cadvisor - 収集ジョブの識別名
  • scrape_configs > static_configs > targets - スクレイピング対象のエンドポイント(cAdvisorの8080ポート)
  • scrape_configs > relabel_configs - メトリクスの instance ラベルをインスタンス識別名に置き換え

CloudWatch Agent設定の更新と起動

次に、CloudWatch Agent の設定ファイルに Prometheus メトリクス収集の設定を記載します。 ※今回は、よくあるEC2自体の収集設定 (メモリ/ディスク使用率) も記載します。

以下、 /home/ec2-user/amazon-cloudwatch-agent-config.json を作成しました。

/home/ec2-user/amazon-cloudwatch-agent-config.json
{
  "agent": {
    "metrics_collection_interval": 60,
    "run_as_user": "cwagent"
  },
  "metrics": {
    "metrics_collected": {
      "mem": {
        "measurement": [ "mem_used_percent" ]
      },
      "disk": {
        "measurement": [ "used_percent" ],
        "resources": [ "/" ]
      }
    }
  },
  "logs": {
    "metrics_collected": {
      "prometheus": {
        "log_group_name": "/CWAgent/test-dify-instance/prometheus",
        "prometheus_config_path": "/opt/aws/amazon-cloudwatch-agent/etc/prometheus.yaml",
        "emf_processor": {
          "metric_namespace": "CWAgent/Container",
          "metric_unit": {
            "container_cpu_usage_seconds_total": "Count",
            "container_memory_usage_bytes": "Bytes"
          },
          "metric_declaration": [
            {
              "source_labels": ["job"],
              "label_matcher": "^cadvisor$",
              "dimensions": [["instance", "name", "image"]],
              "metric_selectors": [
                "^container_cpu_usage_seconds_total$",
                "^container_memory_usage_bytes$"
              ]
            }
          ]
        }
      }
    }
  }
}

この設定で取得できるCloudWatchメトリクスは以下のとおりです。

  • EC2自体のメトリクス (CWAgent名前空間)
    • メモリ使用率とディスク使用率
  • コンテナメトリクス (CWAgent/Container名前空間)
    • cAdvisorから収集したコンテナごとのCPU使用時間とメモリ使用量

設定ファイルの作成後、CloudWatch Agent を起動します。

CloudWatch Agent起動
sudo /opt/aws/amazon-cloudwatch-agent/bin/amazon-cloudwatch-agent-ctl \
  -a fetch-config -m ec2 \
  -s -c file:/home/ec2-user/amazon-cloudwatch-agent-config.json
# ****** processing amazon-cloudwatch-agent ******
# Starting config-downloader, this will map back to a call to amazon-cloudwatch-agent
# Executing /opt/aws/amazon-cloudwatch-agent/bin/amazon-cloudwatch-agent with arguments: [config-downloader -download-source file:/home/ec2-user/amazon-cloudwatch-agent-config.json -output-dir /opt/aws/amazon-cloudwatch-agent/etc/amazon-cloudwatch-agent.d -config /opt/aws/amazon-cloudwatch-agent/etc/common-config.toml -multi-config default -mode ec2]I! Trying to detect region from ec2
# D! [EC2] Found active network interface
# I! imds retry client will retry 1 times
# Start configuration validation...
# 2025/11/13 02:12:47 Reading json config file path: /opt/aws/amazon-cloudwatch-agent/etc/amazon-cloudwatch-agent.d/file_amazon-cloudwatch-agent-config.json.tmp ...
# 2025/11/13 02:12:47 I! Valid Json input schema.
# 2025/11/13 02:12:47 D! loadAllTags: Loaded 1 tags
# 2025/11/13 02:12:47 Configuration validation first phase succeeded
# Starting config-translator, this will map back to a call to amazon-cloudwatch-agent
# Executing /opt/aws/amazon-cloudwatch-agent/bin/amazon-cloudwatch-agent with arguments: [config-translator -output /opt/aws/amazon-cloudwatch-agent/etc/amazon-cloudwatch-agent.toml -mode ec2 -config /opt/aws/amazon-cloudwatch-agent/etc/common-config.toml -multi-config default -input /opt/aws/amazon-cloudwatch-agent/etc/amazon-cloudwatch-agent.json -input-dir /opt/aws/amazon-cloudwatch-agent/etc/amazon-cloudwatch-agent.d]I! Trying to detect region from ec2
# D! [EC2] Found active network interface
# I! imds retry client will retry 1 times
# /opt/aws/amazon-cloudwatch-agent/bin/amazon-cloudwatch-agent -schematest -config /opt/aws/amazon-cloudwatch-agent/etc/amazon-cloudwatch-agent.toml
# Configuration validation second phase succeeded
# Configuration validation succeeded
# amazon-cloudwatch-agent has already been stopped
# Created symlink /etc/systemd/system/multi-user.target.wants/amazon-cloudwatch-agent.service → /etc/systemd/system/amazon-cloudwatch-agent.service.

動作確認

CloudWatchメトリクスを確認してみます。 カスタム名前空間に CWAgent/Container が追加されていました。

sc-2025-11-13_11-22076

CPU使用時間とメモリ使用量のメトリクスが出力されていることも確認しました。

sc-2025-11-13_11-18648

おわりに

Docker on EC2環境にcAdvisorを導入し、 CloudWatch Agentを使ってコンテナメトリクスを収集する方法を紹介しました。

なお、ECS、Fargate あたりだと Container Insights を使うことで、 そもそも cAdvisor を入れずにコンテナ監視ができます。 EC2上で直接 Docker 運用をされている場合は、本ブログの方法が参考になるのではと思います。

また、メトリクス可視化については今回紹介したCloudWatch連携のほか、 Prometheus + Grafanaの組み合わせもあります(むしろ、こちらのほうがより自然かもしれません)。 環境や要件に応じて選択すると良いです。

以上、参考になれば幸いです。

参考

脚注
  1. もともと docker-compose.yaml に直接書き加えていましたが、docker-compose.override.yaml の存在を同僚 から教えてもらいました(ありがとうございます!) ↩︎

この記事をシェアする

FacebookHatena blogX

関連記事