Wichtige Info

Die Inhalte, die du hier siehst stelle ich dir ohne Werbeanzeigen und ohne Tracking deiner Daten zur Verfügung. Trotzdem muss ich die Server bezahlen sowie Zeit in Recherche, Umsetzung sowie Mail Support stecken.
Um dies leisten zu können, verlinke ich in einigen Artikeln auf die Plattform Amazon. Alle diese Links nennen sich Afiliate Links. Wenn du dir mit diesem Link etwas kaufst, dann erhalte ich eine kleine Provision. Dies ändert jedoch NICHT den Preis, den du bezahlst!
Falls du mich also unterstützen möchtest, kannst du auf den Link zum Produkt klicken und hilfst mir dabei, dieses Hobby weiter zu betreiben.
Da ich Keine Werbung schalte und keine Spenden sammle, ist dies die einzige Möglichkeit, meine Systeme und mich zu finanzieren. Ich hoffe du kannst das verstehen :)



Lets Encrypt - Separaten Zertifikat-Server aufsetzen mit DNS-01 Challenge


Einleitung

Dieser Beitrag beschäftigt sich, wie der letzte auch, mit einem persönlichen Thema - Der Härtung meiner Infrastruktur.

Ich setze für meine Server durchweg auf Lets Encrypt Zertifikate, sowohl für meine Mail- als auch meine Webserver. Alles was TLS sprechen kann, nutzt bei mir auch TLS inkl. Lets Encrypt.

Grundsätzlich ist das sehr angenehm, da ich durch Lets Encrypt kostenlose Zertifikate erhalte und durch automatisierungen diese großteilig automatisch erneuert werden können.

Bisher nutze ich dafür hauptsächlich die HTTP-01 Challenge. Diese lässt es zu spezifische Domains (z.B. blog.justinritter.de) zu validieren und dafür dann ein zertifikat auszustellen. Der Nachteil ist jedoch, dass ich meine Webserver in dieser Zeit zumeist stoppen muss und somit meine Dienste für einige Sekunden nicht zur Verfügung stehen. Es gibt auch alternativen, diese nutze ich bisher jedoch nicht.

Der große Nachteil ist jedoch, dass ich jedesmal auf mehreren Servern die Zertifikate erneuern muss, was mir unnötig Arbeit macht.

Aus diesem Grund werde ich einen separaten Zertifizierungsserver aufsetzen, welcher mit der von Let's Encrypt zur Verfügung gestellten DNS-01 Challenge von nun an alle meine Serverzertifikate verwaltet, neu ausstellt und zuletzt auch verteilt.

Dadurch kann ich alle meine Zertifikate mit Wildcard Zertifikaten betreiben, also benötige ich effektiv nur noch 1 Zertifikat pro Domain und weiterhin kann ich mit einem Plugin für einen DNS Anbieter die Zertifikate weiterhin voll automatisch erneuern lassen.

Voraussetzungen

Ich werde hier nicht von 0 auf starten. Ich gehe davon aus, dass ein ordentlich eingerichteter Server bereits vorhanden ist (in meinem Fall auf Basis von Debian).

Es sollte hier beachtet werden, dass der Server später mit die wichtigsten Daten enthält. Sollte der Server übernommen werden, sind eure Zertifikate weg und ggf. können Eindringline auch Zugang zu eurem DNS System haben (wenn ihr ein Plugin verwendet).

In meinem Fall ist daher der Server in meinem Heimnetzwerk gehostet, nur in diesem erreichbar und hat auch sonst keine Dienste am laufen.

Weiterhin ist es nötig eine Domain zu besitzen, welche öffentlich erreicht werden kann. Lets Encrypt stellt keine internen Zertifikate aus (für private IP Adressen).

Installation

Installation Certbot

Um Zertifikate zu erhalten, wird der sog. Certbot benötigt.

Dieser kann ganz simpel zum Repository hinzugefügt order in meinem Fall durch snapd installiert werden.

sudo apt install python3-certbot

