---
categories: email spam
title: Howto OpenDKIM
...

* Documentation : <http://opendkim.org/docs.html>
* opendkim.conf(5) : <http://opendkim.org/opendkim.conf.5.html>

[DKIM (DomainKeys Identified Mail)](https://fr.wikipedia.org/wiki/DomainKeys_Identified_Mail) est une norme pour ajouter une signature cryptographique dans les entêtes d'un email envoyé.
La signature se fait à partir à de l'expéditeur d'entête (`From:` d'un email), des entêtes au choix (sujet, date, etc.) et le corps du message.
Cela utilise aussi une clé publique stockée dans un enregistrement DNS TXT.
La norme DKIM remplace DomainKey (utilisé à l'origine par Yahoo) qui l'on considère désormais comme obsolète.

[OpenDKIM](http://opendkim.org/) est logiciel libre pour vérifier et générer des signatures DKIM. Il implémente un service milter lui permettant notamment d'être utilisé avec [Postfix](HowtoPostfix).


## Installation

~~~
# apt install opendkim opendkim-tools
# adduser opendkim ssl-cert
~~~

On ajoute la ligne suivante dans `/etc/default/opendkim` :

~~~
SOCKET="inet:8891@localhost"
~~~

> *Note* : on peut également utiliser une socket Unix.

> *Note 2* : en Debian 9, l'unité systemd charge seulement `/etc/opendkim.conf`, `/etc/default/opendkim` n'est plus utilisé.

La configuration principale se trouve dans le fichier `/etc/opendkim.conf` :

~~~
UserID                  opendkim:opendkim
Syslog                  yes
#SyslogSuccess          yes
#LogWhy                 yes
UMask                   007
KeyTable                refile:/etc/opendkim/KeyTable
SigningTable            refile:/etc/opendkim/SigningTable
InternalHosts           /etc/opendkim/dkim.peers
Mode                    s
OversignHeaders         From
#DisableADSP             true
Socket                  inet:8891@localhost
PidFile               /var/run/opendkim/opendkim.pid
~~~

Le fichier `SigningTable` contient la liste des domaines qui vont générer des signatures DKIM, et les sélecteurs associés.
Un **sélecteur** est un mot clé à choisir qui sera associé à la signature DKIM et servira notamment pour l'enregistrement DNS TXT qui stocke la clé publique.
Si l'on a plusieurs serveurs de messagerie, on pourra des sélecteurs différents, et donc des clés et un enregistrement DNS différents également.

~~~
*@example.com foo._domainkey.example.com
*@example.org bar2018._domainkey.example.org
~~~

Le fichier `KeyTable` contient les chemins vers les clés privées :

~~~
foo._domainkey.example.com example.com:foo:/etc/ssl/private/dkim_example.com.key
bar2018._domainkey.example.org example.org:bar2018:/etc/ssl/private/dkim_example.org.key
~~~

Pour générer les clés, on utilise la commande :

~~~
# opendkim-genkey -D /etc/ssl/private/ -d example.com -s foo -v
opendkim-genkey: generating private key
opendkim-genkey: private key written to foo.private
opendkim-genkey: extracting public key
opendkim-genkey: DNS TXT record written to foo.txt

# mv /etc/ssl/private/foo.private /etc/ssl/private/dkim_example.com.key
# chown opendkim:opendkim /etc/ssl/private/dkim_example.com.key
# chmod 640 /etc/ssl/private/dkim_example.com.key
~~~

Il faut ensuite publier l'enregistrement DNS à partir du fichier `/etc/ssl/private/foo.txt` généré, en ajoutant la ligne suivante dans la zone DNS du domaine en question :

~~~
foo._domainkey IN TXT "v=DKIM1; k=rsa; p=MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQDcJOD4s/XyvarbBPTyzIKaAsm4BWv9jd/brLdIOBxq177CN17GTQP6eJgAVpEFnMvxVgRNXYQzVJZF5FvownJxHjmma0seVRs8vSwwRbD1OlhSRCjlBWvI3zmyqf8MQVU0K6Zs6NJT5rHEeW3nz6e6c5UtpIjKogshawwMnTvtfwIDAQAB" ; ----- DKIM key foo for example.com
~~~

On utilise le fichier `/etc/opendkim/dkim.peers` pour mettre la liste des adresses IP autorisées à envoyer des messages pour lesquels on va rajouter une signature DKIM (a priori des serveurs SMTP internes uniquement) :

~~~
127.0.0.1
::1
192.0.2.142
192.0.2.0/25
~~~

On ajuste les droits ainsi :

~~~
# chown -R opendkim:opendkim /etc/opendkim*
# chmod 640 /etc/opendkim.conf /etc/opendkim/*
# chmod 750 /etc/opendkim/
~~~

Et l'on peut enfin démarrer le démon :

~~~
# systemctl start opendkim

# opendkim -V | head -4
opendkim: OpenDKIM Filter v2.11.0
        Compiled with OpenSSL 1.1.0f  25 May 2017
        SMFI_VERSION 0x1000001
        libmilter version 1.0.1

# systemctl status opendkim
● opendkim.service - OpenDKIM DomainKeys Identified Mail (DKIM) Milter
   Loaded: loaded (/lib/systemd/system/opendkim.service; enabled; vendor preset: enabled)
     Docs: man:opendkim(8)
           man:opendkim.conf(5)
           man:opendkim-genkey(8)
           man:opendkim-genzone(8)
           man:opendkim-testadsp(8)
           man:opendkim-testkey
           http://www.opendkim.org/docs.html
  Process: 13917 ExecStart=/usr/sbin/opendkim -x /etc/opendkim.conf (code=exited, status=0/SUCCESS)
 Main PID: 13918 (opendkim)
    Tasks: 6 (limit: 7372)
   CGroup: /system.slice/opendkim.service
           └─13918 /usr/sbin/opendkim -x /etc/opendkim.conf
~~~

## Configuration avec Postfix

Pour configurer avec [Postfix](HowtoPostfix) on ajoute simplement les instructions suivantes dans le fichier `/etc/postfix/main.cf` :

~~~
smtpd_milters = inet:127.0.0.1:8891
non_smtpd_milters = inet:127.0.0.1:8891
#milter_default_action=accept
# Pour accélérer les signatures, pas d'attente pour contacter le milter
in_flow_delay = 0s
~~~

Cela entraînera l'ajout d'un entête `DKIM-Signature:` à tous les messages qui correspondent à la configuration d'OpenDKIM.

Si vous utilisez l'option `Mode sv` ou `Mode v` dans la configuration d'OpenDKIM, cela entraînera une vérification des signatures DKIM des emails reçus, et l'ajout d'un entête du type :

~~~
Authentication-Results: antispam.example.com; dkim=pass
        reason="1024-bit key; unprotected key"
        header.d=example.com header.i=@example.com header.b=lJ7oU+Kk;
        dkim-adsp=pass; dkim-atps=neutral
~~~


## Vérifications

### Vérifier sa configuration

On peut vérifier que sa configuration est correcte, notamment son enregistrement DNS (si la commande ne renvoie rien, c'est que c'est OK) :

~~~
# opendkim-testkey -d example.com -s foo -k /etc/ssl/private/dkim_example.com.key -v
opendkim-testkey: /etc/ssl/private/dkim_example.com.key: WARNING: unsafe permissions
opendkim-testkey: key not secure
~~~

> *Note* : vous pouvez ignorer le warning des permissions si vous avez correctement ajusté les droits comme précisé plus haut

### Vérifier la présence de DKIM-Signature

Il faut envoyer un email de test avec un expéditeur d'entête correct ; par exemple en ligne de commande :

~~~
$ telnet 127.0.0.1 25
HELO example.com
MAIL FROM: <noreply@example.com>
RCPT TO: <foo@example.org>
DATA
From: <noreply@example.com>
To: Foo <foo@example.org>
Subject: test DKIM

Ceci est un test
.
~~~

L'email devrait avoir un entête supplémentaire du type :

~~~
DKIM-Signature: v=1; a=rsa-sha256; c=simple/simple; d=example.com; s=foo;
    t=1541094902; bh=xj6JF8HXzDkYeJ72cJNmx7FnTp5CeDo6y+MwRwIeNC4=;
    h=Date:From:To:Subject:From;
    b=lJ8oU+KkUBWEWVl/HpztFx5Hdv2rhqLP03JfJ1yqp3+TR3aZX+uOCI4MKqvonYzXM
     kHl4YYsYT7fSnuSaF48feGbGQ1AauGKd2x9UKcBEBQq2cGLG7ahfXph/SF5eh7/psL
     dXal6gCw6416bJQMBa9sb+zSA/9Avy3zQ0jGCALw=
~~~

Si vous avez accès à un email GMAIL ou Yahoo, vous pouvez lui envoyer un email,
en affichant le message original vous pourrez vérifier la présence de `DKIM-Signature:`
et cela vous indiquera si la signature est bien correcte et acceptée.

### Vérifier via des services externes

* Vérifier (notamment) son enregistrement DNS pour DKIM : <https://toolbox.googleapps.com/apps/checkmx/> (2 premiers résultats à ignorer)

* Vérifier en envoyant un email vers un service externe : <https://dkimcore.org/tools/> ou <http://dkimvalidator.com/> ou <https://www.mail-tester.com/>


## Monitoring

Il est important de s'assurer que le démon *opendkim* tourne en permanence.

### Nagios

Voici un check basique pour vérifier que le port TCP d'*opendkim* répond bien :

~~~
$ /usr/lib/nagios/plugins/check_tcp -H 127.0.0.1 -p 8891
~~~

### log2mail

Pour être alerté en cas de *warning: connect to Milter service inet:8891: Connection refused
on ajoute la configuration suivante au logiciel [log2mail](https://wiki.evolix.org/HowtoLog2mail) :

~~~
file = /var/log/syslog
  pattern = "warning: connect to Milter service inet:8891: Connection refused"
  mailto = alert@example.com
~~~

## FAQ

### opendkim: smfi_opensocket() failed

Si vous obtenez le message suivant au démarrage :

~~~
Starting OpenDKIM Milter: opendkim: smfi_opensocket() failed
~~~

C'est que la socket réseau est déjà occupée !

### ADSP (Author Domain Signing Practices)

**ADSP est désormais obsolète, et remplacé par la spécification [DMARC](https://fr.wikipedia.org/wiki/DMARC)

[ADSP](https://en.wikipedia.org/wiki/Author_Domain_Signing_Practices) est une extension à DKIM permettant d'indiquer le traitement à effectuer en cas de signature DKIM invalide ou absente.

Si l'on est sûr que tous les mails émis avec le nom de domaine utilisé sont bien signés avec DKIM, on peut l'indiquer via l'enregistrement DNS suivant, ce qui provoquera la pénalisation des emails sans signature :

~~~
_adsp._domainkey        IN      TXT "dkim=all"
~~~

On peut vérifier que l'enregistrement ADSP est bien pris en compte avec la commande suivante :

~~~
# opendkim-testadsp example.com
~~~

### Pas d'entête DKIM-Signature

Si vous ne constatez pas l'ajout de la signature DKIM, vérifiez votre configuration, vérifiez que vous utilisez bien un champ `From:` correct et correspondant à un domaine à signer.
Il peut aussi être intéressant d'activer les options suivantes dans `/etc/opendkim.conf` pour avoir davantage de logs :

~~~
Syslog                  yes
SyslogSuccess           yes
LogWhy                  yes
~~~

### Logs de vérification

Il peut être intéressant d'activer l'option suivante /etc/opendkim.conf` pour avoir des logs pour chaque signature vérifiée par *opendkim* :

~~~
LogResults true
~~~

### Requêtes DNS externes pour ADSP

Attention, par défaut OpenDKIM effectue ses vérifications ADSP en faisant de multiples requêtes DNS sans utiliser le resolver local,
ce qui qui peut provoquer des ralentissements notamment si cela n'est pas autorisé au niveau firewall.
Nous conseillons de désactiver ces vérifications qui sont obsolètes :

~~~
DisableADSP true
~~~

### GMAIL/Google et DKIM

Informations de GMAIL/Google à propos de DKIM : <https://support.google.com/a/answer/174124?hl=fr>

### Problème de header (dkim-filter: no sender header found)

Avec dkim-filter, en Debian 7, il se peux que, suite a une règle de ce type dans postfix :

~~~
/^received:/ IGNORE
~~~

cela casse dkim-filter, car il ne vois pas si le sender est correct dans le header du mail, et donc il ne sais pas si c'est un domaine qu'il doit signé ou pas.

### Regenérer la zone DNS

Lors qu'un clé a déjà été généré mais que le fichier contenant la zone DNS n'est plus disponbile, il est possible de la regénérer avec la commande suivante :

~~~
opendkim-genzone -F -d example.com  /etc/opendkim/KeyTable
~~~
