Mehr für Selbermacher

Posted by moritz on Tuesday, February 16, 2016

Eines der (wenigen) Dinge, die ich von meinem Studium mitgenommen habe ist: Was mehr als zwei mal getan werden muss, sollte automatisiert werden. Und damit geht es wohl in keiner Branche so sehr darum, sich selbst abzuschaffen, wie in unserer. Nach dem automatisiertem Zertifikatsimport haben wir uns natürlich nicht zurück gelehnt und die Füße baumeln lassen, sondern die durch die weggefallenen Supportanfragen gewonnene Zeit genutzt, um munter weiter in die Tasten zu hauen. Et voilà: Jetzt ist es soweit. Es hat sich ein bisschen etwas getan hinter den Kulissen:

Zertifikate

Auflisten

Wie bei Domains auch gibt es nun ein Skript, das euch eure aufgeschalteten Zertifikate anzeigt. Und das ist ganz schön gesprächig und kann damit hoffentlich beim Debugging helfen. Denn auch wenn die Supportanfragen zu Zertifikaten deutlich zurück gegangen sind, ist dieses Gebiet für viele verständlicherweise Raketenwissenschaft. So kann ein Aufruf aussehen:

[wiebke@amnesia ~]$ uberspace-list-certificates
common name: wiebke.org
issuer: Let's Encrypt Authority X1
valid until: 2016-04-24 15:18:00 CEST
will be removed in 85 days.
alternative name: www.wiebke.org
alternative name: blog.wiebke.org
alternative name: wiebke.com
alternative name: www.wiebke.com
alternative name: blog.wiebke.com

common name: wiebke.com
issuer: StartCom Certification Authority
valid until: 2017-01-02 13:11:00 CEST
will be removed in 252 days.
alternative name: www.wiebke.com
alternative name: blog.wiebke.com

Die Zertifikate sind jeweils für die Domain im common name, als auch für die als alternative name angegebenen Domains gültig. Wenn mehrere Zertifikate für die gleichen Domains gültig sind, entscheidet die Reihenfolge, welches Zertifikat ausgeliefert wird.

Funfact: Im Beispielfall würde das zweite Zertifikat niemals ausgeliefert werden, da alle Domains bereits über das erste Zertifikat abgedeckt sind. Neu importierte Zertifikate kommen bei uns immer nach ganz oben auf die Liste und werden damit - wenn die Domain stimmt - zuerst ausgespielt. Das Zertifikat könnte also auch genau so gut gelöscht werden.

Manuelles Entfernen

Auch das geht inzwischen ohne Mail an den Support:

[wiebke@amnesia ~]$ uberspace-del-certificate -c wiebke.com

… und schon ist wieder Ordnung geschaffen. Den common name, der mit dem Switch -c übergeben werden muss, liefert uberspace-list-certificates.

Automatisches Entfernen

Da abgelaufene Zertifikate eh eine Warnung im Browser provozieren, entfernen wir diese nun automatisch. Also die abgelaufenen Zertifikate, nicht die Warnung. Vom Sicherheitsaspekt her macht es keinen Unterschied, ob nun mit einem abgelaufenen Zertifikat oder mit unserem vorinstallierten Zertifikat verschlüsselt wird. Und durch Warnmails, die wir zwei und eine Woche vor Ablauf eines Zertifikates versenden, bleibt noch genug Zeit, um sich zu kümmern.

Hinzufügen

In der Vergangenheit haben wir auch Zertifikate importiert, die nicht gegen das ca-bundlevon CentOS validieren (z.B. von CAcert ausgestellte oder selbst signierte Zertifikate). Mit dem Start von Let’s Encrypt sind Zertifikate für jeden einfach und kostenlos verfügbar geworden, sodass wir keinen Grund mehr sehen, an dieser Praxis fest zu halten. Natürlich geht es hier nur um die Zertifikate, die in den Webserver eingebunden sind, also über HTTPS auf Port 443 ausgeliefert und in unsere Infrastruktur eingepflegt werden. Wenn ihr eigene Dienste - wie z.B. einen XMPP-Server - betreibt, könnt ihr hier natürlich weiterhin alles an Zertifikaten nutzen, was ihr mögt. Da hatten wir ja noch nie unsere Finger im Spiel und das wird auch so bleiben.

Notiz am Rande: Da das bisherige uberspace-prepare-certificate inzwischen viel mehr macht, als reine Vorbereitung, heißt es jetzt uberspace-add-certificate (ist aber weiterhin über den bisherigen Namen aufrufbar).

Debugging

Wenn es mit den Zertifikaten mal nicht so klappen sollte wie geplant, hilft cert-info weiter. Mit --help verrät es, was es alles kann (Spoiler: Eine Menge). Hier ein paar Beispiele:

[wiebke@amnesia ~]$ cert-info --file fullchain.pem --cn
wiebke.org
[wiebke@amnesia ~]$ cert-info --file fullchain.pem --alt
www.wiebke.org
blog.wiebke.org
wiebke.com
www.wiebke.com
blog.wiebke.com
[wiebke@amnesia ~]$ cert-info --file fullchain.pem --dates
valid from: 2016-01-24 15:18:00 CEST
valid until: 2016-05-05 10:59:00 CEST
[wiebke@amnesia ~]$ cert-info --file fullchain.pem --issuer
Let's Encrypt Authority X1

