Server-Zertifikate via ACME verwalten

Berechtigte Personen können im IT-Portal ACME-IDs einrichten, mit denen sie auf einem oder mehreren Servern vollautomatisch organisationsvalidierte X.509-Zertifikate für TLS-Server und/oder TLS-Clients beziehen können.

Berechtigt ist, wer in der Rechnerdatenbank der Universität Münster als Verantwortlicher oder Administrator der betreffenden Server eingetragen ist und wer sich am IT-Portal mit seiner persönlichen digitalen ID angemeldet hat.

Die Verwaltung der ACME-IDs finden Sie im IT-Portal unter „Digitale ID (Zertifikat)“.

Bitte beachten Sie die ausführlichen Hinweise im IT-Portal.

Beim Einrichten einer ACME-ID erhalten Sie eine Key-ID, einen HMAC-Key und die URL des Zertifikatservers. Sie müssen dann Ihre ACME-fähige Software veranlassen, sich mit diesen Schlüsseldaten beim Zertifikatserver zu registrieren.

Bei dieser Registrierung wird zwischen Ihrer ACME-fähigen Software und dem Zertifikatserver Schlüsselmaterial ausgetauscht, mit dem die Software dann die gewünschten Zertifikate beantragen und abholen kann.

Key-ID und HMAC-Key werden bei einer erfolgreichen Registrierung vom Zertifikatserver gelöscht, können also nur einmal verwendet werden. Es ist aber möglich, nach der Registrierung die von der ACME-fähigen Software gespeicherten Daten auf einen anderen Server kopieren.

Beispiel: ACME mit CertBot unter CentOS 7

Die nachfolgenden Hinweise beschreiben, wie wir es erfolgreich ausprobiert haben.

Es gibt viele mindestens genauso gute Alternativen.

Kurzfassung

Mit folgenden Kommandos haben wir einen Server erfolgreich eingerichtet:

yum install certbot

certbot register --server 'server-url' --eab-kid 'key-id' --eab-hmac-key 'hmac-key' --email 'e-mail-adresse' --agree-tos --no-eff-email

certbot certonly --standalone --agree-tos --server 'server-url' --domain fqdn1,fqdn2,... --cert-name 'certname' --email='e-mail-adresse' --deploy-hook 'systemctl restart servicename'

setfacl -R -m u:username:rX /etc/letsencrypt/{live,archive}/certname

setfacl -m u:username:rX /etc/letsencrypt/{live,archive}

setfacl -m d:u:username:rX /etc/letsencrypt/{live,archive}/certname

systemctl enable certbot-renew.timer

systemctl start certbot-renew.timer

Dabei bedeuten:

  • key-id = die vom IT-Portal ausgegebene (kürzere) Key-ID

  • hmac-key = der vom IT-Portal ausgegebene (längere) HMAC-Key

  • e-mail-adresse = die E-Mail-Adresse, an die der CertBot seine Informationen sendet

  • fqdn1,fqdn2,... = die vollqualifizierten Rechnernamen (FQDNs), unter denen der Dienst auftritt; diese FQDNs müssen im IT-Portal für die ACME-ID angegeben worden sein; der zuerst angegebene FQDN wird auch in das Subject des Zertifikats aufgenommen, die anderen nur in die Subject Alternative Names

  • certname = der frei wählbare Dateiname (ohne Pfad) des Zertifikats

  • servicename = der Name, unter dem der Dienst vom System-Daemon verwaltet wird

  • username = die Nutzerkennung, unter der der Server läuft

Einrichten der ACME-ID

Die Validierung erfolgt mit External Account Binding (EAB).

