« Traefik » : différence entre les versions
(Remplacement des schémas ASCII Art en SVG) |
(Remplacement des balises "source" obsolètes par "syntaxhighlight") |
||
Ligne 31 : | Ligne 31 : | ||
vim /etc/systemd/system/traefik.service | vim /etc/systemd/system/traefik.service | ||
< | <syntaxhighlight lang="ini"> | ||
[Unit] | [Unit] | ||
Description=Traefik, circulez y'a rien à voir ! | Description=Traefik, circulez y'a rien à voir ! | ||
Ligne 48 : | Ligne 48 : | ||
[Install] | [Install] | ||
WantedBy=multi-user.target | WantedBy=multi-user.target | ||
</ | </syntaxhighlight> | ||
Chargement du service au démarrage du système | Chargement du service au démarrage du système | ||
Ligne 59 : | Ligne 59 : | ||
=Configuration de base= | =Configuration de base= | ||
Le fichier de configuration de ''Traefik'' est au format ''TOML'', mais peux être également au format ''JSON''. Il y a donc deux noms de fichier recommandés suivant le langage utilisé : | Le fichier de configuration de ''Traefik'' est au format ''TOML'', mais peux être également au format ''JSON''. Il y a donc deux noms de fichier recommandés suivant le langage utilisé : | ||
* < | * <syntaxhighlight lang="bash" inline>traefik.toml</syntaxhighlight> | ||
* < | * <syntaxhighlight lang="bash" inline>traefik.yml</syntaxhighlight> | ||
Ce fichier est attendu dans l'une de ces arborescences : | Ce fichier est attendu dans l'une de ces arborescences : | ||
* < | * <syntaxhighlight lang="bash" inline>/etc/traefik/</syntaxhighlight> | ||
* < | * <syntaxhighlight lang="bash" inline>$HOME/.config</syntaxhighlight> | ||
* < | * <syntaxhighlight lang="bash" inline>.</syntaxhighlight> (Dans la même arborescence que le binaire) | ||
Nous pouvons également définir à ''Traefik'' un fichier de configuration spécifique : | Nous pouvons également définir à ''Traefik'' un fichier de configuration spécifique : | ||
< | <syntaxhighlight lang="bash"> | ||
traefik --configFile=foo/bar/myconfigfile.toml | traefik --configFile=foo/bar/myconfigfile.toml | ||
</ | </syntaxhighlight> | ||
{{attention|Dans ce fichier, il est attendu une configuration statique. Une modification de celui-ci nécessitera une relance de ''Traefik'' pour qu'elles soient prisent en compte. Sont également concernés les fichiers étrangers aux différents hôtes virtuels comme par exemple ''middleware.toml'' et ''tls.toml'' que nous verrons plus bas. Seules les fichiers contenants les directives ''routers'' et ''services'' ne nécessites pas de redémarrage du service.}} | {{attention|Dans ce fichier, il est attendu une configuration statique. Une modification de celui-ci nécessitera une relance de ''Traefik'' pour qu'elles soient prisent en compte. Sont également concernés les fichiers étrangers aux différents hôtes virtuels comme par exemple ''middleware.toml'' et ''tls.toml'' que nous verrons plus bas. Seules les fichiers contenants les directives ''routers'' et ''services'' ne nécessites pas de redémarrage du service.}} | ||
Ligne 78 : | Ligne 78 : | ||
vim /opt/traefik/config/traefik.toml | vim /opt/traefik/config/traefik.toml | ||
< | <syntaxhighlight lang="yaml"> | ||
# Configuration globale de Traefik | # Configuration globale de Traefik | ||
[global] | [global] | ||
Ligne 109 : | Ligne 109 : | ||
[entryPoints.http] # Permet de déclarer un point d'entrée nommé "http" | [entryPoints.http] # Permet de déclarer un point d'entrée nommé "http" | ||
address = ":80" # Permet de déclarer le port d'entrée | address = ":80" # Permet de déclarer le port d'entrée | ||
</ | </syntaxhighlight> | ||
{{attention|Pour les < | {{attention|Pour les <syntaxhighlight lang="bash" inline>filePath</syntaxhighlight> des sections <syntaxhighlight lang="bash" inline>[log]</syntaxhighlight> et <syntaxhighlight lang="bash" inline>[accessLog]</syntaxhighlight>, il faudra prévoir une rotation du fichier journal (voir [[Logrotate]]) car ''Traefik'' ne gère pas cette fonction. Ceci est indispensable pour ne pas voir votre partition se remplir jusqu'à déni de service.}} | ||
Comme nous avons édité le fichier de configuration principal du serveur, il faut recharger le service | Comme nous avons édité le fichier de configuration principal du serveur, il faut recharger le service | ||
Ligne 117 : | Ligne 117 : | ||
=Fonctionnalités= | =Fonctionnalités= | ||
L'outil permet un éventail de fonctionnalités souvent rencontrées dans des logiciels de ce type. Elles sont décrites dans un ou plusieurs fichiers. Un hôte étant définit par des sections, il est possible d'en combiner plusieurs en un seul fichier ou d'en faire un par fichier. Ceci est configuré dans le paramètre < | L'outil permet un éventail de fonctionnalités souvent rencontrées dans des logiciels de ce type. Elles sont décrites dans un ou plusieurs fichiers. Un hôte étant définit par des sections, il est possible d'en combiner plusieurs en un seul fichier ou d'en faire un par fichier. Ceci est configuré dans le paramètre <syntaxhighlight lang="bash" inline>directory</syntaxhighlight> de la directive <syntaxhighlight lang="bash" inline>[providers]</syntaxhighlight> vu précédemment. Comme précisé par le paramètre <syntaxhighlight lang="bash" inline>watch</syntaxhighlight> de cette même directive, ces fichiers sont appliqués au serveur à chaque enregistrements. | ||
Parmi les fonctionnalités que nous avons explorées, nous pouvons noter la possibilité de faire: | Parmi les fonctionnalités que nous avons explorées, nous pouvons noter la possibilité de faire: | ||
Ligne 136 : | Ligne 136 : | ||
vim /opt/traefik/config/vhosts/ma_page.toml | vim /opt/traefik/config/vhosts/ma_page.toml | ||
< | <syntaxhighlight lang="yaml"> | ||
# Service de type http | # Service de type http | ||
[http] | [http] | ||
Ligne 148 : | Ligne 148 : | ||
[[http.services.ma_page.loadBalancer.servers]] # Déclaration d'un serveur | [[http.services.ma_page.loadBalancer.servers]] # Déclaration d'un serveur | ||
url = "http://[2001:db8:0:180::a0]" # URL vers mon serveur MaPage | url = "http://[2001:db8:0:180::a0]" # URL vers mon serveur MaPage | ||
</ | </syntaxhighlight> | ||
Vous pouvez noter le mot clé < | Vous pouvez noter le mot clé <syntaxhighlight lang="bash" inline>loadBalancer</syntaxhighlight> à la ligne créant le service (<syntaxhighlight lang="bash" inline>[http.services.ma_page.loadBalancer]</syntaxhighlight>). En fait, ''Traefik'' fait constament de la répartition de charge, même avec un seul hôte (ce qui revient à toujours envoyer les requêtes sur la même machine). La configuration d'une réelle répartition de charge consiste donc à ajouter un hôte, d'où la simplicité de mise en œuvre. Nous verrons ceci plus bas. | ||
Il est également possible de faire des règles (paramètre < | Il est également possible de faire des règles (paramètre <syntaxhighlight lang="bash" inline>rule</syntaxhighlight>) avec plus de conditions en utilisant des [https://docs.traefik.io/routing/routers/#rule structures conditionnelles] telles que <syntaxhighlight lang="bash" inline>||</syntaxhighlight> ou <syntaxhighlight lang="bash" inline>&&</syntaxhighlight>. | ||
==Authentification== | ==Authentification== | ||
Ligne 159 : | Ligne 159 : | ||
<img src="https://doc.ycharbi.fr/fichiers/services/mandataire/traefik/images/Schéma_exemple_Traefik_http_auth.svg" alt="Schéma logique Traefik" style="display: block; width: 60%; height:auto; margin-left:auto; margin-right:auto;"/> | <img src="https://doc.ycharbi.fr/fichiers/services/mandataire/traefik/images/Schéma_exemple_Traefik_http_auth.svg" alt="Schéma logique Traefik" style="display: block; width: 60%; height:auto; margin-left:auto; margin-right:auto;"/> | ||
Pour ce faire, nous allons créer un fichier ''htpasswd'' (utilitaire présent dans le paquet < | Pour ce faire, nous allons créer un fichier ''htpasswd'' (utilitaire présent dans le paquet <syntaxhighlight lang="bash" inline>apache2-utils</syntaxhighlight>): | ||
htpasswd -c /opt/traefik/passwd/groupe1 ycharbi | htpasswd -c /opt/traefik/passwd/groupe1 ycharbi | ||
{{attention| Si vous voulez ajouter un utilisateur, utilisez la commande suivante : < | {{attention| Si vous voulez ajouter un utilisateur, utilisez la commande suivante : <syntaxhighlight lang="bash" inline>htpasswd /opt/traefik/passwd/groupe1 nmorin</syntaxhighlight>. L'usage du paramètre <syntaxhighlight lang="bash" inline>-c</syntaxhighlight> ne devant être utilisé que pour la création du fichier, sous peine de l'écraser. De plus, il faut impérativement relancer le service pour prendre en compte tout ajout/modification/suppression.}} | ||
Un ''middleware'' est unique au sein de ''Traefik'', bien qu'il soit possible de mettre la section dédiée directement dans l'hôte concerné, il est plus judicieux de leur créer un fichier propre afin de pouvoir piocher dedans les groupes d'utilisateurs pour les authentifications: | Un ''middleware'' est unique au sein de ''Traefik'', bien qu'il soit possible de mettre la section dédiée directement dans l'hôte concerné, il est plus judicieux de leur créer un fichier propre afin de pouvoir piocher dedans les groupes d'utilisateurs pour les authentifications: | ||
Ligne 169 : | Ligne 169 : | ||
vim /opt/traefik/config/vhosts/middlewares.toml | vim /opt/traefik/config/vhosts/middlewares.toml | ||
< | <syntaxhighlight lang="yaml"> | ||
# Service de type http | # Service de type http | ||
[http] | [http] | ||
Ligne 175 : | Ligne 175 : | ||
[http.middlewares.mon_auth.basicAuth] # Création d'un middleware nommé "mon_auth" de type "basicAuth" | [http.middlewares.mon_auth.basicAuth] # Création d'un middleware nommé "mon_auth" de type "basicAuth" | ||
usersFile = "/opt/traefik/passwd/groupe1" # Définit l'arborescence du fichier htpasswd | usersFile = "/opt/traefik/passwd/groupe1" # Définit l'arborescence du fichier htpasswd | ||
</ | </syntaxhighlight> | ||
Puis nous allons reprendre le fichier < | Puis nous allons reprendre le fichier <syntaxhighlight lang="bash" inline>/opt/traefik/config/vhosts/ma_page.toml</syntaxhighlight>: | ||
< | <syntaxhighlight lang="yaml"> | ||
[http] | [http] | ||
[http.routers] | [http.routers] | ||
Ligne 191 : | Ligne 191 : | ||
[[http.services.ma_page.loadBalancer.servers]] | [[http.services.ma_page.loadBalancer.servers]] | ||
url = "http://[2001:db8:0:180::a0]" | url = "http://[2001:db8:0:180::a0]" | ||
</ | </syntaxhighlight> | ||
==Répartition de charges== | ==Répartition de charges== | ||
Ligne 200 : | Ligne 200 : | ||
L'ajout d'un serveur dans le système de répartition de charge est très simple. Il faut seulement déclarer un autre serveur dans le service. La répartition de charge utilise l'algorithme d'ordonnancement [https://fr.wikipedia.org/wiki/Round-robin_(informatique) Round-robin]. | L'ajout d'un serveur dans le système de répartition de charge est très simple. Il faut seulement déclarer un autre serveur dans le service. La répartition de charge utilise l'algorithme d'ordonnancement [https://fr.wikipedia.org/wiki/Round-robin_(informatique) Round-robin]. | ||
Reprenons notre fichier < | Reprenons notre fichier <syntaxhighlight lang="bash" inline>/opt/traefik/config/vhosts/ma_page.toml</syntaxhighlight> : | ||
< | <syntaxhighlight lang="yaml"> | ||
[http] | [http] | ||
[http.routers] | [http.routers] | ||
Ligne 216 : | Ligne 216 : | ||
[[http.services.ma_page.loadBalancer.servers]] # Déclaration d'un autre serveur | [[http.services.ma_page.loadBalancer.servers]] # Déclaration d'un autre serveur | ||
url = "http://[2001:db8:0:180::a1]" # URL vers mon serveur 2 MaPage | url = "http://[2001:db8:0:180::a1]" # URL vers mon serveur 2 MaPage | ||
</ | </syntaxhighlight> | ||
===Avec persistance de sessions=== | ===Avec persistance de sessions=== | ||
''Traefik'' nous offre la possibilité de gérer la persistance de sessions sur un serveur de manière très simple. Il faut simplement ajouter la valeur < | ''Traefik'' nous offre la possibilité de gérer la persistance de sessions sur un serveur de manière très simple. Il faut simplement ajouter la valeur <syntaxhighlight lang="bash" inline>.sticky.cookie</syntaxhighlight> lors de la déclaration de notre service. | ||
{{info|La persistance de sessions permet d'allouer un client au premier serveur que le ''Round-robin'' lui aura fait joindre. La technique s'appuie sur la génération et l'envoi d'un cookie au navigateur du client (cela ne fonctionne donc pas avec ''curl'' ou ''wget''). Celui-ci présente ce cookie au serveur mandataire qui retransmet sa requête au même serveur qu'au premier échange.}} | {{info|La persistance de sessions permet d'allouer un client au premier serveur que le ''Round-robin'' lui aura fait joindre. La technique s'appuie sur la génération et l'envoi d'un cookie au navigateur du client (cela ne fonctionne donc pas avec ''curl'' ou ''wget''). Celui-ci présente ce cookie au serveur mandataire qui retransmet sa requête au même serveur qu'au premier échange.}} | ||
Toujours dans notre fichier < | Toujours dans notre fichier <syntaxhighlight lang="bash" inline>/opt/traefik/config/vhosts/ma_page.toml</syntaxhighlight>: | ||
< | <syntaxhighlight lang="yaml"> | ||
# Service de type http | # Service de type http | ||
[http] | [http] | ||
Ligne 240 : | Ligne 240 : | ||
[[http.services.ma_page.loadBalancer.servers]] | [[http.services.ma_page.loadBalancer.servers]] | ||
url = "http://[2001:db8:0:180::a1]" | url = "http://[2001:db8:0:180::a1]" | ||
</ | </syntaxhighlight> | ||
==HTTPS== | ==HTTPS== | ||
Ligne 254 : | Ligne 254 : | ||
vim /opt/traefik/config/traefik.toml | vim /opt/traefik/config/traefik.toml | ||
< | <syntaxhighlight lang="yaml"> | ||
[global] | [global] | ||
sendAnonymousUsage = false | sendAnonymousUsage = false | ||
Ligne 282 : | Ligne 282 : | ||
[entryPoints.https] # Permet de déclarer un autre point d'entrée nommé "https" | [entryPoints.https] # Permet de déclarer un autre point d'entrée nommé "https" | ||
address = ":443" # Permet de déclarer le port d'entrée 443 | address = ":443" # Permet de déclarer le port d'entrée 443 | ||
</ | </syntaxhighlight> | ||
Nous allons ajouter un nouveau fichier pour définir les propriétés pas défaut de notre ''TLS'': | Nous allons ajouter un nouveau fichier pour définir les propriétés pas défaut de notre ''TLS'': | ||
Ligne 288 : | Ligne 288 : | ||
vim /opt/traefik/config/vhosts/tls.toml | vim /opt/traefik/config/vhosts/tls.toml | ||
< | <syntaxhighlight lang="yaml"> | ||
[tls.options] | [tls.options] | ||
[tls.options.default] | [tls.options.default] | ||
Ligne 298 : | Ligne 298 : | ||
curvePreferences = ["x25519", "CurveP521", "CurveP384"] # Définition des algorithmes d'échanges de clés accéptés par le serveur | curvePreferences = ["x25519", "CurveP521", "CurveP384"] # Définition des algorithmes d'échanges de clés accéptés par le serveur | ||
preferServerCipherSuites = true # Imposer l'utilisation des suites cryptographiques définies par le serveur | preferServerCipherSuites = true # Imposer l'utilisation des suites cryptographiques définies par le serveur | ||
</ | </syntaxhighlight> | ||
''Note: Il est à précisé que GoLang ne permet pas de configurer de suites cryptographiques pour le [https://golang.org/doc/go1.12#tls_1_3 TLS 1.3]. Les développeurs du langage se justifient par le fait qu'elles sont définits dans la RFC 8446, respectés à la lettres et concidérées comme sûr donc y'a pas de problèmes... Personellement je trouve ça moyen surtout quand l'AES 128 bits est le choix par défaut... Ce n'est peut-être que temporaire, l'ajout de ce protocole datant de la version 1.12 du langage Go (on en est à la 1.13 au moment de la rédaction de ce paragraphe).'' | ''Note: Il est à précisé que GoLang ne permet pas de configurer de suites cryptographiques pour le [https://golang.org/doc/go1.12#tls_1_3 TLS 1.3]. Les développeurs du langage se justifient par le fait qu'elles sont définits dans la RFC 8446, respectés à la lettres et concidérées comme sûr donc y'a pas de problèmes... Personellement je trouve ça moyen surtout quand l'AES 128 bits est le choix par défaut... Ce n'est peut-être que temporaire, l'ajout de ce protocole datant de la version 1.12 du langage Go (on en est à la 1.13 au moment de la rédaction de ce paragraphe).'' | ||
Ligne 304 : | Ligne 304 : | ||
{{attention|N'oubliez pas que comme nous avons modifié le fichier de configuration principal ainsi qu'un fichier autre qu'un routeur ou un service, il faut relancer ''Traefik'' pour que la prise en compte de la configuration soit effective.}} | {{attention|N'oubliez pas que comme nous avons modifié le fichier de configuration principal ainsi qu'un fichier autre qu'un routeur ou un service, il faut relancer ''Traefik'' pour que la prise en compte de la configuration soit effective.}} | ||
Dans le fichier < | Dans le fichier <syntaxhighlight lang="bash" inline>/opt/traefik/config/vhosts/ma_page.toml</syntaxhighlight> : | ||
< | <syntaxhighlight lang="yaml"> | ||
[http] | [http] | ||
[http.routers] | [http.routers] | ||
Ligne 326 : | Ligne 326 : | ||
certFile = "/opt/traefik/tls/mapage.jmador.yo/mapage.jmador.yo.crt" # Chemin d'accès au certificat | certFile = "/opt/traefik/tls/mapage.jmador.yo/mapage.jmador.yo.crt" # Chemin d'accès au certificat | ||
keyFile = "/opt/traefik/tls/mapage.jmador.yo/mapage.jmador.yo.key" # Chemin d'accès à la clé du certificat | keyFile = "/opt/traefik/tls/mapage.jmador.yo/mapage.jmador.yo.key" # Chemin d'accès à la clé du certificat | ||
</ | </syntaxhighlight> | ||
''Note: la génération des certificats est expliquée dans la documentation concernant [[Openssl#Cr.C3.A9ation_d.27un_couple_de_cl.C3.A9s|OpenSSL]]. Prenez garde aux permissions de vos certificats. L'utilisateur "traefik" doit en être le propriétaire.'' | ''Note: la génération des certificats est expliquée dans la documentation concernant [[Openssl#Cr.C3.A9ation_d.27un_couple_de_cl.C3.A9s|OpenSSL]]. Prenez garde aux permissions de vos certificats. L'utilisateur "traefik" doit en être le propriétaire.'' | ||
Ligne 337 : | Ligne 337 : | ||
Comme nous pouvons le voir sur le schéma ci-dessus, il faut que l'on déclare un nouveau ''middlewares''. | Comme nous pouvons le voir sur le schéma ci-dessus, il faut que l'on déclare un nouveau ''middlewares''. | ||
Reprenons notre fichier < | Reprenons notre fichier <syntaxhighlight lang="bash" inline>/opt/traefik/config/vhosts/middlewares.toml</syntaxhighlight>: | ||
< | <syntaxhighlight lang="yaml"> | ||
[http] | [http] | ||
[http.middlewares] | [http.middlewares] | ||
Ligne 347 : | Ligne 347 : | ||
scheme = "https" # Redirection vers https | scheme = "https" # Redirection vers https | ||
permanent = true # Permet l'envoie d'un code HTTP 301 | permanent = true # Permet l'envoie d'un code HTTP 301 | ||
</ | </syntaxhighlight> | ||
Puis, dans notre fichier d'hôte < | Puis, dans notre fichier d'hôte <syntaxhighlight lang="bash" inline>/opt/traefik/config/vhosts/ma_page.toml</syntaxhighlight>: | ||
< | <syntaxhighlight lang="yaml"> | ||
[http] | [http] | ||
[http.routers] | [http.routers] | ||
Ligne 377 : | Ligne 377 : | ||
certFile = "/opt/traefik/tls/mapage.jmador.yo/mapage.jmador.yo.crt" | certFile = "/opt/traefik/tls/mapage.jmador.yo/mapage.jmador.yo.crt" | ||
keyFile = "/opt/traefik/tls/mapage.jmador.yo/mapage.jmador.yo.key" | keyFile = "/opt/traefik/tls/mapage.jmador.yo/mapage.jmador.yo.key" | ||
</ | </syntaxhighlight> | ||
=Supervision= | =Supervision= | ||
''Traefik'' permet d'exporter ses métriques au format ''OpenMetrics'' afin d'être exploités par des outils de supervision tel que [[Prometheus]]. | ''Traefik'' permet d'exporter ses métriques au format ''OpenMetrics'' afin d'être exploités par des outils de supervision tel que [[Prometheus]]. | ||
Pour cela il faut ajouter les paramètres suivants à la fin du fichier < | Pour cela il faut ajouter les paramètres suivants à la fin du fichier <syntaxhighlight lang="bash" inline>/opt/traefik/config/traefik.toml</syntaxhighlight>: | ||
< | |||
<syntaxhighlight lang="bash"> | |||
[metrics] | [metrics] | ||
[metrics.prometheus] | [metrics.prometheus] | ||
</ | </syntaxhighlight> | ||
{{attention| Relancer ''Traefik'' pour la prise en compte de la configuration.}} | {{attention| Relancer ''Traefik'' pour la prise en compte de la configuration.}} |
Dernière version du 24 février 2023 à 20:05
Traefik est un logiciel permettant de faire un serveur mandataire inversé (reverse proxy) et pouvant faire de la répartition de charge (load balancer). Il est développé en Go et a la particularité de faire de la découverte automatique (toute les deux secondes par défaut) de fichiers de configurations (pas de redémarrage du service). Ceci a pour intérêt de permettre une actualisation du mandataire en agissant uniquement sur des fichiers et non le service lui-même. On peut alors imaginer une actualisation de la configuration du serveur par simple copier/coller de fichiers depuis un partage sans privilèges root par exemple.
ATTENTION
L'application Traefik évolue très rapidement. Le présent document traite de la version 2 de Traefik, les fichiers de configurations n'ont rien à voir.Schéma fonctionnel
Traefik traite les requêtes des clients en les faisant passer dans divers fonctions selon le schéma suivant:
<img src="https://doc.ycharbi.fr/fichiers/services/mandataire/traefik/images/Schéma_logique_Traefik.svg" alt="Schéma logique Traefik" style="display: block; width: 60%; height:auto; margin-left:auto; margin-right:auto;"/>
- EntryPoint : Permet la déclaration des ports d'entrés de Traefik. Habituellement 80 et 443
- Routers : Permet la déclaration de l'URL pour contacter le service
- Middlewares : Permet la modification du comportement de l'appel. Ex: Ajout d'une authentification
- Service : Permet la déclaration du serveur qui héberge le service
Installation
Traefik n'est pas présent dans les dépôts Debian Buster. Il va donc falloir le télécharger depuis son dépôt Git.
wget https://github.com/containous/traefik/releases/download/v2.2.1/traefik_v2.2.1_linux_amd64.tar.gz -P /tmp/ mkdir -p /opt/traefik/{config/vhosts,tls,passwd,logs} tar xzvf /tmp/traefik_v2.2.1_linux_amd64.tar.gz -C /opt/traefik/
Création de l'utilisateur du service
useradd --system --home-dir /opt/traefik --user-group --shell /usr/sbin/nologin traefik chown -R traefik:traefik /opt/traefik chmod -R g+w /opt/traefik
Création du service Systemd
vim /etc/systemd/system/traefik.service
[Unit]
Description=Traefik, circulez y'a rien à voir !
[Service]
RestartSec=2s
Type=simple
User=traefik
Group=traefik
WorkingDirectory=/opt/traefik
ExecStart=/opt/traefik/traefik --configFile=/opt/traefik/config/traefik.toml
Restart=always
CapabilityBoundingSet=CAP_NET_BIND_SERVICE
AmbientCapabilities=CAP_NET_BIND_SERVICE
[Install]
WantedBy=multi-user.target
Chargement du service au démarrage du système
systemctl daemon-reload systemctl enable traefik.service systemctl start traefik.service systemctl status traefik.service
Configuration de base
Le fichier de configuration de Traefik est au format TOML, mais peux être également au format JSON. Il y a donc deux noms de fichier recommandés suivant le langage utilisé :
traefik.toml
traefik.yml
Ce fichier est attendu dans l'une de ces arborescences :
/etc/traefik/
$HOME/.config
.
(Dans la même arborescence que le binaire)
Nous pouvons également définir à Traefik un fichier de configuration spécifique :
traefik --configFile=foo/bar/myconfigfile.toml
ATTENTION
Dans ce fichier, il est attendu une configuration statique. Une modification de celui-ci nécessitera une relance de Traefik pour qu'elles soient prisent en compte. Sont également concernés les fichiers étrangers aux différents hôtes virtuels comme par exemple middleware.toml et tls.toml que nous verrons plus bas. Seules les fichiers contenants les directives routers et services ne nécessites pas de redémarrage du service.Voici un exemple:
vim /opt/traefik/config/traefik.toml
# Configuration globale de Traefik
[global]
sendAnonymousUsage = false # Évite l'envoi d'informations à l'éditeur
# Configuration des journaux de Traefik
[log]
level = "DEBUG" # Niveau de journalisation [DEBUG|PANIC|FATAL|ERROR|WARN|INFO]
format = "common" # Format des journaux [common|json]
filePath = "/opt/traefik/logs/traefik.log" # Chemin d'accès au fichier de journalisation
# Configuration des journaux d'accès
[accessLog]
filePath = "/opt/traefik/logs/access.log" # Chemin d'accès au fichier de journalisation
# Configuration des fourniseurs
[providers]
[providers.file] # Fournisseur de type "fichier"
directory = "/opt/traefik/config/vhosts/" # Chemin d'accès du répertoire où sont stockés les fichiers des services
watch = true # Permet le chargement à chaud des modifications de fichiers de configuration des hôtes virtuels
# Configuration de l'API
[api]
dashboard = true # Permet d'activer le tableau de bord de Traefik
debug = false # Permet de désactiver le mode développeur de l'API
insecure = true # Permet d'activer l'accès à l'API via le port 8080 par défaut
# Configuration des points d'entrées de Traefik
[entryPoints]
[entryPoints.http] # Permet de déclarer un point d'entrée nommé "http"
address = ":80" # Permet de déclarer le port d'entrée
ATTENTION
Pour lesfilePath
des sections [log]
et [accessLog]
, il faudra prévoir une rotation du fichier journal (voir Logrotate) car Traefik ne gère pas cette fonction. Ceci est indispensable pour ne pas voir votre partition se remplir jusqu'à déni de service.Comme nous avons édité le fichier de configuration principal du serveur, il faut recharger le service
systemctl restart traefik.service
Fonctionnalités
L'outil permet un éventail de fonctionnalités souvent rencontrées dans des logiciels de ce type. Elles sont décrites dans un ou plusieurs fichiers. Un hôte étant définit par des sections, il est possible d'en combiner plusieurs en un seul fichier ou d'en faire un par fichier. Ceci est configuré dans le paramètre directory
de la directive [providers]
vu précédemment. Comme précisé par le paramètre watch
de cette même directive, ces fichiers sont appliqués au serveur à chaque enregistrements.
Parmi les fonctionnalités que nous avons explorées, nous pouvons noter la possibilité de faire:
- un mandataire inverse HTTP/HTTPS
- l'ajout d'une authentification HTTP
- un répartiteur de charge
Afin de simplifier la compréhension des fichiers d'exemples qui suivront, nous allons partir du principe que nous voulons mettre à disposition de visiteurs sur Internet, un site WEB simple en HTML. Ce site est hébergé sur deux serveurs, ce qui nous permettra de configurer une répartition de charge. Nous le configurerons tout d'abord en HTTP, lui appliquerons une authentification, mettrons en place la répartition de charge et le passerons en HTTPS.
HTTP
Dans cette section, nous allons aborder la mise en place d'une redirection simple en HTTP comme on le ferrai avec Haproxy.
<img src="https://doc.ycharbi.fr/fichiers/services/mandataire/traefik/images/Schéma_exemple_Traefik_http.svg" alt="Schéma logique Traefik" style="display: block; width: 60%; height:auto; margin-left:auto; margin-right:auto;"/>
Nous allons créer un fichier représentant le nom du service:
vim /opt/traefik/config/vhosts/ma_page.toml
# Service de type http
[http]
[http.routers] # Déclaration des routers
[http.routers.vers_ma_page] # Création d'un routeur nommé "vers_ma_page"
rule = "Host(`mapage.jmador.yo`)" # URL avec laquelle sera joint notre site web
service = "ma_page" # Nom du service (déclaré ci-dessous)
[http.services] # Déclaration des services
[http.services.ma_page.loadBalancer] # Création d'un service nommé "ma_page"
[[http.services.ma_page.loadBalancer.servers]] # Déclaration d'un serveur
url = "http://[2001:db8:0:180::a0]" # URL vers mon serveur MaPage
Vous pouvez noter le mot clé loadBalancer
à la ligne créant le service ([http.services.ma_page.loadBalancer]
). En fait, Traefik fait constament de la répartition de charge, même avec un seul hôte (ce qui revient à toujours envoyer les requêtes sur la même machine). La configuration d'une réelle répartition de charge consiste donc à ajouter un hôte, d'où la simplicité de mise en œuvre. Nous verrons ceci plus bas.
Il est également possible de faire des règles (paramètre rule
) avec plus de conditions en utilisant des structures conditionnelles telles que ||
ou &&
.
Authentification
Pour l’authentification, nous avons besoin d'un "middlewares" qui intercepte le lien pour demander un utilisateur et un mot de passe :
<img src="https://doc.ycharbi.fr/fichiers/services/mandataire/traefik/images/Schéma_exemple_Traefik_http_auth.svg" alt="Schéma logique Traefik" style="display: block; width: 60%; height:auto; margin-left:auto; margin-right:auto;"/>
Pour ce faire, nous allons créer un fichier htpasswd (utilitaire présent dans le paquet apache2-utils
):
htpasswd -c /opt/traefik/passwd/groupe1 ycharbi
ATTENTION
Si vous voulez ajouter un utilisateur, utilisez la commande suivante :htpasswd /opt/traefik/passwd/groupe1 nmorin
. L'usage du paramètre -c
ne devant être utilisé que pour la création du fichier, sous peine de l'écraser. De plus, il faut impérativement relancer le service pour prendre en compte tout ajout/modification/suppression.Un middleware est unique au sein de Traefik, bien qu'il soit possible de mettre la section dédiée directement dans l'hôte concerné, il est plus judicieux de leur créer un fichier propre afin de pouvoir piocher dedans les groupes d'utilisateurs pour les authentifications:
vim /opt/traefik/config/vhosts/middlewares.toml
# Service de type http
[http]
[http.middlewares] # Déclaration des middlewares
[http.middlewares.mon_auth.basicAuth] # Création d'un middleware nommé "mon_auth" de type "basicAuth"
usersFile = "/opt/traefik/passwd/groupe1" # Définit l'arborescence du fichier htpasswd
Puis nous allons reprendre le fichier /opt/traefik/config/vhosts/ma_page.toml
:
[http]
[http.routers]
[http.routers.vers_ma_page]
rule = "Host(`mapage.jmador.yo`)"
service = "ma_page"
middlewares = ["mon_auth"] # Définit les middlewares utilisés pour ce routeur
[http.services]
[http.services.ma_page.loadBalancer]
[[http.services.ma_page.loadBalancer.servers]]
url = "http://[2001:db8:0:180::a0]"
Répartition de charges
Nous allons voir la configuration de la répartition de charge. Plusieurs serveurs pourront êtres utilisés pour répondre de façon alternés aux clients. Attention, nous n'aborderons pas ici la notion de gestion de faillite (failover). Un serveur injoignable sera quand même utilisé dans la répartition et renvéra des erreurs aux clients.
<img src="https://doc.ycharbi.fr/fichiers/services/mandataire/traefik/images/Schéma_exemple_Traefik_http_auth_rep.svg" alt="Schéma logique Traefik" style="display: block; width: 60%; height:auto; margin-left:auto; margin-right:auto;"/>
L'ajout d'un serveur dans le système de répartition de charge est très simple. Il faut seulement déclarer un autre serveur dans le service. La répartition de charge utilise l'algorithme d'ordonnancement Round-robin.
Reprenons notre fichier /opt/traefik/config/vhosts/ma_page.toml
:
[http]
[http.routers]
[http.routers.vers_ma_page]
rule = "Host(`mapage.jmador.yo`)"
service = "ma_page"
middlewares = ["mon_auth"]
[http.services]
[http.services.ma_page.loadBalancer]
[[http.services.ma_page.loadBalancer.servers]]
url = "http://[2001:db8:0:180::a0]"
[[http.services.ma_page.loadBalancer.servers]] # Déclaration d'un autre serveur
url = "http://[2001:db8:0:180::a1]" # URL vers mon serveur 2 MaPage
Avec persistance de sessions
Traefik nous offre la possibilité de gérer la persistance de sessions sur un serveur de manière très simple. Il faut simplement ajouter la valeur .sticky.cookie
lors de la déclaration de notre service.
INFORMATION
La persistance de sessions permet d'allouer un client au premier serveur que le Round-robin lui aura fait joindre. La technique s'appuie sur la génération et l'envoi d'un cookie au navigateur du client (cela ne fonctionne donc pas avec curl ou wget). Celui-ci présente ce cookie au serveur mandataire qui retransmet sa requête au même serveur qu'au premier échange.Toujours dans notre fichier /opt/traefik/config/vhosts/ma_page.toml
:
# Service de type http
[http]
[http.routers]
[http.routers.vers_ma_page]
rule = "Host(`mapage.jmador.yo`)"
service = "ma_page"
middlewares = ["mon_auth"]
[http.services]
[http.services.ma_page.loadBalancer.sticky.cookie] # Création d'un service nommé "ma_page" avec gestion des cookies de session
[[http.services.ma_page.loadBalancer.servers]]
url = "http://[2001:db8:0:180::a0]"
[[http.services.ma_page.loadBalancer.servers]]
url = "http://[2001:db8:0:180::a1]"
HTTPS
Dans cette section nous ajouterons le support de TLS pour faire du HTTPS. Vous trouverez la documenation officielle sur le sujet ici ainsi que l'ensemble des suites cryptographiques configurables pour le chiffrement du flux et les algorithmes d'échange de clés basés sur les courbes ellyptiques (la syntaxes des algorithmes de la RFC 8446 est utilisable dans la configuration).
Simple
Le support de HTTPS se ferra en cohabitation avec HTTP. Les clients pourrons se connecter soit en clair, soit en chiffré.
<img src="https://doc.ycharbi.fr/fichiers/services/mandataire/traefik/images/Schéma_exemple_Traefik_https_auth_rep.svg" alt="Schéma logique Traefik" style="display: block; width: 60%; height:auto; margin-left:auto; margin-right:auto;"/>
Comme vous pouvez le voir dans le schéma ci-dessus, nous avons un nouveau point d'entrée sur le port 443. Il faut donc l'ajouter dans la configuration de base de Traefik.
vim /opt/traefik/config/traefik.toml
[global]
sendAnonymousUsage = false
# Configuration des journaux de Traefik
[log]
level = "DEBUG"
format = "common"
filePath = "/opt/traefik/logs/traefik.log"
[accessLog]
filePath = "/opt/traefik/logs/access.log"
[providers]
[providers.file]
directory = "/opt/traefik/config/vhosts/"
watch = true
[api]
dashboard = true
debug = false
insecure = true
[entryPoints]
[entryPoints.http]
address = ":80"
[entryPoints.https] # Permet de déclarer un autre point d'entrée nommé "https"
address = ":443" # Permet de déclarer le port d'entrée 443
Nous allons ajouter un nouveau fichier pour définir les propriétés pas défaut de notre TLS:
vim /opt/traefik/config/vhosts/tls.toml
[tls.options]
[tls.options.default]
# Définition des suites cryptographiques accéptés par le serveur
cipherSuites = [
"TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384",
"TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256"
]
curvePreferences = ["x25519", "CurveP521", "CurveP384"] # Définition des algorithmes d'échanges de clés accéptés par le serveur
preferServerCipherSuites = true # Imposer l'utilisation des suites cryptographiques définies par le serveur
Note: Il est à précisé que GoLang ne permet pas de configurer de suites cryptographiques pour le TLS 1.3. Les développeurs du langage se justifient par le fait qu'elles sont définits dans la RFC 8446, respectés à la lettres et concidérées comme sûr donc y'a pas de problèmes... Personellement je trouve ça moyen surtout quand l'AES 128 bits est le choix par défaut... Ce n'est peut-être que temporaire, l'ajout de ce protocole datant de la version 1.12 du langage Go (on en est à la 1.13 au moment de la rédaction de ce paragraphe).
ATTENTION
N'oubliez pas que comme nous avons modifié le fichier de configuration principal ainsi qu'un fichier autre qu'un routeur ou un service, il faut relancer Traefik pour que la prise en compte de la configuration soit effective.Dans le fichier /opt/traefik/config/vhosts/ma_page.toml
:
[http]
[http.routers]
[http.routers.vers_ma_page]
entryPoints = ["https"] # On force l'accès via le point d'entrée "https"
rule = "Host(`mapage.jmador.yo`)"
service = "ma_page"
middlewares = ["mon_auth"]
[http.routers.vers_ma_page.tls] # On autorise les connexion "TLS"
[http.services]
[http.services.ma_page.loadBalancer.sticky.cookie]
[[http.services.ma_page.loadBalancer.servers]]
url = "http://[2001:db8:0:180::a0]"
[[http.services.ma_page.loadBalancer.servers]]
url = "http://[2001:db8:0:180::a1]"
[[tls.certificates]]
certFile = "/opt/traefik/tls/mapage.jmador.yo/mapage.jmador.yo.crt" # Chemin d'accès au certificat
keyFile = "/opt/traefik/tls/mapage.jmador.yo/mapage.jmador.yo.key" # Chemin d'accès à la clé du certificat
Note: la génération des certificats est expliquée dans la documentation concernant OpenSSL. Prenez garde aux permissions de vos certificats. L'utilisateur "traefik" doit en être le propriétaire.
Avec redirection de HTTP vers HTTPS
Le support d'HTTPS sera obligatoire, toute connexion en HTTP redirigera automatiquement le client en HTTPS.
<img src="https://doc.ycharbi.fr/fichiers/services/mandataire/traefik/images/Schéma_exemple_Traefik_redirect_https_auth_rep.svg" alt="Schéma logique Traefik" style="display: block; width: 60%; height:auto; margin-left:auto; margin-right:auto;"/>
Comme nous pouvons le voir sur le schéma ci-dessus, il faut que l'on déclare un nouveau middlewares.
Reprenons notre fichier /opt/traefik/config/vhosts/middlewares.toml
:
[http]
[http.middlewares]
[http.middlewares.mon_auth.basicAuth]
usersFile = "/opt/traefik/passwd/groupe1"
[http.middlewares.redirection_https.redirectScheme] # Création d'un middleware nommé "redirection_https" de type "redirectScheme"
scheme = "https" # Redirection vers https
permanent = true # Permet l'envoie d'un code HTTP 301
Puis, dans notre fichier d'hôte /opt/traefik/config/vhosts/ma_page.toml
:
[http]
[http.routers]
[http.routers.vers_ma_page_http] # Création d'un routeur nommé "vers_ma_page_http"
entryPoints = ["http"] # On force l'accès via le point d'entrée "http"
rule = "Host(`mapage.jmador.yo`)" # URL avec laquelle sera joint notre site web
service = "ma_page" # Nom du service (même si on y va pas)
middlewares = ["redirection_https"] # Définit les middlewares utilisés pour ce routeur
[http.routers.vers_ma_page_https] # Création d'un routeur nommé "vers_ma_page_https"
entryPoints = ["https"]
rule = "Host(`mapage.jmador.yo`)"
service = "ma_page"
middlewares = ["mon_auth"]
[http.routers.vers_ma_page_https.tls]
[http.services]
[http.services.ma_page.loadBalancer.sticky.cookie]
[[http.services.ma_page.loadBalancer.servers]]
url = "http://[2001:db8:0:180::a0]"
[[http.services.ma_page.loadBalancer.servers]]
url = "http://[2001:db8:0:180::a1]"
[[tls.certificates]]
certFile = "/opt/traefik/tls/mapage.jmador.yo/mapage.jmador.yo.crt"
keyFile = "/opt/traefik/tls/mapage.jmador.yo/mapage.jmador.yo.key"
Supervision
Traefik permet d'exporter ses métriques au format OpenMetrics afin d'être exploités par des outils de supervision tel que Prometheus.
Pour cela il faut ajouter les paramètres suivants à la fin du fichier /opt/traefik/config/traefik.toml
:
[metrics]
[metrics.prometheus]
ATTENTION
Relancer Traefik pour la prise en compte de la configuration.