简介

Traefik 是一款基于 Go 语言开发的代理服务器,同时也是 Kubernetes 的 Ingress,所以天然支持多种服务发现机制:

  • File
  • Nomad
  • Docker
  • Kubernetes
  • Etcd
  • Consul
  • Redis
  • HTTP
  • ZooKeeper

我这里主要使用 Docker 来后端服务的自动发现与反向代理!

前置条件

我打算使用 *.service.local 作为 Traefik 反向代理后端服务的访问域名,Traefik 的 Console 则是 ingress.service.local

生成证书

在本地开发环境,我希望也是通过 HTTPS 来管理和访问 Traefik,所以用 mkcert 创建了自签名的证书。

mkcert -cert-file ./fullchain.cer -key-file ./fullchain.key service.local "*.service.local"

配置 TLS

global:
  checkNewVersion: true
  sendAnonymousUsage: true
serversTransport:
  insecureSkipVerify: true
tls:
  options:
    default:
      sniStrict: true
      minVersion: VersionTLS12
      maxVersion: VersionTLS13
      cipherSuites:
        - TLS_AES_128_GCM_SHA256
        - TLS_AES_256_GCM_SHA384
        - TLS_CHACHA20_POLY1305_SHA256
        - TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384
        - TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256
        - TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256
  certificates:
    - certFile: /certs/fullchain.cer
      keyFile: /certs/fullchain.key

这里发现 serversTransport.insecureSkipVerify 似乎并不生效,因为某个后端服务使用自签的证书运行的 HTTPS 服务,开了这个配置项后,依然无法正常访问,需要再 Traefik 启动时手动增加 --serverstransport.insecureskipverify=true 参数,才能按预期运行!

编排

services:
  traefik:
    image: traefik:latest
    hostname: traefik
    container_name: traefik
    ports:
      - "0.0.0.0:80:80/tcp"
      - "0.0.0.0:443:443/tcp"
    networks:
     - traefik
    command: 
      - --api=true
      - --api.dashboard=true

      - --log.level=FATAL

      - --serverstransport.insecureskipverify=true

      - --entrypoints.http.address=:80
      - --entrypoints.https.address=:443

      - --providers.file=true
      - --providers.file.watch=true
      - --providers.file.directory=/etc/traefik/config
      - --providers.file.debugloggeneratedtemplate=true

      - --providers.docker=true
      - --providers.docker.watch=true
      - --providers.docker.network=traefik
      - --providers.docker.useBindPortIP=false
      - --providers.docker.endpoint=unix:///var/run/docker.sock
    labels:
      - traefik.enable=true
      - traefik.docker.network=traefik

      - traefik.http.middlewares.gzip.compress=true
      - traefik.http.middlewares.redir-https.redirectscheme.scheme=https
      - traefik.http.middlewares.redir-https.redirectscheme.permanent=true

      - traefik.http.routers.traefik-dashboard.middlewares=redir-https@docker
      - traefik.http.routers.traefik-dashboard-secure.middlewares=gzip@docker
      - traefik.http.routers.traefik-dashboard-api-secure.middlewares=gzip@docker

      - traefik.http.routers.traefik-dashboard.entrypoints=http
      - traefik.http.routers.traefik-dashboard.rule=Host(`ingress.service.local`)
      - traefik.http.routers.traefik-dashboard.service=noop@internal

      - traefik.http.routers.traefik-dashboard-secure.entrypoints=https
      - traefik.http.routers.traefik-dashboard-secure.tls=true
      - traefik.http.routers.traefik-dashboard-secure.rule=Host(`ingress.service.local`)
      - traefik.http.routers.traefik-dashboard-secure.service=dashboard@internal

      - traefik.http.routers.traefik-dashboard-api-secure.entrypoints=https
      - traefik.http.routers.traefik-dashboard-api-secure.tls=true
      - traefik.http.routers.traefik-dashboard-api-secure.rule=Host(`ingress.service.local`) && PathPrefix(`/api`)
      - traefik.http.routers.traefik-dashboard-api-secure.service=api@internal
    volumes:
      - ./certs/:/certs/:ro
      - ./config/:/etc/traefik/config/:ro
      # So that Traefik can listen to the Docker events
      - /var/run/docker.sock:/var/run/docker.sock

networks:
  traefik:
    external: true

配置解释:

  • 17 行设置跳过对后端 HTTPS 的校验
  • 36 行用于配置 gzip 中间件,对内响应容进行压缩,
  • 37~38 行则用于配置 HTTP 重定向到 HTTPS
  • 44 行为 Traefik Dashboard 配置 Entrypoint 为 HTTP,也就是监听 80 端口的流量
  • 45 行为 Traefik Dashboard 配置 路由规则,这里是请求域名是 ingress.service.local 就会路由到 Traefik 上
  • 46 行为 Traefik Dashboard 指定后端的服务,noop@internal 是 Traefik 内部的一个“魔术变量”

创建网络

docker network create traefik --subnet 10.8.10.0/24 --gateway 10.8.10.1

网段和网关可以根据自己的需求自行设置!

启动服务

docker compose up -d

最终效果

Dashboard

Dashboard

Dashboard

Dashboard

I hope this is helpful, Happy hacking…