Docker Compose ファイルから構成図を作る方法

サービス、ネットワーク、ボリュームがすでに書かれた compose.yaml を図に起こし、隠れた呼び出しを見つけて、図を最新に保つ方法を紹介します。

2026/10/22

Docker Compose ファイルから構成図を作る方法

Compose ファイルは、多くの場合、手元にあるシステムの説明のなかでいちばん正直なものです。ノート PC でも CI でも、ときには本番環境でも、実際に起動するのはこのファイルの中身です。一方で、それは YAML の壁でもあります。新しく入ったメンバーは、結局「どのサービスがどのサービスと通信しているのか」を聞くことになります。

このガイドでは、Compose ファイルを信頼できる構成図に変えていきます。Compose が実際に実行するファイルをレンダリングし、各キーを図の要素に対応させ、ファイルでは表現できない呼び出しを書き加え、図をファイルと同期させ続ける、という流れです。最後に、Archboard の無料ツールを使って最初の下書きを数秒で作ります。

例: 小さな shop スタック

これから図にする compose.yaml です。短いですが、よくある落とし穴はそろっています。2 つのネットワークに属するサービス、設定ファイルの中にしか存在しない依存関係、そして開発専用のツールです。

name: shop

services:
  web:
    image: nginx:1.27
    ports:
      - "8080:80"
    volumes:
      - ./nginx.conf:/etc/nginx/conf.d/default.conf:ro
    depends_on:
      - api
    networks: [frontend]

  api:
    build: ./api
    environment:
      DATABASE_URL: postgres://shop:${POSTGRES_PASSWORD}@db:5432/shop
      REDIS_URL: redis://cache:6379/0
    depends_on:
      db:
        condition: service_healthy
      cache:
        condition: service_started
    networks: [frontend, backend]

  worker:
    build: ./api
    command: ["node", "worker.js"]
    environment:
      DATABASE_URL: postgres://shop:${POSTGRES_PASSWORD}@db:5432/shop
      REDIS_URL: redis://cache:6379/0
    depends_on:
      - db
    deploy:
      replicas: 2
    networks: [backend]

  db:
    image: postgres:16
    environment:
      POSTGRES_USER: shop
      POSTGRES_PASSWORD: ${POSTGRES_PASSWORD}
    volumes:
      - db-data:/var/lib/postgresql/data
    healthcheck:
      test: ["CMD-SHELL", "pg_isready -U shop"]
      interval: 5s
    networks: [backend]

  cache:
    image: redis:7
    networks: [backend]

  adminer:
    image: adminer
    ports:
      - "8081:8080"
    profiles: [debug]
    networks: [backend]

volumes:
  db-data:

networks:
  frontend:
  backend:

ステップ 1: Compose が実際に実行するファイルをレンダリングする

書かれたとおりのファイルを 1 つだけ実行しているチームはまれです。override ファイルがポートを追加し、.env ファイルが変数を埋め、extends が別のサービスからフィールドを取り込みます。描き始める前に、Compose に結果を出力させましょう。

docker compose config > rendered.yaml

docker compose config は override ファイルをマージし、変数を展開し、extends を解決したうえで、Compose が実行するモデルを出力します。たまたま開いているファイルではなく、この出力をもとに描いてください。

注意点が 1 つあります。出力には、.env 内の秘密情報も含め、変数の実際の値が入っています。rendered.yaml は .env ファイルそのものと同じように扱い、コミットも共有もしないでください。

ステップ 2: Compose のキーを図の要素に対応させる

図の大部分は、ファイルからそのまま読み取れます。

Compose のキー 図の要素
services.<name> サービスごとに 1 枚のカード。名前はキー名にする
image / build カード上に、イメージのタグまたはビルドコンテキスト
ports (8080:80) カード上と、外部から入るエッジに :8080 → 80
deploy.replicas / scale カード上のレプリカ数。ボックスは増やさない
networks ネットワークごとに 1 つのフレーム。各サービスは最初のネットワークのフレームに置く
名前付きの volumes ボリュームのノード。マウントしているサービスとつなぐ
secrets、configs 使っているサービスとつないだノード(名前のみ)
depends_on 起動順序。カードに書くか、破線のエッジにする
profiles オプションのサービス。省くか、オプションであることを明記する

図を正直に保つためのルールが 2 つあります。api のように 2 つのネットワークに参加するサービスは、両者をつなぐ橋です。最初のネットワークのフレームの端に置き、接続がもう一方のネットワークへまたがるようにします。また、レプリカは数であって、ボックスの山ではありません。worker ×2 は、5 にスケールしても正しいままです。

ステップ 3: ファイルに表れない呼び出しを加える

これは、ツールが代わりにやってくれないステップです。depends_on が扱うのは起動順序です。Compose は db を api より先に起動し、condition: service_healthy が指定されていればヘルスチェックが通るまで待ちます。実行時に誰が誰を呼び出すかについては、何も表していません。

実際の呼び出しは 3 か所に隠れています。

  • 接続文字列。 DATABASE_URL と REDIS_URL は、ホスト(db、cache)とポートを指定しています。その 1 つひとつがエッジです。
  • コンテナにマウントされた設定ファイル。 nginx.conf には proxy_pass http://api:3000; と書かれています。これが web から api へのエッジで、Compose ファイルの外にあります。
  • コード。 Compose に 1 行も書かれていなくても、あるサービスが別のサービスを呼び出すことがあります。worker は REDIS_URL を使っていますが、cache への depends_on はありません。Redis の起動が遅れると worker は起動時に失敗します。そのすき間が最初に見えるのが、構成図です。

簡単な検索で、ほとんどは見つかります。

