Passage de StartSSL à Let’s Encrypt avec validation DNS

Bonjour à tous,

Pour ceux qui suivent les articles peu fréquents du blog, je m’intéresse particulièrement aux certificats x.509 et aux configurations des services associés depuis 2014. Après plusieurs années de bons services avec StartSSL, il se trouve que je dois changer d’autorité de certification (CA, Certificate Authority) car cette dernière ne sera plus reconnue de confiance à partir du 8 mai 2017. Pour les détails, vous les retrouverez sur le blog de Qualys.com (en anglais).

Après recherche d’un remplaçant pour ma nouvelle autorité, j’ai finalement opté pour Let’s Encrypt, autorité gratuite et reconnu de la plupart des clients (logiciels).

Seulement avant de se lancer, il y a des choses à connaitre sur les modalités de signature d’un certificat :

Validité de 60 jours

Pas de certificat EV (Extended Validation), le nom de l’entité ayant fait la demande

Utilisation du protocole ACME (Automatic Certificate Management Environment) pour la demande et le renouvellement

Validation de l’appartenance du domaine à signer par une vérification HTTP ou DNS

Autre choix à faire, quel client ACME utiliser. La liste est longue et il est difficile de les distinguer, tous n’implémentent pas toutes les possibilités de Let’s Encrypt, certains détails ne sont pas paramétrables, pas mis à jour depuis plusieurs mois. J’ai finalement choisi d’utiliser acme.sh, un client shell, tout simplement.

Un autre point à prendre en compte, mon port 80 n’est pas disponible publiquement sur internet, je n’étais donc pas super chaud pour l’ouvrir dans le seul but de valider mon domaine tous les 60 jours (environ). C’est la où le challenge DNS m’intéresse. Le principe est simple, si vous avez la main sur le DNS gérant le domaine, vous êtes légitime pour obtenir un certificat, comment ? En ajoutant un ou plusieurs enregistrements TXT contenant une clé de validation. Alors oui à la main ça sera fastidieux d’ajouter/modifier l’enregistrement tous les 60 jours, mais acme.sh s’interface avec les API de nombreux opérateurs DNS dont OVH, problème résolu !

Installation

Comme d’habitude, je ne saurais trop vous inciter à mettre à jour votre système par le classique :

aptitude update

aptitude upgrade

Pour les 4 façons d’installer le client acme.sh, je vous invite à lire la page wiki dédiée, ici j’indique la méthode simple.

Information importante : bien que les installations en « root » ne soit pas toujours un bon choix, pour notre usage il semble que ça soit la bonne méthode, à cause des droits déjà et également pour les commandes après signature (issue) et renouvellement (renew). A vous d’évaluer ceci selon votre environnement !

curl https://get.acme.sh | sh

L’installation faisant un ajout dans le fichier .bashrc de l’utilisateur, il faut se déconnecter et reconnecter au shell pour que la modification soit active.

Mode manuel avec challenge DNS

Si vous n’avez pas d’API pour votre DNS ou que vous voulez gérer cette partie manuellement, c’est possible, la première demande s’effectue de la manière suivante :

acme.sh –issue –dns -d sub.domaine.tld -d domaine.tld –keylength 4096

Ici, on fait une demande (–issue) par DNS challenge (–dns) pour un domaine et sous-domaine (-d sub.domaine.tld -d domaine.tld) avec une clé privée de longueur 4096 (–keylength 4096) générée de suite (par défaut 2048).

Le script nous indique les enregistrements TXT pour _acme-challenge.sub.domaine.tld et _acme-challenge.domaine.tld.

Mode auto API OVH

Comme indiqué plus haut, acme.sh s’interface avec l’API d’OVH, une page wiki d’explication est disponible également.

On suit donc ce qui est indiqué en se connectant sur https://eu.api.ovh.com/createApp/ on remplit les informations et on valide. On dispose maintenant de deux éléments importants, « Application Key » et « Application secret » à renseigner dans le fichier :

/root/.acme.sh/dnsapi/dns_ovh.sh

J’en profite pour préciser que l’ensemble des fichiers liées à acme.sh et Let’s Encrypt se trouve dans le dossier caché « .acme.sh » de l’utilisateur qui a fait l’installation.

Première demande en utilisant l’API OVH :

acme.sh –issue –dns dns_ovh -d sub.domaine.tld -d domaine.tld –keylength 4096

Et la ça ne fonctionne pas, un message nous indique d’ouvrir une grande URL « https://eu.api.ovh.com/auth/?credentialToken=XXXxxXXXx » afin de déterminer la durée de validité du compte sur l’API, « Unlimited » semble la bonne réponse dans notre usage et on valide. C’est normal, cette opération est à faire seulement la première fois.

Répéter la commande précédente, si tout va bien, vous devriez obtenir votre certificat, le certificat de l’autorité et la chaine complète de certification.

Les fichiers se trouveront dans /root/.acme.sh/sub.domaine.tld/

-rw-r–r– 1 root root 1,7K avril 30 15:35 ca.cer

-rw-r–r– 1 root root 3,8K avril 30 15:35 fullchain.cer

-rw-r–r– 1 root root 2,2K avril 30 15:35 sub.domaine.tld.cer

-rw-r–r– 1 root root 900 avril 30 15:51 sub.domaine.tld.conf

-rw-r–r– 1 root root 1,7K avril 30 15:35 sub.domaine.tld.csr

-rw-r–r– 1 root root 203 avril 30 15:35 sub.domaine.tld.csr.conf

-rw-r–r– 1 root root 3,2K avril 30 15:35 sub.domaine.tld.key

Mise en place des certificats

Aller chercher les certificats dans /root ce n’est pas vraiment l’état de l’art, il faut donc les installer dans un endroit accessible par notre ou nos application(s).

Il reste à repasser sur les configurations des services afin de spécifier où se trouve les fichiers de certificats dont ils auront besoin pour démarrer. Sur ce point je vous laisse faire et vous référer à la commande qui suit pour les chemins.

acme.sh –installcert -d sub.domaine.tld –keypath /etc/ssl/private/sub.domaine.tld.key –capath /etc/ssl/certs/sub.domaine.tld-ca.pem –fullchainpath /etc/ssl/certs/sub.domaine.tld-full.pem –reloadcmd « service nginx reload && service postfix reload && service dovecot restart »

Grâce à cette commande, la clé privée est installée dans /etc/ssl/private. Le certificat de l’autorité et la chaine complète dans /etc/ssl/certs. Enfin, le paramètre –reloadcmd permet d’exécuter une commande à l’issue, ici le reload des configurations de nginx et postfix ainsi que le restart de dovecot. On peut très bien exécuter un script shell si besoin.

Logiquement tout est en place. Toutes les nuits une tâche cron s’exécutera afin de vérifier si il faut faire une demande de renouvellement. Pour vous en assurer :

crontab -e

Conclusion

Tout ceci n’est pas très difficile en soit mais il faut faire les choses dans l’ordre et analyser un peu ce que l’on veut faire et comment.

Pour ceux qui font du DANE TLSA, il faudra mettre à jour votre enregistrement DNS TLSA associé.

Concernant la clé privée, les droits de lecture en 644 (lecture/écriture pour le propriétaire, lecture pour le groupe et les autres) ne me plait pas des masses, je préfère 640, donc un petit chmod s’imposera, éventuellement à ajouter à un script à exécuter avant le reload des services.

Comme d’habitude, si vous avez des remarques ou des commentaires, n’hésitez pas !

Stay tuned !