[OpenVPN] UDP et TCP avec Traefik

Tags: Informatique Tutoriel Traefik VPN Docker


Bonjour à tous,

Il y a 4 ans, j’avais écrit un article expliquant comment installer et utiliser OpenVPN en UDP sur un serveur. Puis en septembre 2018, je faisais un article à propos de l’utilisation d'OpenVPN sur smartphone.

Aujourd’hui, nous allons encore parler d’OpenVPN, mais cette fois-ci, pour utiliser à la fois l'UDP mais aussi le TCP. Nous allons notamment reprendre les bases du VPN, je trouve que mon propos à l’époque n’était pas forcément le plus clair pour expliquer ce qu’est et à quoi sert un VPN.

Qu’est-ce qu’un VPN ?

Un VPN (Virtual Private Network) est un réseau reliant directement deux ordinateurs distants.

Schéma explicatif d'un VPN
Schéma explicatif d'un VPN

Cette image ne provient pas de moi mais de VPN Monitor. J’ai ajouté des crédits de cette façon car j’avais été victime de hotlinking dans mon premier article sur le sujet.

Expliquons donc ce schéma !

Vous et votre ordinateur êtes sur la gauche et le serveur du VPN sur la droite. Le lien entre ces 2 parties est chiffré ce qui implique le fait que personne n’est capable de le comprendre.

Globalement, lorsque vous êtes connecté à un serveur VPN, vous allez naviguer sur internet en vous faisant passer pour ce serveur VPN (vous allez utiliser son adresse IP notamment). Donc tout le trafic entre vous et le serveur VPN est chiffré, en revanche, le trafic entre le serveur VPN et le serveur final ne l’est pas forcément, tout dépend de ce que vous faites.

Anonyme avec un VPN ?

Un serveur VPN ne vous rend absolument pas anonyme. Comme je le disais dans mon premier article, plutôt que ce soit votre opérateur qui soit au courant de ce que vous faites sur internet, ce sera votre fournisseur VPN ou l’hébergeur de votre serveur si vous avez votre propre serveur VPN.

En revanche, un serveur VPN avec une IP en France, vous permettra d’accéder à des services qui sont soit accessibles uniquement en France, soit qui ne sont pas accessibles là où vous vous trouvez.

Donc quand tous ces influenceurs vous vendent une promotion sur NordVPN pour que vous deveniez anonyme sur internet ou pour votre sécurité sur internet, c’est faux et complètement faux. Vous allez juste donner toutes vos informations (votre historique de navigation entre autres) à NordVPN en lieu et place de votre opérateur. En revanche, comme je l’ai dit précédemment, cela vous permettra d’avoir une IP dans un autre pays pour contourner certaines censures de certains pays par exemple.

Pourquoi un VPN ?

Accéder à un réseau à distance

Un VPN relie donc deux ordinateurs sur un même réseau. Prenons un exemple relativement d’actualité pour les télétravailleurs. Chez vous, vous avez votre PC relié à internet. Votre entreprise a un serveur (PC sans écran) relié à son réseau interne mais également à internet.

Le VPN n’est finalement qu’un lien entre ces 2 PC, ce qui vous permet de rentrer de manière sécurisée dans le réseau de votre entreprise.

Maitriser sa vie privée

Globalement si vous êtes dans votre pays, en déplacement vous avez la 4G (ou la 5G), vous faites donc confiance à votre opérateur mobile. Chez vous, vous êtes connecté à votre box, vous faites donc confiance à votre opérateur. Dans un train (en France), vous faites confiance à la SNCF (ou à son prestataire).

Bref, systématiquement, il faut comprendre qui a accès à vos données transitant sur internet.

Ensuite, il faut faire attention, lorsque vous tapez un mot de passe pour vous connecter sur un site, votre opérateur n’y a pas accès, il sait uniquement que vous communiquez avec ce site (mais n’a pas la notion des données qui transitent). Il existe cependant des solutions techniques pour empêcher à votre opérateur de savoir sur quels sites vous allez en chiffrant le premier échange que vous faites avec le serveur cible. C’est un sujet que j’ai abordé dans cet article.

Mais un VPN vous permet de mieux maîtriser votre vie privée. Si par exemple votre opérateur est Orange et que votre serveur VPN est sur votre serveur chez OVH vous avez le choix entre faire confiance à Orange ou à OVH.

