0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

一人アドカレ 3日目: Traefikの紹介

Posted at

イントロ

みなさま、自分のPCでサーバーを建てた経験はありますか?

Webサーバーなどを実際にブラウザで確認する時は、http://localhost:ポート番号のようにアクセスすることが多いかと思います。
開発の時に1つのサービスだけ動かすならそれで問題ないでしょう。

でもセルフホスティングって複数のサービスを同時に動かすことが多いので、いちいちポート番号なんて覚えてられないのです。

そんなあなたへTraefik

俗にいうリバースプロキシサーバーの一つです。

https://web.example.comや、https://blog.example.comのように、サブドメインを覚えていればアクセスできる、という環境が簡単に作れます。

CaddyやNginxなどもリバースプロキシとして動作しますが、TraefikのメリットはDockerのラベルを見て自動的に設定を反映してくれる点です。
新しいサービスを追加した都度、設定ファイルを書き換えたりする必要がなく、Dockerコンテナを起動するだけで自動的にTraefikが認識してくれます。

traefikの使い方

環境情報
$ docker version
Client: Docker Engine - Community
 Version:           29.1.3
 API version:       1.52
 Go version:        go1.25.5
 Git commit:        f52814d
 Built:             Fri Dec 12 14:49:51 2025
 OS/Arch:           linux/amd64
 Context:           default

Server: Docker Engine - Community
 Engine:
  Version:          29.1.3
  API version:      1.52 (minimum version 1.44)
  Go version:       go1.25.5
  Git commit:       fbf3ed2
  Built:            Fri Dec 12 14:49:51 2025
  OS/Arch:          linux/amd64
  Experimental:     false
 containerd:
  Version:          v2.2.0
  GitCommit:        1c4457e00facac03ce1d75f7b6777a7a851e5c41
 runc:
  Version:          1.3.4
  GitCommit:        v1.3.4-0-gd6d73eb8
 docker-init:
  Version:          0.19.0
  GitCommit:        de40ad0

前提条件

  • Dockerがインストールされていること
  • ドメインを所有していること(保有していなくても可能ですが、あくまで自分のドメインで建てた例を紹介します)
  • ドメインのDNS管理がCloudflareでできること(他のDNSプロバイダでも可能ですが、ここではCloudflareを使った例を紹介します)
    • DNSの設定とかは省きます
  • CloudflareのAPIトークンを発行していること

