Hébergement d’un serveur d’email

Je suis passé à l’hébergement de mes emails.
Gandi a récemment augmenté ses prix et pour mes besoins ça devenait délirant (250€ par an pour 4 comptes email)

Ayant déjà un serveur en ligne sur Internet, j’ai décidé de faire le pas. Cela fait un mois désormais et tout fonctionne bien. Pas de problème de mail rejeté, de spam ou autre. Donc je partage ma technique.

Je me suis orienté vers DockerMailServer. Une solution tout en un.

Je l’ai installé sur une Debian 12. Vu que c’est une solution basée sur un conteneur Linux, ça dépend assez peu de votre système.

Je vous invite à suivre leur documentation. Je vais juste éclaircir certains points. (Je reste novice dans l’email, corrigez moi si je me trompe)

Spam & SPF/DKIM/DMARC en 2 secondes

Une des plaies de l’email a longtemps été le spam. Dans le lot, on peut distinguer le spam de boites ayant pignon sur rue et celui envoyé de machines zombies. SPF/DKIM/DMARC s’attaque au second.

Ça ne résout pas le problème des publicités non sollicitées (avec domaine valide) qui tombent sous le coup du RGPD et qu’on peut normalement refuser, mais empêche de manière automatisée (sans coût humain) pas mal de spam envoyés depuis des machines zombies.

L’idée est que le détenteur d’un domaine désigne dans la zone DNS quelle est la machine (IP) autorisée à envoyer des emails pour ce domaine (SPF), que les emails soient signé (DKIM) et que quand un receveur juge un email ‘invalide’ en provenance de ce domaine ile puisse en notifier le domaine expéditeur (DMARC).

Je trouve cela plutôt une amélioration. Ca réduit la dépendance à des heuristiques pas terribles (serveur déjà connu -> privilégie les gros, filtre bayésien -> empêche les messages simples, non réception des messages silencieuse -> pousse à aller chez les gros qui ont du volume pour se rendre compte du problème )

Le tuto que je propose, vous permet d’être un expéditeur ‘en règle’ et c’est pas chronophage du tout à mettre en place. Donc c’est cool ;) Mes emails sortants ont tout de suite été acceptés par Gmail, Hotmail, etc… sans soucis.

Configuration DNS

Dans ma configuration j’ai un service « mail.jesuislibre.net » qui sert pour envoyer des mails depuis plusieurs domaines (example1.com, exemple2.com, etc…). J’ai trouvé que la documentation était assez peu claire sur ce schéma. Donc je vais partager un tutoriel ici:

Dans la zone DNS de chacun de vos domaines (example1.com, example2.com) vous avez besoin de définir ceci:

@ 10800 IN MX 10 mail.jesuislibre.net.
@ 10800 IN TXT "v=spf1 redirect=mail.jesuislibre.net"
_dmarc 10800 IN TXT "v=DMARC1; p=quarantine; sp=quarantine; fo=0; adkim=r; aspf=r; pct=100; rf=afrf; ri=86400; rua=mailto:reportdmarc@jesuislibre.net; ruf=mailto:reportdmarc@jesuislibre.net"
mail._domainkey 10800 IN TXT "v=DKIM1; h=sha256; k=rsa; " "p=MIICIjANBgkqhkiG9w0BAQEFAAOCAg8AMIICCgKCAgEAtKmXwOR6KgXm0eAVmk8z02FlJWlhfDoAW57UTJiyui3dDZhSqfJfhEcKi+DRkKzR2V+n2eGAhp8C9A4e0+Ad3/ey4ulyIvxzNRizp5nHgWdaWCscWz2ibTsdYH2R5in54clfDMiED0H3cDChtKjnIYTGEAA1dZbHYq/wmsO1TV9u2o4ria+tJtQuUZEe4Capwjgc3rMns0TWWx" "F8hApX3cVlRiYPLZ0qz63L6/9ZB/9bHRDdX9fvb3tqEv3w6IzcZSKZRFjg7hYDeGTQuPfHTDZt9AUCs4PcuTMf4JevGJ4x31K043hzIX/F8J8wpdV0oHJ0+OrXvPtC+ZCtIudIlHvhwVEiLa2VbDMhvMS0cuUCwQaP67dyZjcgN/8q4vY+Rg0QKHA1r29PjRiQD4egHwj6Wg5sFqRhWoPSSI9xvNV046w0K01nDfMyNYc5wNwN4E20J811" "voWQkYRqUlC3VLv/DXx9f2RstysPpM7RVsoVKOC7M04bJMwwCZgxPbKdUNN5kVpMCICZD+eGAlPXtfJ+h5YjwpbWX2toHGeF60IGhp00drBQmwduV9QJlx5A3XqbyyboE1Kpu9G8SK5D2X0Oc3VWWovYdbhu3+dTv6zHJGUSBEk1PMyG6qSJtpyKzvEk5Fw6TLQ7S0RMkJ9dOW5Dgfm/XIEXoNstavJHl2kCAwEAAQ=="