Dafür muss man sich zuerst im IT-Portal mit seiner persönlichen digitalen ID anmelden (https://xsso.uni-muenster.de/IT-Portal/) und dort unter „Digitale ID (Zertifikat)“ | „Neue ACME-ID“ eine ACME-ID für die in die zukünftigen Zertifikate aufzunehmende vollqualifizierten Domainnamen (FQDNs) einrichten. (Die Liste der FQDNs einer ACME-ID kann später im IT-Portal geändert werden.)

Dabei enthält man Schlüsseldaten in Form einer EAB-Key-ID und eines EAB-HMAC-Key, die für die Registrierung des Servers benötigt werden.

Installation der Software

Das EPEL-Repository enthält die CertBot-Software, diese kann installiert werden mit:

yum install certbot

Registrierung des CertBot

Um den Server beim ACME-Dienst zu registrieren muss einmalig folgender Befehl eingegeben werden. Dieser enthält Key-ID und HMAC-Key für das External Account Binding sowie die E-Mail-Adresse, die bei Problemen informiert werden soll:

certbot register --server 'server-url' --eab-kid 'key-id' --eab-hmac-key 'hmac-key' --email 'e-mail-adresse' --agree-tos --no-eff-email

Dabei bedeuten:

  • key-id = die vom IT-Portal ausgegebene (kürzere) Key-ID

  • hmac-key = der vom IT-Portal ausgegebene (längere) HMAC-Key

  • e-mail-adresse = die E-Mail-Adresse, an die der CertBot seine Informationen sendet

Nach erfolgreicher Registrierung werden Key-ID und HMAC-Key vom ACME-Server gelöscht und können nicht mehr verwendet werden.

Wenn eine ACME-ID auf mehreren Servern eingesetzt werden soll, kann aber das CertBot-Verzeichnis /etc/letsencrypt auf die weiteren Server kopiert werden.

Zertifikat erzeugen

Um dann tatsächlich ein Zertifikat per ACME zu beantragen, abzuholen, zu installieren und gleich auch noch den zertifizierten Service neu zu starten, dient folgender Befehl:

certbot certonly --standalone --agree-tos --server 'server-url' --domain fqdn1,fqdn2,... --cert-name 'certname' --email='e-mail-adresse' --deploy-hook 'systemctl restart servicename'

Dabei bedeuten:

  • fqdn1,fqdn2,... = die vollqualifizierten Rechnernamen (FQDNs), unter denen der Dienst auftritt; diese FQDNs müssen im IT-Portal für die ACME-ID angegeben worden sein; der zuerst angegebene FQDN wird auch in das Subject des Zertifikats aufgenommen, die anderen nur in die Subject Alternative Names

  • certname = der frei wählbare Dateiname (ohne Pfad) des Zertifikats

  • e-mail-adresse = die E-Mail-Adresse, an die der CertBot seine Informationen sendet

  • servicename = der Name, unter dem der Dienst vom System-Daemon verwaltet wird

Dieser Befehl legt alle benötigten Dateien im Verzeichnisbaum /etc/letsencrypt/archive/certname/ ab und sorgt dafür, dass die folgenden symbolischen Links immer auf die gerade aktuellen Dateien verweisen:

  • /etc/letsencrypt/live/certname/privkey.pem

  • /etc/letsencrypt/live/certname/cert.pem

  • /etc/letsencrypt/live/certname/chain.pem

  • /etc/letsencrypt/live/certname/fullchain.pem

Der Service sollte natürlich so konfiguriert sein, dass er genau diese symbolischen Links zum Zugriff auf die Dateien verwendet und dass er sich mit dem mit --deploy-hook angegebenen Befehl neu starten lässt.

Statt diese Pfade zu benutzen, könnte CertBot auch automatisch in Services eingebaut werden (z. B. mit --apache oder --nginx statt --standalone), das erfordert aber Plugins.

Zugriffsberechtigungen auf die Zertifikatdateien

CertBot legt die Zertifikatdateien, insbesondere den privaten Schlüssel, mit Zugriffsrechten nur für den root-User ab (0700). Damit Anwendungen, die nicht als root, sondern unter einer anderen Kennung laufen, diese Zertifikate auch einlesen dürfen, müssen die entsprechenden Leserechte gesetzt werden.

setfacl -R -m u:username:rX /etc/letsencrypt/{live,archive}/certname

setfacl -m u:username:rX /etc/letsencrypt/{live,archive}

setfacl -m d:u:username:rX /etc/letsencrypt/{live,archive}/certname

Dabei bedeuten:

  • username = die Nutzerkennung, unter der der Server läuft

  • certname = der frei wählbare Dateiname (ohne Pfad) des Zertifikats

Sie sollten unbedingt prüfen, ob die Kennung die erzeugten privaten Schlüssel tatsächlich lesen kann, beispielsweise mit:

getfacl /etc/letsencrypt/archive/certname/priv*

Notfalls muss die ACL-Maske in obigen Befehlen angepasst werden.

Sie sollten die Zugriffsrechte nicht mit chown, chgrp oder chmod bearbeiten, denn das wird vom CertBot geändert oder moniert.

Eine ganz andere Herangehensweise wäre, oben im certbot-Kommando bei der Option --deploy-hook ein Skript anzugeben, welches die Datei an eine andere Stelle kopiert, die Zugriffsrechte dieser Kopien mit chmod richtig setzt und dann den Server neu startet. Dann muss der Server natürlich so konfiguriert werden, dass er diese Kopien verwendet und nicht die Originaldateien.

Automatische Zertifikaterneuerung aktivieren

Dazu ist nur der CertBot-Renew-Timer zu starten:

systemctl enable certbot-renew.timer

systemctl start certbot-renew.timer

Es werden dann automatisch alle erzeugten und hinterlegten Zertifikate vor Ablauf erneuert.

Mehrere Zertifikate mit einer ACME-ID

Um mit derselben ACME-ID mehrere Zertifikate zu verwalten, wählt man bei den obigen Befehlen jeweils einen anderen certname und die jeweils gewünschte FQDNs fqdn1,fqdn2,...

Die ACME-ID muss für alle FQDNs in allen Zertifikaten freigeschaltet sein, aber es ist natürlich nicht nötig, in jedes Zertifikat alle FQDNs aufzunehmen.

Bei Systemen, die sich zwar über mehrere Server erstrecken (Cluster, Hochverfügbarkeit, usw), die aber alle vom selben Personenkreis administriert werden, kann man den Verzeichnisbaum /etc/letsencrypt nach der Registrierung auf die anderen Server verteilen. Dann kann sich jeder beteiligte Server unter der gleichen ACME-ID seine Zertifikate besorgen.

Sobald aber unterschiedliche Personenkreise administrativen Zugriff auf die verschiedenen Server haben, sollten unbedingt getrennte ACME-IDs eingesetzt werden.

Deploy-Hook nachträglich einrichten/ändern

Wird beim erstmaligen Abrufen eines Zertifikats (certbot certonly --standalone ...) die Option --deploy-hook mitgegeben, so wird dieses Kommando/Script nach jedem Zertifikat-Austausch aufgerufen. Das bietet sich als einfacher Weg an, um Services automatisiert nach dem Zertifikatwechsel neuzustarten.

War das nicht gewollt oder wurde das vergessen, gibt es diverse Alternativen, um die Service-Restarts mit CertBot zu realisieren:

  • in /etc/letsencrypt/renewal/certname.conf unter [renewalparams] nachträglich die Zeile renew_hook = systemctl restart servicename eintragen

  • einfach den Zertifikatsabruf mit --deploy-hook wiederholen; das erzeugt dann diese Zeile, erneuert allerdings auch gleich das Zertifikat

  • certbot renew --deploy-hook ... aufrufen, das wirkt dann aber auf alle Zertifikate und führt bei allen Zertifikaten zu diesem Eintrag

  • unter /etc/letsencrypt/renewal-hooks/deploy ein entsprechendes Script ablegen, auch das wirkt auf alle Zertifikate

Letzteres bietet sich vor allem an, wenn man mehr machen will, statt nur ein einfaches Kommando abzusetzen. Allerdings akzeptiert --deploy-hook auch Pfade zu selbst geschriebenen Skripten.

Wer noch mehr Kontrolle wünscht oder noch komplexere Start/Stop-Scripte benutzen möchte, der kann auch mit --pre-hook und --post-hook oder mit Skripten in /etc/letsencrypt/renewal-hooks/pre bzw. /etc/letsencrypt/renewal-hooks/post arbeiten, letztere wirken auf alle Zertifikate.

Zertifikaterneuerung ausprobieren

certbot renew --noninteractive --no-random-sleep-on-renew --force-renewal

Nutzung mit privaten IP-Adressen

Damit der Zertifizierungsserver erreicht werden kann, sollte vor dem Absetzen von certbot-Kommandos der Proxy-Server eingestellt werden:

http_proxy=http://wwwproxy.uni-muenster.de:3128
https_proxy=http://wwwproxy.uni-muenster.de:3128
export http_proxy https_proxy

Damit der Timer-gesteuerte automatische Zertifikatabruf klappt, sollten im der Systemkonfigurationsdatei /etc/sysconfig/certbot folgende Zeilen ergänzt werden:

http_proxy=http://wwwproxy.uni-muenster.de:3128
https_proxy=http://wwwproxy.uni-muenster.de:3128

Alternative: acme.sh

Auf dem Server richtet man dann einen dedizierten Nutzer ein (Name beliebig), in dessen HOME-Verzeichnis anschließend acme.sh installiert und verwendet wird wie folgt:

adduser acmeuser

su - acmeuser

git clone https://github.com/acmesh-official/acme.sh.git

cd ./acme.sh

./acme.sh --install -m e-mail-adresse

exit

Zum Einlesen der geänderten rc-Dateien wird der Nutzer erneut eingeloggt, der Default-CA-Server wird gesetzt, der EAB-Account registriert (Nebenprodukt ACCOUNT_THUMBPRINT) und ein Zertifikat angefordert:

su - acmeuser

acme.sh --set-default-ca --server 'server-url'

acme.sh --register-account --server 'server-url' --eab-kid 'key-id' --eab-hmac-key 'hmac-key'

acme.sh --issue -d fqdn1 --stateless

Im Default werden die Zertifikatsdateien dann im Unterordner ~/.acme.sh/fqdn1/ abgelegt und müssen noch an die von der Anwendung benötigte Stelle kopiert werden. Als acmeuser' kann man mit crontab -l den ggf. schon von acme.sh eingerichteten Renewal-Eintrag sehen und anpassen bzw. um ein Deployment ergänzen.