Hier kann jetzt noch schnell geschaut werden, ob der Certbot verfügbar ist - dafür wird der folgende Command ausgeführt:

certbot --version

Nach Eingabe des Commands erhalte ich die folgende Version:

certbot 2.4.0

Wenn kein Ergebnis kommen sollte, dann konnte der Certbot nicht korrekt installiert werden. Wenn alles gut ist, dann wird dir nun ebenfalls eine Versionsnummer angezeigt. Wichtig ist, dass die Version höher 2.0 sein muss! - Alternativ kann man per SNAP Certbot installieren.

Installation des Netcup Plugin

Der folgende Schritt könnte für dich anders aussehen:

Um die Zertifikate automatisiert installieren zu können, ist es in meinem Fall nötig, mein Anbieter Plugin (Netcup) zu installieren.

Es gibt leider kein Plugin für mich Nativ von ACME, sondern "nur" ein Community Plugin. Dieses muss ich mit Python installieren. Dafür ist bei mir ein wenig extra Arbeit nötig:

sudo pip3 install certbot-dns-netcup

Sobald das Plugin installiert ist, erstelle ich eine Datei mit den Daten meines DNS Provider um die API Verwenden zu können.

vi /Pfad/zur/datei/.netcup-credentials.ini

dns_netcup_customer_id = 12345
dns_netcup_api_key = NETCUP_API_KEY
dns_netcup_api_password = NETCUP_API_PASSWORT

Danach werden die Rechte eingeschränkt

chmod 0600 /pfad/zur/datei/.netcup-credentials.ini

Diese Schritte können bei euch wie gesagt variieren, wenn ihr etwas anderes als netcup nutzt.

Generieren eines (wildcard)Zertifikat

Zuletzt können nun Zertifikate erstellt werden. In meinem Fall möchte ich diese nur abrufen aber nicht installieren. Um die Installation kümmere ich mich ebenfalls selber, sodass diese auf allen Servern ausgerollt werden, welche die zertifikate benötigen.

Dafür wird der folgende Befehl eingegeben:

sudo certbot certonly --authenticator dns-netcup --dns-netcup-credentials /pfad/zur/Credentials-Datei.ini --dns-netcup-propagation-seconds 900 --keep-until-expiring --non-interactive --expand --server https://acme-v02.api.letsencrypt.org/directory -d 'domain.de' -d '*.domain.de' --agree-tos --email mail@deine-email.de

Sobald dieser Command beendet ist, solltest du eine Bestätigung erhalten, dass alles funktioniert hat. Daraufhin kannst du die Zertifikate an die betroffenen Server verteilen.

In meinem Fall geschieht dies per NFS innerhalb meiner Control Plane. Falls dich auch das weitere Vorgehen interessiert, kannst du gerne weiterlesen. Ansonsten ist der folgende Abschnitt für dich nicht mehr interessant.

NFS auf dem Zielserver vorbereiten

Um die Zertifikate auf den anderen Servern verwenden zu können, muss zuerst die Infrastruktur dafür aufgebaut werden.

In meinem Fall möchte ich NFS nutzen, da ich ohnehin nur im Controlplane Netz arbeite, hier sollte niemand sein, können die Zertifikate problemlos über NFS ausgetauscht werden. Zudem ist NFS am einfachsten einzurichten.

Zuerst wird auf dem Zielserver ein NFS-Server installiert

sudo apt install nfs-kernel-server

Nachdem dieser installiert worden ist, wird ein Export eingerichtet, auf welchen der Deployment Server zugreifen muss. In meinem Fall befindet sich der Deploymentserver auf meiner Controlplane via NAT und greift unter anderem über das 192.168.50.0/24 und 192.168.51.0/24 Netz auf die Zielserver zu.

Im folgenden konfiguriere ich Beispielhaft einen Export für das Netz 192.168.50.0/24. Der Deployment Server greift per NAT über die Adresse 192.168.50.1/24 auf das Zielnetz zu und der Zielserver steht in dem Netz mit der Adresse 192.168.50.10/24.

