https://argentumcation.com/posts/traefik-setup/

Getting up and running with Traefik

Written by: ArgentumCation
2 min read
Last Changed:

  • Okay so you’ve got a server now and need a reverse proxy
  • Traefik is pretty decent at that, it’ll set up your HTTPS certs and auto generate routes from your docker images
  • only problem is its an absolute bitch to set up
  • Here’s a stripped down docker-compose.yml to give you an idea of how I have it set up
  • The end result should be a lighttpd server running on blog.argentumcation.com
# Just setting some default values for my containers
x-service_defaults: &service_defaults
  env_file: .env
  restart: unless-stopped
  extra_hosts:
    - host.docker.internal:host-gateway
services:
  traefik:
    <<: *service_defaults
    container_name: traefik
    env_file:
      - .env
      # Cloudflare API token to add new paths
      - $ENV_DIR/traefik.secrets.env
    hostname: traefik
    image: traefik:latest
    labels:
      - traefik.http.services.traefik-docker.loadbalancer.server.port=8080
      # For the management interface
      - "8080:8080"
      # To let traefik receive incoming HTTP traffic
      - "80:80"
      # To let traefik receive incoming HTTPS traffic
      - "443:443"
    volumes:
      # This lets traefik see your docker services
      - $DOCKER_SOCK:/var/run/docker.sock:ro
      # Traefik Configs
      - $CONF_DIR/traefik/traefik.yml:/traefik.yml
      - $CONF_DIR/traefik/traefik_dynamic.yml:/etc/traefik/traefik_dynamic.yml
      # Let's Encrypt folder (for storing HTTPS cert related stuff)
      - $CONF_DIR/letsencrypt:/letsencrypt
  # Example container we're proxying with traefik
  lighttpd:
    <<: *service_defaults
    container_name: public_lighttpd
    image: sebp/lighttpd
    labels:
      # This is the hostname that traefik will proxy to this container
      - traefik.http.routers.lighttpd-docker.rule=Host(`blog.$PUBLIC`)
      # This is the port the container is listening on, often traefik can detect this
      # automatically, but we'll just be explicit here
      - traefik.http.services.lighttpd-docker.loadbalancer.server.port=80
  • traefik.secrets.env contains my cloudflare API key so that Traefik can automatically add DNS routes
  • For reference, here’s my .env file
# GENERAL
PUBLIC=argentumcation.com
TZ=America/New_York

#for container specific env vars
ENV_DIR=./env

CONF_DIR=./config

DOCKER_DIR=/home/mira/docker
DOCKER_SOCK=/var/run/docker.sock

# So my containers run as a non-root user
UID=1000
GID=1000
PUID=1000
PGID=1000
USER_UID=1000
USER_GID=1000
  • And of course, the actual traefik configuration files:
    • traefik.yml:
accessLog:
  filePath: ./traefik-access.log

api:
  dashboard: true
  debug: true
  insecure: true
certificatesResolvers:
  letsencrypt:
    acme:
      dnschallenge:
        provider: cloudflare #look, I know, don't judge me
      email: [redacted]
      storage: /letsencrypt/acme.json
entryPoints:
  web:
    address: ":80"
    forwardedHeaders:
      insecure: true
    http:
      middlewares:
        - https_redirect@file

  websecure:
    address: ":443"
    forwardedHeaders:
      insecure: true
    http:
      tls:
        certresolver: letsencrypt
        domains:
          - main: argentumcation.com
            sans:
              - "*.argentumcation.com"
log:
  level: INFO
providers:
  docker:
    # Routes will be set to [container-name].argentumcation.com by default
    defaultRule: Host(`{{ index .Labels "com.docker.compose.service" }}.argentumcation.com`)
    endpoint: unix:///var/run/docker.sock
    exposedByDefault: true # exposes auto-discovered containers by default, not secure but I'm lazy
    network: docker_default
    watch: true
  file:
    directory: /etc/traefik/
    watch: true
- `traefik-dynamic.yml`
http:
  middlewares: #This should redirect incoming http connections to https
    https_redirect:
      redirectscheme:
        scheme: https
        permanent: true