Bei meiner täglichen Arbeit als DevOps Engineer nutze ich täglich verschiedene Docker-Container. Da brauche ich eine Art Proxy, der vorgeschaltet ist und alle meine Anfragen entgegen nimmt und auf die richtigen Container weiter leitet. Dafür verwende ich den Container traefik und hier zeige ich euch, wie man schnell eine kleine Umgebung aufsetzt.

Netzwerk

Man braucht ein gemeinsames Netzwerk, in dem alle Container laufen und untereinander kommunizieren können. Dieses legt man einfach mit dem folgenden Befehl an:

docker network create traefik

Ordnerstruktur

Ich lege mir für jeden Container einen eigenen Ordner an und in diesem wird ein data-Verzeichnis sowie die Datei docker-compose.yml erstellt. Für den Container Traefik ist die Struktur wie folgt:

Ordnerstruktur für den Container *Traefik*

Konfiguration

Die Datei traefik.toml enthält die Konfiguration des Traefik-Servers. Falls jemand andere Arten der Konfiguration bevorzugt: die verschiedenen Arten der Konfiguration, die bei Traefik möglich sind, werden in der Dokumentation sehr gut beschrieben.

[entryPoints]
    [entryPoints.http]
        address = ":80"
    [entryPoints.https]
        address = ":443"

[certificatesResolvers]
    [certificatesResolvers.mbit]
        [certificatesResolvers.mbit.acme]
            email = "hostmaster@example.com"
            storage = "/acme.json"
            [certificatesResolvers.mbit.acme.tlsChallenge]

[api]
    dashboard = true

[providers]
    [providers.docker]
        endpoint = "unix:///var/run/docker.sock"
        exposedByDefault = false

[accessLog]
    filePath = "/logs/access.log"

[log]
    filePath = "/logs/traefik.log"
    level = "INFO"

Als erstes definiere ich zwei Einstiegspunkte (entryPoints) namens http und https (Zeile 1 bis 5). Diese nehmen Anfragen entgegen und verarbeiten sie entsprechend der jeweils passenden Konfiguration. Der dann folgende Konfigurationseintrag (certificatesResolvers) erhält den Namen mbit und nutzt den acme-Provider. Die benötigten Zertifikate werden also über Let's Encrypt für die jeweilige Domain erstellt (Zeile 7 bis 12). Der Rest ist relativ selbst erklärend und weiterführende Details zur Konfiguration von Traefik findet man in der Dokumentation.

Die Datei docker-compose.yml:

version: '3'

services:

    reverse-proxy:
        image: "traefik:v2.3"
        restart: "always"
        container_name: "traefik"
        networks:
            - traefik
        ports:
            - "80:80"
            - "443:443"
            - "8080:8080"
        volumes:
            - "/var/run/docker.sock:/var/run/docker.sock:ro"
            - "/srv/traefik/data/logs:/logs"
            - "/srv/traefik/data/config/traefik.toml:/etc/traefik/traefik.toml"
            - "/srv/traefik/data/config/acme.json:/acme.json"
        labels:
            - "traefik.enable=true"
            - "traefik.http.routers.api.rule=Host(`docker.example.com`)"
            - "traefik.http.routers.api.service=api@internal"
            - "traefik.http.routers.api.entrypoints=https"
            - "traefik.http.routers.api.tls.certresolver=mbit"
            - "traefik.http.routers.api.middlewares=traefik-auth"
            - "traefik.http.middlewares.traefik-auth.basicauth.users=admin:##PASSWORD##"
            - "traefik.http.middlewares.redirect-to-https.redirectscheme.scheme=https"

networks:
    traefik:
        external: true

Der Container erhält seine Konfiguration über einen Volume-Mount (traefik.toml) und die Datei acme.json ist der Storage für die Let's Encrypt Zertifikate. Die weitere Konfiguration erfolgt über die Labels:

  • Die API (ein Dashboard zur Ansicht der laufenden Dienste, der eingerichteten entryPoints usw.) wird an die Domain docker.example.com gehängt (Zeile 22 bis 24)
  • Die Zertifikate werden über Let's Encrypt bezogen (Zeile 25)
  • Es wird eine Passwort-Authentifizierung vorgeschaltet (Zeile 26 und 27)
  • Alle Anfragen werden auf HTTPS weiter geleitet (Zeile 28)

Alle weiteren Container hängen sich an Traefik ebenfalls über Labels an. Hier ein Beispiel des Containers pypiserver:

---
version: "3.3"

services:
    pypiserver:
        image: pypiserver/pypiserver:v1.3.2
        restart: unless-stopped
        container_name: pypiserver
        networks:
            - traefik
        volumes:
            - /srv/pip/data/packages:/data/packages:rw
            - /srv/pip/data/conf/htpasswd:/data/.htpasswd:ro
        command: -P /data/.htpasswd -a update,download -v /data/packages
        labels:
            - "traefik.enable=true"

            - "traefik.http.routers.pypiserver.rule=Host(`ppi.example.com`)"
            - "traefik.http.routers.pypiserver.entrypoints=http"
            - "traefik.http.routers.pypiserver.service=pypiserver-pip"
            - "traefik.http.middlewares.pypiserver-redirectscheme.redirectscheme.scheme=https"
            - "traefik.http.middlewares.pypiserver-redirectscheme.redirectscheme.permanent=true"
            - "traefik.http.routers.pypiserver.middlewares=pypiserver-redirectscheme"

            - "traefik.http.routers.pypiserver-secure.rule=Host(`ppi.example.com`)"
            - "traefik.http.routers.pypiserver-secure.entrypoints=https"
            - "traefik.http.routers.pypiserver-secure.service=pypiserver-pip"
            - "traefik.http.routers.pypiserver-secure.tls=true"
            - "traefik.http.routers.pypiserver-secure.tls.certresolver=mbit"

networks:
    traefik:
        external: true
  • Der Container wird an die Domain ppi.example.com gehängt (Zeile 18 und 25)
  • Die Einstiegspunkte HTTP und HTTPS werden beide verwendet (Zeile 19 und 26)
  • Alle auf HTTP ankommenden Requests werden auf HTTPS umgeleitet (Zeile 20 bis 23)
  • Die Zertifikate werden über Let's Encrypt bezogen (Zeile 28 und 29)

    Nun kann man weitere Container starten und ebenfalls über Traefik routen lassen. Viel Spass!

Vorheriger Beitrag Nächster Beitrag