Il faut adapter les valeurs, mais je vous explique.

La première ligne définit où il faut adresser les emails (champ MX), ici ca redirige vers mail.jesuislibre.net (n’oubliez pas le ‘.’ à la fin)

La deuxième ligne définit les règles d’acception des emails ou SPF (Sender policy framework). Ici ca dit, il faut reprendre la règle définie dans la zone DNS de mail.jesuislibre.net (je vous la donne plus tard). Ca m’évite de recopier la règle sur tous les domaines (example1.com, example2.com) et mettre à jour la règle pour tous les domaines en même temps.

La troisième ligne correspond au champ DMARC. Ca dit quoi faire si l’email est rejeté car n’étant pas ‘conforme’. Ici mettre en en quarantaine (spam ou autre) et signaler l’incident en m’envoyant un message par email à reportdmarc@jesuislibre.net. sympa ;)

La quatrième défini la clé de vérification de signature des emails (DKIM). Tous les emails sortant envoyés pour ce domaine seront signés par un chiffrement asymétrique. Ce champ donne la clé publique de la signature. Ainsi le serveur de réception peut vérifier que l’email qu’il reçoit a été envoyé par un serveur « approuvé » par le détenteur de la config DNS du nom de domaine. Précision: le ‘mail’ ici n’a rien à voir avec le ‘mail’ de ‘mail.jesuislibre.net’. C’est juste un tag. Le mail est signé avec le tag ‘mail’ et c’est ainsi que le serveur de réception sait quelle clé publique aller chercher dans la zone DNS. Le couple de clé publique/privé est différent par domaine. Vous les trouverez dans les points de montage de DockerMailServer après avoir lancé ‘docker exec -ti <CONTAINER NAME> setup config dkim’

Du coup fans la zone DNS de mon domaine jesuislibre.net, je définis pour le sous domaine ‘mail’ (qui correspond donc à ‘mail.jesuislibre.net’) :

mail 10800 IN A 148.251.20.238
mail 10800 IN AAAA 2a01:4f8:201:81ef::2
mail 10800 IN TXT "v=spf1 a -all"

Première ligne l’adresse IP v4 du serveur email

Deuxième ligne, l’adresse IP v6 du serveur email

Troisième ligne, la règle SPF (à laquelle les autre domaines font référence si vous avez suivi). Ca dit : Si le mail n’est pas envoyé de l’IP (v4 ou v6) indiqué par le DNS pour mail.jesuislibre.net, alors considérer l’email comme invalide.

Email & Regexp

Un des trucs géniaux du service Gandi était son système d’alias avec des *. En gros, pouvait définir un alias ‘de*@jesuislibre.net’ et quand vous alliez dans un magasin physique et qu’on vous demandait un email vous n’aviez qu’à donner à la volée un email qui remplisse cette règle comme ‘dedarty@jesuislibre.net’. Si un jour, cet email fuite et devient un pot de miel pour spammeurs, il suffisait alors de rajouter une règle SIEVE (comprendre qui s’execute coté serveur) pour supprimer les emails ayant ce destinaire. Et on ne voyait plus jamais de spam coté client ;)

Avec DockerMailServer, on peut faire la même chose. On peut configurer des règles SIEVE. Et faire des alias à base de regexp.

Astuce cependant, la syntaxe regexp s’arrête au caractère ‘@’ de mes tests.

Voici comment j’écrirais la règle d’un alias regexp pour recevoir les emails ‘de*@jesuislibre.net’ dans le compte perso@example1.com :

/^de[.A-Za-z0-9-]+@example1.com/ perso@example1.com

Service en IPv6

Si vous exposez votre serveur en IPv6 avec la config par défaut, vous aurez comme symptôme que parfois vous ne recevez pas les emails, celui ci s’étant fait rejeté par votre serveur à cause de son origine douteuse.

Visiblement l’usage de docker en IPv6 n’est pas direct. J’ai du bidouiller en prenant exemple sur la doc encore plus récente que latest : edge . Voici le tutoriel:

Modifier ou créer le fichier /etc/docker/daemon.json :

{
  "ip6tables": true,
  "experimental" : true,
  "userland-proxy": true
}

redémarrer le service docker (systemctl restart docker)

Créer un sous réseau :

docker network create --ipv6 --subnet fd00:cafe:face:feed::/64 dms-ipv6

Référencer le sous réseau dans le config de DockerMailServer. Ici mon compose.yaml:

