OCSP Stapling mit letsencrypt (dehydrated) und nginx
Ich habe schon länger versucht OCSP stapling zu aktivieren. Es gibt viele Anleitung hierzu und alle sagen mehr oder weniger dasselbe. Leider hat das so bei mir nie funktioniert. Aber fangen wir vorne an.
Was ist OCSP überhaupt?
SSL-Zertifikate sind nach ihrer Ausstellung eine bestimmte Zeit lang gültig (bei letsencrypt 90 Tage). Es kann natürlich sein, dass ein Zertifikat in dieser Zeitspanne kompromittiert wird. In diesem Fall muss es zurückgezogen werden. Passiert das nicht bleibt es bis zum Ablauf der 90 Tage gültig. Über OCSP kann ein Client herausfinden ob ein Zertifikat vorzeitig für ungültig erklärt wurde. Jedes Zertifikat enthält hierzu eine URL zur jeweiligen Zertifizierungsstelle unter der eben jene Gültigkeitsprüfung vorgenommen werden kann.
Das bedeutet jedoch dass der Zertifizierungsstelle vom Client mitgeteilt werden muss, welche Zertifikat er gerade abruft. Außerdem dauert die Anfrage natürlich auch etwas. Um beiden Problemen zu begegnen gibt es OCSP stapling. Hierbei fragt der Server zu dem das SSL-Zertifikat gehört regelmäßig (z.B. jede Stunde) selbst bei der Zertifizierungsstelle nach, ob sein Zertifikat noch gültig ist. Diese Information liefert er dann beim Aufbau einer SSL-Verbindung an den Client mit. Die Anfrage bei der Zertifizierungsstelle kann entfallen.
Ich nutze das Script dehydrated um meine letsencrypt-Zertifikate zu verwalten. In der config.sh
von dehydrated werden folgende Zeilen eingefügt:
OCSP_MUST_STAPLE="yes"
OCSP_FETCH="yes"
Das Script läuft bei mir täglich um ggf. ablaufende Zertifikate zu erneuern. Ab sofort werden hierbei auch neue OCSP-Stapling Dateien geladen. Die Dateien werden im gleichen Verzeichnis abgelegt in die dehydrated auch die jeweiligen Zertifikate ablegt. Der Dateiname lautet ocsp.der
.
Mit diesen Informationen kann man nun die nginx-Konfiguration überarbeiten:
server {
listen 443 ssl http2;
listen [::]:443 ssl http2;
server_name searx.xyz
www.searx.xyz;
gzip off;
ssl_certificate /etc/letsencrypt.sh/certs/searx.xyz/fullchain.pem;
ssl_certificate_key /etc/letsencrypt.sh/certs/searx.xyz/privkey.pem;
ssl_trusted_certificate /etc/letsencrypt.sh/certs/searx.xyz/chain.pem;
ssl_dhparam /etc/nginx/dhparam.pem;
ssl_session_cache shared:SSL:50m;
ssl_session_timeout 10m;
ssl_session_tickets off;
ssl_protocols TLSv1.2;
ssl_prefer_server_ciphers on;
ssl_ciphers 'AES256+EECDH:AES256+EDH:!aNULL';
ssl_ecdh_curve secp384r1;
ssl_stapling on;
ssl_stapling_verify on;
ssl_stapling_file /etc/letsencrypt.sh/certs/searx.xyz/ocsp.der;
resolver 8.8.8.8 8.8.4.4 valid=300s;
resolver_timeout 5s;
}
[...]
Für das OCSP-Stapling sind insbesondere die folgenden Zeilen ausschlaggebend:
ssl_stapling on;
ssl_stapling_verify on;
ssl_stapling_file /etc/letsencrypt.sh/certs/searx.xyz/ocsp.der;
resolver 8.8.8.8 8.8.4.4 valid=300s;
resolver_timeout 5s;
Die Angabe von ssl_stapling_file
sollte eigentlich nicht nötig sein, da nginx sich die OCSP-Daten auch selbst beschaffen kann (dafür wird dann auch der resolver
angegeben). Das hat bei mir jedoch nie funktioniert, weshalb auch die ganzen Anleitungen im Netz nicht funktioniert haben. Den resolver
könnte ich mir jetzt wahrscheinlich sparen, aber für den Fall dass nginx die OCSP-Daten doch noch selbst einsammeln möchte habe ich es mal drin gelassen.
Nach einem Neustart/Reload von nginx sollte nun alles klappen, prüfen kann man es mit folgendem Befehl:
openssl s_client -connect www.searx.xyz:443 -status
Der relevante Teil der Ausgabe sollte etwa wie folgt aussehen:
OCSP response:
======================================
OCSP Response Data:
OCSP Response Status: successful (0x0)
Response Type: Basic OCSP Response
Version: 1 (0x0)
Responder Id: C = US, O = Let's Encrypt, CN = Let's Encrypt Authority X3
Produced At: Feb 24 19:10:00 2019 GMT
Alternativ kann man natürlich die Testtools von SSLLabs oder HTBridge nutzen.