Compose の ネットワーク機能(networking)

注釈

このページの内容が適用されるのは、 Compose ファイルフォーマットの バージョン 2 と それ以降 です。 ネットワーク機能は バージョン 1 ではサポートされません(非推奨)。

デフォルトで Compose はアプリに対して1つの ネットワーク を作成します。サービス用の各コンテナはデフォルトのネットワークに接続し、そのネットワーク上で他のコンテナと相互に「 接続可能(reachable) 」になります。そして、コンテナ名と同じホスト名として、お互いが「 発見可能(discoverable) 」になります。

注釈

アプリのネットワークは「プロジェクト名」に基づき作成されます。これは、その場所にいるディレクトリ名が元になります。プロジェクト名は --project-name フラグ や COMPOSE_PROJECT_NAME 環境変数 で上書きできます。

たとえば、 myapp という名前のディレクトリ内にアプリがあり、 docker-compose.yml は次のようなものだと想定します。

version: "3.9"
services:
  web:
    build: .
    ports:
      - "8000:8000"
  db:
    image: postgres
    ports:
      - "8001:5432"

docker-compose up を実行すると、以下の処理が行われます。

  1. myapp_default という名前のネットワークが作成される。

  2. web の設定を使うコンテナが作成される。これは myapp_default ネットワークに web という名前で接続する。

  3. db の設置を使うコンテナが作成される。これは myapp_default ネットワークに db という名前で接続する。

注釈

v2.1 以上では、オーバレイ ネットワークは常に「attachable」

Compose ファイル形式 2.1 からは、オーバレイ ネットワークは常に attachable として作成され、これは変更できません。つまり、スタンドアロン コンテナはオーバレイ ネットワークに接続できません。

Compose ファイル形式 3.x からは、オプションで attachable 属性を false に設定できます。

これで各コンテナはホスト名 web や db で探せるようになり、適切なコンテナの IP アドレスが帰ってきます。たとえば、 web アプリケーションのコードが URL postgres://db:5432 に接続すると、Postgres データベースを使用開始します。

重要な注意点として、 HOST_PORT と CONTAINER_PORT は区別が必要です。先述の例では、 db の場合、 HOST_PORT は 8001 で、コンテナのポートは 5432 です(postgres のデフォルト)。ネットワーク内のサービス間通信で使うのは CONTAINER_PORT です。 HOST_PORT を定義した場合、サービスは swam (クラスタ)外からも同様にアクセスできるようになります。

web コンテナ内では、 db に接続する文字列は postgres://db:5432 のようになります。ホストマシン上から接続する文字列は postgres://{DOCKER_IP}:8001 のようになります。

コンテナの更新

サービスの設定情報に変更を加え、 docker-compose up を実行すると、設定情報は更新されるため、古いコンテナは削除され、新しいコンテナがネットワークに接続します。この時、ネットワーク上の名前は同じですが IP アドレスは異なります。実行中のコンテナは名前で名前解決できますので、新しい IP アドレスに接続できます。その一方、古い IP アドレスは動作を停止します。

古いコンテナに対して接続していたあらゆるコンテナは、接続が閉じられます。コンテナはこの状況を検出する役割があり、再び同じ名前で名前解決し、再接続します。

複数ホスト間(multi-host) でのネットワーク機能

Swarm モードを有効化 した Docker Engine で Compose アプリケーションをデプロイする場合、内蔵の overlay ドライバを使い、複数のホスト間で通信が可能です。

Swarm モードのセクション を参考にし、 Swarm クラスタのセットアップ方法を確認し、複数ホストでのオーバレイ ネットワークについて学ぶには 複数ホストのネットワーク機能を始めましょう をご覧ください。

任意のネットワークを指定

デフォルトのアプリ用ネットワークを使う代わりに、トップレベルの networks キーを使い、自身のネットワークを指定できます。これにより、より複雑なトポロジーの作成や、 任意のネットワーク ドライバ とそのオプションが指定できるようになります。また、Compose によって管理されていない外部ネットワークに対し、サービスの接続もできます。

各サービスでは、「 サービス レベル(service-level) 」の networks キーを使い、接続するネットワークを指定できます。これは、トップレベルの networks キー以下のエントリを参照する、名前のリストです。

以下にある Compose ファイル例は、2つの任意ネットワークを定義しています。この proxy サービスは db サービスから分離されます。これは、どちらも共通するネットワークを共有しないためです。 app サービスのみが両サービスと通信できます。

version: "3.9"

services:
  proxy:
    build: ./proxy
    networks:
      - frontend
  app:
    build: ./app
    networks:
      - frontend
      - backend
  db:
    image: postgres
    networks:
      - backend

networks:
  frontend:
    # Use a custom driver
    driver: custom-driver-1
  backend:
    # Use a custom driver which takes special options
    driver: custom-driver-2
    driver_opts:
      foo: "1"
      bar: "2"

networks では、接続するネットワークごとに ipv4_address か ipv6_address の両方、またはいずれか を指定し、 固定(static) IP アドレスを設定できます。

また、 networks では 任意の名前 も指定できます(バージョン 3.5 以降)。

version: "3.9"
services:
  # ...
networks:
  frontend:
    name: custom_frontend
    driver: custom-driver-1

利用可能なネットワークのオプション詳細は、以下のリファレンスをご覧ください。

デフォルト ネットワークの設定

自身のネットワークを指定する代わりに(あるいは指定するように)、アプリケーション全体のデフォルトネットワークの設定を、 networks 以下の default エントリの定義によって行えます。

version: "3.9"
services:
  web:
    build: .
    ports:
      - "8000:8000"
  db:
    image: postgres

networks:
  default:
    # 任意のドライバを使う
    driver: custom-driver-1

既存のネットワークを使う

コンテナを既存のネットワークに対して接続したい場合は、 external オプション を使います。

services:
  # ...
networks:
  default:
    name: my-pre-existing-network
    external: true

[プロジェクト名]_default という名前でネットワーク作成を試みるのに代わり、 Compose は my-pre-existing-network という名前のネットワークを探し、そこへアプリのコンテナを接続します。

参考

Networking in Compose

https://docs.docker.com/compose/networking/