website/public/anleitungen/traefik.html
2022-05-20 16:32:48 +02:00

185 lines
9.3 KiB
HTML

<!DOCTYPE html>
<html lang="de">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<link href="/css/style.css" rel="stylesheet">
<title></title>
</head>
<body>
<jl-header data-title="Traefik Reverse Proxy"></jl-header>
<div id="content">
<p>In der folgenden Anleitung werde ich darauf eingehen, wie man eine VM mit alpine Linux aufsetzt, darauf
Docker installiert und dann als Container einen Traefik 2 reverse Proxy.</p>
<p>Als erstes muss eine neue VM erstellt werden und als Boot Medium Alpine Linux eingelegt werden. Wenn die ISO
gebootet ist kommt ein Login Fenster, hier einfach mit dem Benutzer <code class="language-text">root</code>
anmelden. Danach sollte ein Terminal Prompt kommen. Um Alpine zu installieren muss der Befehl <code
class="language-text">setup-alpine</code> eingegeben werden. Hierbei gilt es zu beachten, dass die ISO
ein englisches Tastaturlayout benutzt. Der Bindestrich liegt hier auf dem ß. Als erstes muss nun im Setup
das Tastaturlayout angegeben werden, um dieses auf Deutsch festzulegen zwie mal <code
class="language-text">de</code> eingeben.
Nachdem die Tastatur geändert wurde muss der Hostname festgelegt werden, meine VM heißt einfach <code
class="language-text">docker</code>. In der darauffolgenden Netzwerkkonfiguration muss als erstes der
Name des zu konfigurierendes Netzwerkinterfaces angegeben werden (meist <code
class="language-text">eth0</code>)
Im darauffolgenden Schritt wird die Methode der IP konfiguration angegeben. Im Folgenden setze ich hier auf
DHCP. Nachdem das root Passwort (welches mit einem <a href="/passwordgen.html">Passwortgenerator</a>
generiert wurde) festgelegt wurde muss die Zeitzone angegeben werden. Für Deutschland ist
diese <code class="language-text">Europe/Berlin</code>. Einen Proxy brauchen wir nicht, genauso wie beim
mirror können wir einfach mit enter bestätigen. Der SSH Server kann auch bei openssh belassen werden.
Nachdem nun die Grundkonfiguration im Installer abgeschlossen ist, muss noch die Festplatte angegeben
werden. Dafür wird eine Liste an erkannten Platten angezeigt. In meinem Fall war dies <code
class="language-text">sda</code> und danach noch der Typ. Dies ist <code
class="language-text">sys</code>,
da das System auf die Platte installiert wird. Nach der Installation muss das System nochmal neugestartet
werden.
</p>
<p>
Wenn das System nun von der Festplatte gebootet hat kann man sich mit dem Benutzer <code
class="language-text">root</code> und dem zuvor gewählten Passwort anmelden. Danach muss als erstes das
System auf den neuesten Stand gebracht werden und ein paar tool installiert werden. Dazu die beiden unten
ausfgeführten Befehle eingeben.
<pre>
<code class="language-bash">apk update
apk upgrade
apk add nano htop git</code>
</pre>
Um nun Docker zu installieren muss als erstes die Community repo aktiviert werden. Dazu mit <code
class="language-bash">nano</code> die Datei <code class="language-text">/etc/apk/repositories</code> öffnen
und in der Zeile, welche mit <code class="language-text">community</code> endet das <code
class="language-text">#</code> am Anfang entfernen. (Nicht in den Zeilen mit <code
class="language-text">edge</code> im URL) Danach kann Docker installiert werden.
</p>
<pre>
<code class="language-bash">nano /etc/apk/repositories
apk update
apk add docker docker-compose
rc-update add docker
/etc/init.d/docker start</code>
</pre>
<p>
Nun ist Docker auf unserem System installiert und kann eingesetzt werden. Um Traefik 2 nun einzusetzen muss
als erstes meine Vorlage von <a href="https://gitlab.jonasled.de/jonasled/traefik-config">hier</a>
heruntergeladen werden. Danach muss in der Datei <code class="language-text">config/traefik.yml</code> unter
letsencrypt => acme => email die E-Mail Adresse festgelegt werden, welche für letsencrypt verwendet werden
soll. Danach noch die Berechtigungen von der Zertifikatsdatei einschränken. Bevor wir traefik starten könenn
müssen wir noch ein Netzwerk namens <code class="language-text">web</code> angelegt werden. Nachdem nun
alles vorbereit wurde kann dieser mit
<code class="language-bash">docker-compose up</code> gestartet werden.
</p>
<pre>
<code class="language-bash">git clone https://gitlab.jonasled.de/jonasled/traefik-config
cd traefik-config
nano config/traefik.yml
chmod 600 letsencrypt/acme.json
docker network create web
docker-compose up
# Wenn alles läuft strg und c drücken
docker-compose up -d</code>
</pre>
<p>
Traefik ist nun installiert und sollte von außen erreichbar sein. Als Antwort sollte bei nicht bekannten
Domains immer ein 404 Fehler kommen. Zum testen setzen wir als nächstes den whoami Docker Container auf,
dieser ist nur wenige kb groß und bietet einen minimalen Webserver. Dazu muss als erstes die unten
angehängte docker-compose auf dem Host in einem neuen Ordner unter dem Namen <code
class="language-text">docker-compose.yml</code> abspeichern und den Host anpassen. Danach kann der
Container mit <code class="language-bash">docker-compose up</code> gestartet werden. Nun sollte nach 1-2
Minuten auf dem zuvor angegebenen Domain die 404 Meldung durch eine Seite ersetzt werden. Falls dies nicht
der Fall ist kann im Ordner, in dem der Traefik abgelegt wurde der Befehl <code
class="language-text">docker-compose logs -f</code> ausgeführt werden um den Fehlerlog zu überprüfen.
</p>
<pre>
<code class="language-yaml">version: "3.2"
services:
whoami:
image: containous/whoami
restart: unless-stopped
networks:
- web
labels:
- traefik.http.routers.whoami-https.rule=Host(`whoami.jonasled-test.xyz`)
- traefik.http.routers.whoami-https.entrypoints=https
- traefik.http.routers.whoami-https.tls=true
- traefik.http.routers.whoami-https.tls.certresolver=letsencrypt
- traefik.http.services.whoami.loadbalancer.server.port=80
networks:
web:
external: true</code>
</pre>
<p>
Um die Konfigurationen für den Traefik Server zu erstellen verwende nutze ich ein kleines selber
geschriebenes Tool, welches <a
href="https://jonasled.pages.gitlab.jonasled.de/traefik-config-generator/">hier</a> erreichbar ist.
</p>
<h2>Verbesserungen</h2>
<h3>HTTP auf HTTPS weiterleiten</h3>
<p>Ich empfehle diesen Schritt für alle, da dadurch traefik den Nutzer automatisch von einer unverschlüsselten
HTTP Verbindung auf eine verschlüsselte HTTPS verbindung weiterleitet. Dies verhindert das mitlesen der
Daten durch dritte. Um die Weiterleitung einzurichten muss unter <code
class="language-text">config/providers</code> eine neue Datei mit der Endung <code
class="language-text">.yml</code> angelegt werden. (also z.B. <code
class="language-bash">nano config/providers/http.yml</code>) Danach muss in die Datei der unten
angeführte Snippet eingefügt werden und danach gescpeichert werden (strg + x und dann mit y und enter
bestätigen)
</p>
<pre>
<code class="language-yaml">http:
routers:
http-redirect:
rule: HostRegexp(`{any:.+}`)
middlewares: redirect
service: dummy
middlewares:
redirect:
redirectscheme:
scheme: https
services:
dummy:
loadBalancer:
servers:
- url: "http://0.0.0.0/"
passHostHeader: true</code>
</pre>
<h2>Nicht Docker Services einbinden</h2>
<p>
Das Einbinden von Diensten, die nicht auf dem Docker Host laufen ist auch ziemlich einfach. Dafür muss nur
eine Provider yaml Datei (Dateiendung .yml) im <code class="language-text">config/providers</code> Ordner
mit dem nachfolgenden Inhalt angelegt werden. Um den Router zu nutzen muss <code
class="language-text">servicename</code> und <code class="language-text">routername</code> durch Namen
ersetzt werden. Zusätzlich muss im Router der Hostname und im Service der interne URL zu dem dienst, der von
außen erreichbar sein soll gesetzt werden.
</p>
<pre>
<code class="language-yaml">http:
# Add the router
routers:
routername:
service: servicename
rule: Host(`whoami.jonasled-test.xyz`)
tls:
certresolver: letsencrypt
# Add the service
services:
servicename:
loadBalancer:
servers:
- url: http://10.0.0.1
passHostHeader: true</code>
</pre>
<h2>Kommentare:</h2>
<jl-comments_display></jl-comments_display>
<jl-new_comment id="newComment"></jl-new_comment>
</div>
<jl-footer></jl-footer>
<script src="/js/script.js"></script>
</body>
</html>