Contourner les restrictions

En revanche, lorsque vous êtes à l’étranger dans un pays qui pratique la censure, ou que vous possédez des informations sensibles (un journaliste par exemple), la question ne sera plus entre Orange et OVH mais entre le pays en question et OVH (ou votre fournisseur VPN, ce sont des exemples). Dans ce cas, le fait d’utiliser un serveur VPN devient alors nécessaire (vous pouvez contourner la censure ou faire transiter vos informations sensibles sans que le gouvernement local ne soit au courant et que vous finissiez en prison ou ailleurs).

Maitriser votre DNS

Si vous ne savez pas ce qu’est un serveur DNS, je vous renvoie vers cet article.

Vous pouvez directement configurer les serveurs DNS que vous souhaitez sur votre périphérique, mais ce n’est pas toujours possible. Dans la configuration de votre VPN, vous pouvez choisir le DNS par lequel passeront toutes les requêtes DNS. De cette façon, toute connexion passant par le VPN utilisera également ce DNS.

Bloquer la pub sur smartphone

Si l’on reprend le dernier point, utiliser un serveur VPN revient à utiliser les serveurs DNS qui y sont configurés. Il suffit alors d’utiliser un serveur DNS qui filtre la publicité et les trackers et le fait de passer par le VPN utilisera ce serveur DNS et la publicité sera automatiquement bloquée (que ce soit dans votre navigateur ou vos applications).

Mise en place avec Traefik

Dans la suite de cet article, nous allons partir du principe que vous avez une architecture fonctionnelle avec Traefik au moins configurée sur le port 443. Si ce n’est pas le cas, j’ai déjà écrit un article, sinon la documentation vous sera fortement utile.

Pourquoi TCP + UDP ?

Nous allons faire en sorte que notre serveur VPN puisse fonctionner à la fois en UDP et en TCP.

L’UDP reste le protocole préconisé pour ce genre d’usages car le débit global montant et descendant sera par définition plus élevé. Le TCP impliquant par exemple des messages d’acquittement et des paquets plus gros ou plus nombreux pour s’assurer que tous les paquets soient bien arrivés. Pour ceux n’étant pas familiers avec ces protocoles, l’UDP reviendrait à envoyer une lettre classique par la Poste (rien ne garantit son arrivée) alors que le TCP reviendrait à envoyer une lettre avec accusé de réception (où vous ré-envoyez la lettre avec accusé de réception si tant que vous ne recevez pas l’accusé).

Par défaut avec OpenVPN, le trafic UDP passe sur le port 1194. Il peut arriver que ce port ne soit pas ouvert sur certains réseaux, c’est là que le protocole TCP vient à notre rescousse. En effet, le port 443 (souvent associé au protocole HTTPS) est donc quasiment toujours ouvert (pour justement faire passer le trafic HTTPS). On peut donc faire passer notre flux VPN par ce port, il ne sera donc pas filtré par les pare-feux.

Traefik sait gérer sans soucis le TCP et l’UDP. De plus, on peut avoir sur le port 443 nos services Web classiques en parallèle du serveur VPN.

On aura donc le flux UDP sur le port 1194 et le flux TCP sur le port 443. Et comme OpenVPN sait gérer plusieurs remote (serveurs) dans un même fichier .ovpn, on pourra mettre nos 2 remotes au sein du même fichier. Cela permettra à OpenVPN de basculer sur le second protocole quand le premier ne fonctionne pas.

Lorsque la connexion est établie avec le premier remote par exemple puis que ce lien tombe, OpenVPN fait automatiquement (après un certain laps de temps), la bascule sur le second remote.

En revanche, je n’ai pas pu faire de réel test de débit pour comparer les 2 protocoles. En effet, j’étais bridé par le débit de mon serveur. J’aurai pu limiter mon débit avec des règles TC mais je ne pense pas que ce soit réellement pertinent et valable.

L’image Docker OpenVPN

Ici, nous allons utiliser une image d’OpenVPN prête à l’emploi, il s’agit de kylemanna/openvpn. Elle possède l’avantage de packager OpenVPN avec tout ce dont on a besoin et notamment des scripts pour gérer les certificats des clients du serveur VPN. Le code source de cette image est disponible ici et les fameux scripts sont dans le dossier bin/.

