最初 nginx でリバースプロキシサーバーを構築していたのですが、いろいろ調べていく中で Traefik というサーバーの存在を知りました。
公式ではエッジルーターという言い方がされていますが、要はリバースプロキシ+ロードバランサーという感じらしいです。
nginx より後発で、Docker との親和性が高いとのことで試しに使ってみました。
環境
- Docker: 20.10.12
- Traefik: v2.7
Traefik 自身も Docker で動かします。
docker network の作成
アプリと Traefik で共通で使用するネットワークを作成しておきます。
$ docker network create sample-network
Traefik の設定
Traefik の設定は /etc/traefik/traefik.yml
に記述する方法と、docker-compose.yml
で指定する方法があるようです。
前者の例が多いですが、後者の方が docker-compose.yml
一つで設定が完結して良いと思うのは私だけでしょうか?
設定ファイルに記述する例
traefik.yml
というファイルを作成して、以下のように記述します。
# Providers config
providers:
# Docker との連携を有効にする
docker:
# false に指定することで Label 付けしていない docker コンテナを Traefik が無視するようになる
exposedByDefault: false
# 使用するネットワーク
network: sample-network
entryPoints:
# http という任意の名前のエントリーポイントを定義し、80番ポートをリッスンするよう指定
http:
address: ':80'
https:
address: ':443'
# API/Dashboard config
api:
# WebUI にアクセスできるように設定
insecure: true
Trafik を起動します。
ネットには docker-compose を使った例が多いですが、とりあえず docker run
で動かしてみます。
$ docker run -it --rm \
--name reverse-proxy \
--network sample-network \
-v /var/run/docker.sock:/var/run/docker.sock \
-v $(pwd)/traefik.yml:/etc/traefik/traefik.yml \
-p 80:80 \
-p 8080:8080 \
traefik:v2.7
とりあえずこれで、http://localhost:8080 にアクセスすると Traefik の WebUI が表示されるかと思います。
docker-compose.yml で設定する例
上記の設定を docker-compose.yml
のみで行った場合の例です。
version: '3.9'
services:
reverse-proxy:
image: traefik:v2.7
volumes:
- /var/run/docker.sock:/var/run/docker.sock
# ファイルで設定する場合は以下
#- type: bind
# source: ./traefik.yml
# target: /etc/traefik/traefik.yml
ports:
- 80:80
- 8080:8080
networks:
- sample-network
command:
# traefik.yml の代わりに command で設定
- --providers.docker.exposedByDefault=false
- --providers.docker.network=sample-network
- --entryPoints.http.address=:80
- --entryPoints.https.address=:443
- --api.insecure=true
networks:
sample-network:
external: true
アプリケーション側の設定
ルーティングの設定などは全てコンテナのラベルで設定します。 他のサーバーだとサーバー側の設定を変更する必要がありますが、 Traefik+Docker だとコンテナの増減に対して対応しやすいなと思いました。
とりあえず docker run
で動かしてみます。
docker run -it --rm \
--network sample-network \
-l "traefik.enable=true" \
-l "traefik.http.routers.api.entrypoints=http" \
-l "traefik.http.routers.api.rule=Host(\"api.localhost\")"
sample_app
これで http://api.localhost/ に該当のアプリにアクセスすれば繋がると思います。
解説は次に書いてあります。
docker-compose での例
上記の設定は、docker-compose.yml
で以下のように設定します。
コメントで簡単な解説をつけておきました。
labels:
# Traefik の有効化(exposedByDefault:false に設定した場合に必要)
- traefik.enable=true
# api という名前のルーターを定義し、
# エントリーポイント http (traefik.yml で定義した名前) と関連付け
- traefik.http.routers.api.entrypoints=http
# ルーター api のホスト名を "api.localhost" に設定
- traefik.http.routers.api.rule=Host(`api.localhost`)
基本は以上です。
他の詳細な設定については追々記事を書こうかなと思っています。