grep -rnE "://([^/@[:space:]]*@)?(api|web|db|cache)[:/]|proxy_pass" --include="*.conf" --include="*.yaml" --include="*.yml" --include="*.env" .

そのうえで、各サービスのオーナーに確認しましょう。実行時の呼び出しはプロトコルとポートをラベルにした実線のエッジで描き、depends_on はメモか破線のエッジとして残します。そうすれば、起動順序をトラフィックと取り違える人はいなくなります。

ステップ 4: 何を省くかを決める

Compose ファイルには、システムそのものと、その周りのツールが混在しています。通常は次のものを省きます。

  • 開発専用のサービス。 profiles で切り替える adminer、メールキャッチャー、デバッグ用プロキシなどです。
  • 単発のジョブ。 マイグレーションやシーダーなどです。ただし、デプロイについての図なら別です。
  • ソースコードや設定ファイルのバインドマウント。 設定ファイルは、それがもたらす依存関係を通してだけ示します。この例なら nginx.conf 由来の proxy_pass のエッジです。
  • 環境変数の値。 変数名はエッジの説明に役立ちますが、値はシークレットストアに置くもので、図に載せるものではありません。

ステップ 5: レイアウトを組む

トラフィックは左から右へ並べます。ブラウザー、公開ポート、その後ろのサービスの順です。ネットワークはそれぞれフレームとして描くと、ネットワークをまたぐ呼び出しがひと目でわかります。データストアはひとまとめにし、ボリュームはそれをマウントするサービスの下に置きます。すべてのエッジに、HTTP :3000 や SQL :5432 のようにプロトコルとポートを書きましょう。

無料ツールで最初の下書きを作る

カードを手で描く必要はありません。ファイル(またはレンダリング結果。ツールは環境変数の値を読み取りません)を、無料ツール「Docker Compose を図に変換」に貼り付けてください。表示だけならアカウントは不要です。サービスはイメージ、ポート、レプリカ数を載せたカードになり、ネットワークはフレームになります。名前付きボリューム、secret、config はそれを使うサービスにつながり、depends_on はサービス間の接続になります。

ツールが描くのは、ファイルに書かれていることだけです。実行時の呼び出しは表示せず、環境変数の値や env_file の中身も読み取らず、include もたどりません。extends を使うサービスでは、そのサービスに書かれたフィールドだけを描きます。だからこそ、ステップ 1 と 3 は今でも重要なのです。

無料アカウントがあれば、結果を Archboard で新しい図として開けます。そこでステップ 3 の実行時のエッジを加え、ステップ 4 のノイズを取り除きます。その作業を終えた shop スタックがこちらです。

Compose プロジェクトの Docker 構成図。ブラウザーはポート 8080 で web(nginx)にアクセスし、web は api へプロキシします。api と 2 レプリカの worker は、backend ネットワークにある db(PostgreSQL)と cache(Redis)を呼び出します。ボリューム db-data は db がマウントしています。

10 個のコンポーネント · 7 個の接続

Archboard で開く
ダイアグラムの内容
  • Browser
  • frontend
  • backend
  • web
  • api
  • cache
  • db
  • worker
  • db-data
  • HTTP :8080 → 80
  • proxy_pass :3000
  • SQL :5432
  • RESP :6379
  • jobs :6379
  • /var/lib/postgresql/data
このガイドの shop スタック。各ネットワークのフレームに入ったサービス、データベースのボリューム、そして Compose ファイルだけではわからない、nginx.conf と接続 URL から読み取った実行時の呼び出しを示しています。

カードは Docker パック、ブラウザーはネットワークパックのもので、図全体が Free プランの上限であるダイアグラムノード 15 個に収まっています。コンテナ、レジストリ、ロードバランサーを含む別の Docker レイアウトは、Docker Runtime Mesh の例を参照してください。

最新に保つ

Compose ファイルから描いた図は、誰かがサービスを追加したその日に古くなります。次の 3 つの習慣が役立ちます。

  • プルリクエストのテンプレートに 1 行加えます。「サービス、ネットワーク、公開ポート、接続文字列を追加しましたか? 図を更新してください。」
  • レビューのときに docker compose config を再実行し、サービスの一覧を図と比較します。
  • README にはスクリーンショットを貼らず、ライブの図へのリンクを置きます。そうすれば、更新するコピーは 1 つだけで済みます。

スタックが Kubernetes に移ったら、同じ方法をマニフェストに適用できます。「Kubernetes YAML から構成図を作る方法」を参照してください。

よくある質問

depends_on は、あるサービスが別のサービスを呼び出すという意味ですか? いいえ。起動順序を制御するもので、condition: service_healthy を付けるとヘルスチェックも待ちます。実行時の呼び出しは、接続文字列、設定ファイル、コードからわかります。

複数の Compose ファイルをまとめて図にできますか? まず docker compose config でレンダリングしてください。override ファイルが 1 つのモデルにマージされます。無料ツールが一度に読み込むのは 1 ファイルです。

ツールは .env ファイルを読み取りますか? いいえ。変数は展開されません。image: shop-api:${TAG} のように変数を使って書かれたイメージタグやポートは書かれたとおりに表示され、environment の値や env_file の中身も読み取りません。

コンテナごとにボックスを描くべきですか? サービスごとにカードを 1 枚描き、そこにレプリカ数を書きます。個々のコンテナは生まれては消えていくもので、チームが考える単位はサービスです。

compose.yaml を変更したら、図も更新されますか? いいえ。図は出発点です。上で紹介した習慣で最新に保つか、ツールで描き直して実行時のエッジを移してください。

無料で始める — 1 シート、クレジットカード不要。

関連記事

← ブログに戻る

1分でキャンバスを開く

Google または GitHub でサインイン。1シートは無料で、チームが加わったらアップグレード。