L’inconvénient majeur de ce genre d’images est la fréquence des mises à jour. Si OpenVPN corrige une faille critique et qu’elle n’est pas rapidement répercutée, il faut alors regénérer nous-même l’image Docker avec la dernière version d’OpenVPN. C’est un point dont il faut avoir conscience et ne pas prendre à la légère.

Ouverture du port UDP avec Traefik

Comme je l’ai dit, je pars du principe que vous avez une instance de Traefik fonctionnelle et ouverte sur le port 443. Voici les étapes à suivre pour rajouter le port 1194 en UDP.

Dans le fichier de configuration statique de Traefik, il faut rajouter un entrypoint sur le port 1194 dédié à l’UDP. Dans le cas où on a déjà les ports 80 (redirigé vers le port 443) et 443, cela nous donne:

[entryPoints]
    [entryPoints.web]
        address = ":80"

    [entryPoints.web.http]
        [entryPoints.web.http.redirections]
            [entryPoints.web.http.redirections.entryPoint]
                to = "websecure"
                scheme = "https"

    [entryPoints.websecure]
        address = ":443"

    [entryPoints.openvpn]
        address = ":1194/udp"

Il faut ensuite rajouter le port 1194 à notre image Traefik. Personnellement, cela se passe dans son fichier docker-compose:

        container_name: "traefik"
        ports:
            - "80:80"
            - "443:443"
            - "1194:1194/udp"

Je vous laisse donc rajouter le port 1194 en vous adaptant à votre architecture.

Ensuite, il suffit de redémarrer Traefik, sur l’interface Web (si vous l’avez activé), vous devriez vous apparaître le port 1194.

Les 3 entrypoints fonctionnels
Les 3 entrypoints fonctionnels

Le docker-compose

Cet exemple est issu du docker-compose que j’utilise, il faut évidemment l’adapter à votre situation. Je pense notamment:

  • au dossier data/
  • au réseau traefik-frontend qui est celui que j’utilise pour Traefik
  • aux noms des entrypoints (websecure étant mon entrypoint sur le port 443 et openvpn celui sur le port UDP 1194).
version: '3.7'

services:
    openvpn-tcp:
        image: kylemanna/openvpn:2.4
        container_name: "openvpn-tcp"
        command: ovpn_run --proto tcp
        volumes:
            - ./data/openvpn:/etc/openvpn
        networks:
            - traefik-frontend
        cap_add:
            - NET_ADMIN
        restart: always
        labels:
            - "traefik.enable=true"
            - "traefik.docker.network=traefik-frontend"
            - "traefik.tcp.services.openvpn-tcp.loadBalancer.server.port=1194"
            # openvpn does not not support SNI, we provide wildcard
            - "traefik.tcp.routers.openvpn-tcp.rule=HostSNI(`*`)"
            - "traefik.tcp.routers.openvpn-tcp.entrypoints=websecure"

    openvpn-udp:
        image: kylemanna/openvpn:2.4
        container_name: "openvpn-udp"
        command: ovpn_run --proto udp
        volumes:
            - ./data/openvpn:/etc/openvpn
        networks:
            - traefik-frontend
        cap_add:
            - NET_ADMIN
        restart: always
        labels:
            - "traefik.enable=true"
            - "traefik.docker.network=traefik-frontend"
            - "traefik.udp.services.openvpn-udp.loadBalancer.server.port=1194"
            - "traefik.udp.routers.openvpn-udp.service=openvpn-udp"
            - "traefik.udp.routers.openvpn-udp.entrypoints=openvpn"

networks:
    traefik-frontend:
        name: traefik-frontend

On voit par exemple que j’utilise le même dossier data/. Cela permet aux 2 serveurs (TCP et UDP) de fonctionner avec les mêmes clients.

L’ajout de NET_ADMIN est nécessaire pour que le serveur VPN se connecte sur le socket de la machine hôte (avec la commande getsockopt).

Ici, je fixe l’image Docker sur sa version 2.4, je vous laisse gérer cela comme vous le faîtes avec vos autres images. C’est un sujet que j’ai déjà abordé ici et je ferai sûrement un article un jour sur la façon dont je gère tout cela.

Génération du certificat racine et ajout d’un client

Avant de démarrer nos 2 serveurs VPN, voici les quelques commandes à effectuer.

Génération de la configuration d’OpenVPN