Export auf dem Zielserver erstellen

Um unter Debian einen NFS Export zu erstellen, wird die Datei "/etc/exports" angepasst. Zuvor wird ein Ordner erstellt, welcher für NFS verwendet werden soll. Hier landen später dann die Zertifikate.

mkdir /nfs/zielserver
chown nobody:nogroup /nfs/zielserver
chmod 777 /nfs/zielserver
vi /etc/exports

Sobald dies geschehen ist, wird in die exports Datei der folgende Text reingeschrieben:

/nfs/zielserver    192.168.50.1(rw,sync,no_subtree_check)

Damit ist die Freigabe erstellt. Wer die Flags genauer erklärt haben möchte, kann sich diese Doku ansehen.

Sobald das geschehen ist, wird mit dem Befehl sudo service nfs-server restart der Dienst neugestartet. Auf Dinge wie die Firewall konfiguration gehe ich hier jetzt mal nicht ein. Grundsätzlich wird der Port 2049 verwendet, also sollte dieser natürlich geöffnet sein. Zum Beispiel mit dem folgenden Befehl.

sudo ufw allow in on <interface> from 192.168.50.1/24 to any port 2049

Sobald dies geschehen ist, kann auf dem Deployserver der Share eingehängt werden. Dafür wird die /etc/fstab Datei angepasst.

Auch hier verweise ich auf die Doku, da die Funktionalität von NFS bei Ubuntuusers (und das einhängen) hervorragend beschrieben ist.

192.168.50.10:/nfs/zielserver         /nfs/localcerts nfs auto,nofail,noatime,nolock,intr,tcp,actimeo=1800 0 0

Zuletzt wird mit einem mount -a die Datei neu eingelesen und der Share sollte dann nun verfügbar sein.

Automatisierung und Deployment

Um die Zertifikate auf mich angepasst automaitsieren zu können, habe ich ein eigenes kleines Script geschrieben, welches es ermöglicht mit einer JSON Config zu arbeiten. Dieses ist hier zu finden.

Dieses Script wird auf dem Deployment Server in ein Verzeichnis deiner Wahl kopiert und dann später im Command bei Certbot aufgerufen. Zuerst ist jedoch die Config anzulegen. Im folgenden gebe ich ein kleines Beispiel für eine Domain auf meinem Server an. Mehr Info findest du im Repo oder alternativ kannst du einfach eine E-Mail schreiben :).

{
    "pure-smart.de": 
    [
        {
          "wildcard": true,
          "base": true,
          "domains": [
            "*"
          ],
          "target": [
            "/nfs/publicServices/certificates/pure-smart.de/"
          ]
        }
    ]
}

In der COnfig können auch noch weitere Domains eingefügt werden und auch SUbdomains unterschieden werden, dies ist auf Github im Repo beschrieben. Die Config geben wir beim Aufruf mit und dann werden die Zertifikate automatisch auf die NFS Shares geschoben. Demnächst werde ich auch noch Dienste neustarten lassen, dies ist aber gerade noch in arbeit und kommt in einem Update nach.

Zertifikate erstellen und ausrollen

Zuletzt wird jetzt noch das Zertifikat wie oben in dem Command beschrieben angefordert, mit dem folgenden Zusatz:

sudo certbot certonly --authenticator dns-netcup --dns-plugin-credentials /dns/.credentials.ini --dns-plugin-propagation-seconds 900 --keep-until-expiring --non-interactive --expand --server https://acme-v02.api.letsencrypt.org/directory -d 'domain.tld' -d '*.domain.tld' --agree-tos --email mail@deinemail.tld --deploy-hook '/opt/deploy.py -domainspath="$RENEWEDLINEAGE" -reneweddomains="$RENEWEDDOMAINS"'

Das wars :) - Nachdem die Zertifikate abgerufen worden sind, solltet ihr diese in den Target Verzeichnissen finden.


Back…