Das geht übrigens nicht nur für Dateien, sondern auch für Hosts:

[wiebke@amnesia ~]$ cert-info --host wiebke.org --cn
wiebke.org
[wiebke@amnesia ~]$ cert-info --host wiebke.org --dates
valid from: 2016-01-24 15:18:00 CEST
valid until: 2016-05-05 10:59:00 CEST

Ports

Ihr könnt nun eure in der Firewall geöffneten Ports - wie die Zertifikate und aufgeschalteten Domains - selbst verwalten. Das geht per uberspace-add-port, uberspace-del-port und uberspace-list-ports. Bei mehr als 10 Ports pro User und Protokoll ist aber erst mal Schluss und ihr müsst uns - wie früher - eine Mail schreiben. Hier mal ein Beispiel an Hand eines TCP-Ports:

[wiebke@amnesia ~]$ uberspace-add-port -p tcp --firewall
🚀  All good! Opened tcp port 61032.
[wiebke@amnesia ~]$ uberspace-list-ports --open
tcp 61032
[wiebke@amnesia ~]$ uberspace-del-port -p tcp -n 61032 --firewall
closed tcp port 61032.

uberspace-list-ports bringt noch ein kleines Schmankerl mit und kann alle Prozesse auflisten, die aktuell auf TCP- oder UDP-Ports auf Verbindungen lauschen. Du bist dir nicht ganz sicher, ob und auf welchem Port dein Ghost läuft? Kein Problem:

[wiebke@amnesia ~]$ uberspace-list-ports --listen
tcp 63421: node (7491), node/home/wiebke/ghost/index.js
tcp 63747: nginx (28605), nginx: master process /home/wiebke/.linuxbrew/bin/nginx -c /home/wiebke/nginx/nginx.conf

Webserver

Auf Zuruf haben wir schon immer den (oder das?) Apache error_log angeknippst und in letzter Zeit sind die Anfragen zu HSTS gestiegen. Eine gute Gelegenheit, um Euch ein Tool zu geben, mit dem ihr das ab sofort selbst regeln könnt: uberspace-configure-webserver. Auch hier haben wir nicht gekleckert sondern geklotzt:

Usage: uberspace-configure-webserver <enable|disable|status> <feature>

This shell script configures the vhost.

features:
         error_log
           handles Apache error_log

         hsts
           sets Strict-Transport-Security: max-age=15768000

         nosniff
           sets X-Content-Type-Options: nosniff

         xframe_deny
           sets X-Frame-Options: DENY

         xxss_protection
           sets X-Xss-Protection: 1; mode=block

Wir haben uns am Blogartikel Hardening your HTTP response headers von Scott Helme orientiert und alles umgesetzt, was Apache umsetzen kann. Auch hier abschließend ein Beispiel:

[wiebke@amnesia ~]$ uberspace-configure-webserver status hsts
hsts is disabled.
[wiebke@amnesia ~]$ uberspace-configure-webserver enable hsts
Strict-Transport-Security is now enabled.
🚀  All good! Your new configuration will be live within the next five minutes.

Und nach spätestens 5 Minuten sieht das dann so aus:

[wiebke@amnesia ~]$ curl -I wiebke.amnesia.uberspace.de
HTTP/1.1 200 OK
Date: Tue, 16 Feb 2016 04:42:54 GMT
Server: Apache/2.2.15 (CentOS)
Strict-Transport-Security: max-age=15768000
Accept-Ranges: bytes
Content-Length: 4961
Connection: close
Content-Type: text/html

MariaDB

Last but not least: Wir betreiben einen Standalone-Host mit MariaDB 10.0, der über einen SSH-Tunnel von jedem unserer Server erreichbar ist. Mit uberspace-setup-mariadb könnt ihr Euch eine Datenbank auf diesem Host anlegen. Die Zugangsdaten werden in ~/.my.mariadb.cnf abgelegt.

Hierbei möchten wir ganz explizit noch mal auf unseren Wikiartikel hinweisen:

Wir erstellen zwar auch von diesem separaten Host regelmäßig Backups; auf jene hast du aber - im Gegensatz zu den normalen MySQL-Backups - nicht direkt Zugriff, sondern wir müssen dir Dumps auf Anfrage bereitstellen. Das kostet nichts, muss aber über den Support laufen.

Es handelt sich wie gesagt um eine Übergangslösung, die nur für Leute gedacht ist, die zwingend hier und jetzt unbedingt MySQL 5.5 bzw. etwas dazu Kompatibles brauchen. Sobald unsere CentOS-7-Hosts am Start sind, gibt es noch eine Übergangsfrist von voraussichtlich 3 Monaten, innerhalb derer die betreffenden User dann von ihrem CentOS-6- auf einen CentOS-7-Host migrieren müssen, wo MariaDB dann offizielles Feature ist.

Wir wünschen Euch frohes Selbermachen! 💪