# vpn.example.com est l'adresse du serveur
# Vous pouvez choisir les DNS que vous voulez, j'ai mis ici ceux de Cloudflare.
# Pour afficher les autres options:
# docker-compose run --rm openvpn-tcp ovpn_genconfig -h
docker-compose run --rm openvpn-tcp ovpn_genconfig -u tcp://vpn.example.com:443 -n "1.1.1.1" -n "1.0.0.1"

Le script n’est pas parfait et ajoute une option dépréciée (même si c’est pour la désactiver, OpenVPN n’a pas le même comportement si elle est totalement absente de la configuration ou si elle est présente mais désactivée). On édite donc le fichier openvpn.conf généré dans le dossier data/ et on supprime les 2 lignes suivantes:

comp-lzo no
push "comp-lzo no"

Comme on génère la configuration en précisant TCP, le protocole est rajouté dans la configuration, par soucis de propreté, on supprime alors la ligne proto tcp (cela n’a pas d’incidence car on démarre les serveurs avec l’option --proto udp ou --proto tcp).

Création de l’autorité de certification TLS

# Sauvegardez bien le mot de passe que vous renseignerez.
# Pour le "Common Name", vous pouvez mettre l'adresse du serveur que vous avez renseigné précédemment (ici vpn.example.com)
docker-compose run --rm openvpn-tcp ovpn_initpki

Une fois cette étape passée, on peut démarrer les serveurs VPN avec la commande docker-compose up -d.

Génération du certificat d’un client

# on utilise une variable globale par simplicité
export CLIENTNAME="nom-du-client"
docker-compose run --rm openvpn-tcp easyrsa build-client-full $CLIENTNAME nopass
docker-compose run --rm openvpn-tcp ovpn_getclient $CLIENTNAME > $CLIENTNAME.ovpn

On a alors un fichier nom-du-client.ovpn. Si on l’ouvre, on peut voir un seul remote: remote vpn.example.com 443 tcp. On rajoute alors l’UDP juste avant celui-ci (OpenVPN essaie d’abord le premier remote dans l’ordre), on obtient alors:

remote vpn.example.com 1194 udp
remote vpn.example.com 443 tcp

On peut ensuite importer ce fichier dans notre client OpenVPN et lancer la connexion.

Conclusion

Et voilà, on a donc un serveur OpenVPN (du point de vue externe, il n’y en a qu’un seul alors qu’en réalité, on en a un par protocole) qui gère à la fois l’UDP et le TCP et qui passe du premier au second selon les blocages sur le réseau.

C’est la première fois que j’utilise le protocole UDP avec Traefik, force est de constater que c’est d’une simplicité enfantine ! Évidemment, j’avais fait une boulette et j’avais mis 1194:1994 dans la définition des ports, ce qui faisait que Traefik renvoyait le trafic entrant sur le mauvais port … et aucun log qui ne nous informe de quoi que ce soit …

J’espère que cet article vous a été utile, il m’aura pris pas mal de temps afin d’obtenir un résultat clair et un tutoriel simple et fonctionnel (du moins je l’espère) ! N’hésitez pas à me faire des retours avec la section des commentaires ci-dessous.

Commentaires




Ailleurs sur le Web


SQLite is not a toy database | Anton Zhiyanov

C'est vrai qu'il y a pas mal de temps, je faisais partie de ceux qui avaient un à-priori sur SQLite. Après, pour une instance de home-assistant, SQLite ne tient pas la route là où MariaDB tient les performances sans soucis (sur Raspberry Pi 3 il y …

via Shaarli le 29 mars 2021

Deux mots sur les NFT

Un article vraiment bien rédigé pour ceux qui veulent savoir ce que sont les NFT (Non-Fungible-Token).

via Shaarli le 19 mars 2021

OVH brûle, Internet hurle

Je rejoins à 100% cette première analyse à chaud ...

via Shaarli le 11 mars 2021

Généré avec openring


Recettes de gourmands


Pizza poulet curry

Une pizza plus estivale, mais qui sait rester gourmande !

via cooking.pofilo.fr le 31 mai 2020

Fajitas

A manger avec les mains, évidemment !

via cooking.pofilo.fr le 24 mai 2020

Pad Thai

Une recette longue mais qui reste relativement simple qui devrait ravir tous les gourmands !

via cooking.pofilo.fr le 17 mai 2020

Généré avec openring