For quite some time I thought about automating the tedious and error-prone process of managing SSL certificates. The basic steps involved are:
  • Generating a private key
  • Calculating the Certificate Signing Request (CSR) from it
  • Submitting the CSR to a Certificate Authority and receiving the certificate
  • Storing the certificate to a file
  • (overwriting the old certificate or) changing all references to the certificate in config files

Now I've written a bunch of Python scripts to do all these things.

  • For StartSSL, my favorite CA despite the horrible web interface, I've built a CLI. https://github.com/max-weller/StartSSL_API
  • I generate all private keys on my local machine and upload them to the server later. So I've built a script `copy.py` which copies a bash command to the clipboard which contains the certificate and its private key.
  • To use copy.py you also need a helper script on the server, called `crtpaste`. This writes certificate and private key to timestamped files. Then it adjusts some symlinks to point to the new cert and key. It also creates a certificate bundle for nginx, postfix etc which contains StartSSLs intermediate certificate.

To use these tools, first follow the install instructions:
http://home.max-weller.de/certificate-manager/install/

Now I'll give a short walkthrough of the workflow. There are more detailed instructions on the StartSSL CLI in its README.

Domain Validation

Validate some domains with StartSSL if you didn't do that already via the web interface:

startssl_validate.py example.org

Create a file called example_domains.txt where example is a freely chosen nickname for the certificate. It should contain a list of all domains and subdomains you want to have certified.

e.g.
cat > example_domains.txt
example.org
mail.example.org
shop.example.org
^D

startssl_certify.py example

This will automatically generate a private key (example_privatekey_YYMMDD.pem) and a CSR for you. It then uploads it to StartSSL, adds all domains and subdomains from the txt file and stores the certificate to example_cert_YYMMDD.pem.

You can then copy the certificate to clipboard with
crtcopy example

Login to your server via SSH, then paste the clipboard (as root). It will contain something like:
crtpaste <<END
CERTDATA example YYMMDD
-----BEGIN CERTIFICATE-----
...
-----END CERTIFICATE-----
-----BEGIN PRIVATE KEY-----
...
-----END PRIVATE KEY-----
END

crtpaste will parse this and create files containing your cert and key:
  • /etc/ssl/mycerts/available/example_cert_YYMMDD.pem
  • /etc/ssl/mycerts/available/example_privatekey_YYMMDD.pem
It will also create or adjust symlinks to these files:
  • /etc/ssl/mycerts/current/example_cert.pem
  • /etc/ssl/mycerts/current/example_privatekey.pem
Moreover, it creates a bundle file containing your certificate and the intermediate certificate:
  • /etc/ssl/mycerts/current/example_chainedcert.pem

Afterwards it prints out the configuration statements for Apache and nginx.


crtpaste also allows to only change the symlinks to other version (timestamp) of the certificate. Just pass the name of the certificate file as command line argument. Example:

root@server# crtpaste example_cert_150106.pem
Created new symlinks:
/etc/ssl/mycerts/current/example_cert.pem -> /etc/ssl/mycerts/available/example_cert_150106.pem
/etc/ssl/mycerts/current/example_privatekey.pem -> /etc/ssl/mycerts/available/example_privatekey_150106.pem

Apache Config:
        SSLCertificateFile      /etc/ssl/mycerts/current/example_cert.pem
        SSLCertificateKeyFile   /etc/ssl/mycerts/current/example_privatekey.pem
        SSLCertificateChainFile /etc/ssl/certs/sub.class2.server.sha2.ca.pem

Created bundle for nginx etc.:
        ssl_certificate /etc/ssl/mycerts/current/example_chainedcert.pem;
        ssl_certificate_key /etc/ssl/mycerts/current/example_privatekey.pem;



Have a lot of fun!

Kommentare