手順

  1. 事前設定
    docker networkを作成する(traefikから参照できるためのネットワーク)

    # traefik-networkという名前で作成する、subnet, gatewayは任意
    docker network create --subnet 172.100.0.0/16 --gateway 172.100.0.1 traefik-network
    
  2. compose.ymlの作成

    domain.tldの部分は自分のドメインに書き換えてください。https://domain.tld/dashboadでTraefikのダッシュボードにアクセスできるようなルールをラベルに追加しています

    compose.yml
    services:
      traefik:
        image: traefik:v3.6
        container_name: traefik
        restart: unless-stopped
        ports:
          - 80:80
          - 443:443/tcp
        volumes:
          - ./traefik.yml:/etc/traefik/traefik.yml
          - ./letsencrypt:/letsencrypt
        environment:
          TZ: Asia/Tokyo
          TRAEFIK_CERTIFICATESRESOLVERS_cloudflare_ACME_EMAIL: ${CF_API_EMAIL}
          CF_DNS_API_TOKEN: ${CLOUDFLARE_DNS_API_TOKEN}
          CF_ZONE_API_TOKEN: ${CLOUDFLARE_ZONE_API_TOKEN}
        dns:
          - 1.1.1.1
        networks:
          - default
          - traefik-network
        labels:
          traefik.enable: true
          traefik.docker.network: traefik-network
          # Dashboard & API Router
          traefik.http.routers.dashboard.rule: Host(`domain.tld`) && (PathPrefix(`/api`) || PathPrefix(`/dashboard`))
          traefik.http.routers.dashboard.service: api@internal
          traefik.http.routers.dashboard.entrypoints: websecure
          traefik.http.routers.dashboard.tls: true
          traefik.http.routers.dashboard.tls.certResolver: cloudflare
          # Redirect router
          traefik.http.routers.dashboard-redirect.rule: Host(`domain.tld`) && Path(`/`)
          traefik.http.routers.dashboard-redirect.service: api@internal
          traefik.http.routers.dashboard-redirect.entrypoints: websecure
          traefik.http.routers.dashboard-redirect.tls: true
          traefik.http.routers.dashboard-redirect.tls.certResolver: cloudflare
          traefik.http.routers.dashboard-redirect.middlewares: dashboard-redirect
          # Redirect middleware
          traefik.http.middlewares.dashboard-redirect.redirectregex.regex: ^(https://[^/]+)/?$$
          traefik.http.middlewares.dashboard-redirect.redirectregex.replacement: $${1}/dashboard/
          traefik.http.middlewares.dashboard-redirect.redirectregex.permanent: true
        depends_on:
          socket-proxy:
            condition: service_started
      socket-proxy:
        image: tecnativa/docker-socket-proxy
        restart: unless-stopped
        container_name: readonly-socket
        environment:
          CONTAINERS: 1 # コンテナ情報の読み取り(必須)
          SERVICES: 0 # サービス情報の読み取り(Swarmモード用)
          NETWORKS: 1 # ネットワーク情報の読み取り(必須)
          # セキュリティ関連
          POST: 0 # 作成禁止
          DELETE: 0 # 削除禁止
          BUILD: 0 # ビルド禁止
          IMAGES: 0 # イメージ操作不要
          VOLUMES: 0 # ボリューム操作不要
          SYSTEM: 0 # システム情報不要
          SECRETS: 0 # SECRETS不要
          CONFIGS: 0 # Configs不要
          PLUGINS: 0 # プラグイン不要
          # Swarm関連は全て不要
          SWARM: 0
          NODES: 0
          TASKS: 0
          LOG_LEVEL: warning # default infoだと結構うるさい
        volumes:
          - /var/run/docker.sock:/var/run/docker.sock:ro
        networks:
          - default
    networks:
      default:
      traefik-network:
        external: true
    
  3. .envの作成

    CloudflareのAPIトークンを環境変数として渡すための.envファイルを作成します

    .env
    CLOUDFLARE_DNS_API_TOKEN=your_cloudflare_dns_api_token
    CLOUDFLARE_ZONE_API_TOKEN=your_cloudflare_zone_api_token
    CF_API_EMAIL=your_email_address_used_in_cloudflare
    
  4. traefik.ymlの作成

    traefik.yml
    api:
      dashboard: true
      insecure: false
    
    entryPoints:
      web:
        address: ":80"
        http:
          redirections:
            entryPoint:
              to: websecure
              scheme: https
              permanent: true
      websecure:
        address: ":443"
    
    providers:
      docker:
        endpoint: "tcp://readonly-socket:2375"
        exposedByDefault: false
        network: traefik-network
    
    certificatesResolvers:
      cloudflare:
        acme:
          dnsChallenge:
            provider: cloudflare
            propagation:
              delayBeforeChecks: 2s
          storage: /letsencrypt/acme.json
          ## test用
          # caServer: https://acme-staging-v02.api.letsencrypt.org/directory
    
  5. Traefikの起動

    下記コマンドを実行したらhttps://domain.tld/dashboardにアクセスできる

    docker compose up -d
    

アクセス経路のイメージ図

03.traefik.png

traefikの感想

  • 良いところ
    • Dockerラベルを見て自動的に設定を反映してくれるので、新しいサービスを追加するのが楽
    • Let's EncryptによるSSL証明書発行が自動化されている
    • ダッシュボードが用意されているので、現在のルーティング状況などが確認できる
  • 不満・使いこなせていないところ
    • 設定項目が多すぎて、最初は何をどう設定すれば良いのかわからない
      • わかれば死ぬほど楽、もうtraefikからは離れられない

以上でTraefikの紹介を終わり!
次は認証に使えるPocketIDの紹介をします。

なお、compose.ymlで削除していますが、次回のPocketIDとその次のTinyAuthを導入することで、Traefikのダッシュボードに認証を追加することも可能です。

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?