services:
  mailserver:
    image: ghcr.io/docker-mailserver/docker-mailserver:latest
    container_name: mailserver
    # Provide the FQDN of your mail server here (Your DNS MX record should point to this value)
    hostname: mail.jesuislibre.net
    env_file: mailserver.env
    # More information about the mail-server ports:
    # https://docker-mailserver.github.io/docker-mailserver/latest/config/security/understanding-the-ports/
    # To avoid conflicts with yaml base-60 float, DO NOT remove the quotation marks.
    environment:
      - SSL_TYPE=letsencrypt
    ports:
      - "25:25"    # SMTP  (explicit TLS => STARTTLS)
      - "143:143"  # IMAP4 (explicit TLS => STARTTLS)
      - "465:465"  # ESMTP (implicit TLS)
      - "587:587"  # ESMTP (explicit TLS => STARTTLS)
      - "993:993"  # IMAP4 (implicit TLS)
    volumes:
      - ./docker-data/dms/mail-data/:/var/mail/
      - ./docker-data/dms/mail-state/:/var/mail-state/
      - ./docker-data/dms/mail-logs/:/var/log/mail/
      - ./docker-data/dms/config/:/tmp/docker-mailserver/
      - /etc/localtime:/etc/localtime:ro
      - /etc/letsencrypt:/etc/letsencrypt
    restart: always
    stop_grace_period: 1m
    # Uncomment if using `ENABLE_FAIL2BAN=1`:
    # cap_add:
    #   - NET_ADMIN
    healthcheck:
      test: "ss --listening --tcp | grep -P 'LISTEN.+:smtp' || exit 1"
      timeout: 3s
      retries: 0
    networks:
      - dms-ipv6

networks:
  dms-ipv6:
   external: true

6 réactions sur “ Hébergement d’un serveur d’email ”

  1. Andy Swift

    Avez-vous eu des problèmes de réception de mails ?

    Je voulais faire pareil mais j’ai vite découvert que les serveurs de mail « inconnus » sont généralement bloqué par défaut par les filtres de spam, au point ou c’était pas vraiment faisable de gérer son propre serveur de mail.

    L’avez vous fait avec une adresse IP spéciale ? (pas un FAI résidentiel, par exemple)

  2. utux

    Pour avoir déjà installé des serveurs mail sur des hébergements low cost, je confirme que l’envoi se passe bien, c’est pas bloqué, surtout si comme expliqué dans l’article le SPF et DKIM sont bien configurés. Au pire il est possible de demander à se désinscrire des listes antispam. Il faut pas avoir peur de faire son propre serveur mail (du moins ça vaut le coup d’essayer).

    Je dirais que le plus gros problème avec le « tout docker » c’est pour déboguer quand ça commence à mal fonctionner. Je n’ai pas regardé le détail du projet, mais ça devient vite l’enfer quand on a des containers dans tous les sens, surtout quand il n’y a pas de centralisation des logs.

  3. ache

    J’héberge également mes e-mails sur un VPS d’OVH (deux car un de mes serveurs a brûlé ce qui m’a fait prendre conscience de l’importance de la redondance).

    J’ai effectivement eu des problèmes pour envoyer des e-mails chez plusieurs fournisseurs Allemands (par exemple telekom.de). Chose que j’ai réglé en leur envoyant un e-mail leur demandant de retirer mon IP de leur liste noire. En effet, ils se basent sur des listes un peu obscures sur le net et OVH est expressément visé par une de ses listes.

    Le plus gros fournisseur d’e-mail qui me pose problème est Microsoft. Je ne peux pas contacter une adresse Microsoft (@live et @hotmail, il semble que le problème ne se pose pas pour une entreprise ayant ses e-mails chez Microsoft avec un ndd personnalisé) sans que celle-ci m’ait en premier lieu contacté d’abord. Ça ne m’a pas beaucoup posé de problème.

    Le gros souci de mon infra est le coût. Un peu plus de 6€ par mois mais j’héberge plusieurs services, pas juste mes e-mails.

    La maintenance est assez légère (30min par mois je dirais sauf en cas de vrai gros pépin). Je n’utilise pas docker. J’ai un truc très flexible je trouve qui me permet de jouer un peu avec IMAP et surtout SMTP (surtout expérimenter).

    Bref, ce n’est pas fait pour tout le monde mais c’est quelque chose que je ne regrette pas.

  4. tuxicoman Auteur Article

    aucun problème de délivrabilité pour l’instant, comme indiqué dans l’article.
    J’utilise une machine chez Hetzner que j’ai depuis longtemps. Donc l’IP est ‘propre’.

  5. djib

    Le signe + est communément utilisé pour l’usage que tu décris : « de+darty@example.com » arrive dans le dossier Darty du mail « de@example.com » ou à défaut de dossier, la racine de la boite de réception. Exemples : YunoHost en auto-hébergement, mais aussi gmail, outlook.com…

Laisser un commentaire

Ce site utilise Akismet pour réduire les indésirables. En savoir plus sur comment les données de vos commentaires sont utilisées.