====== Let's Encrypt with acme.sh ====== WORK IN PROGRESS - I am converting these instructions to use acme.sh I use X.509 certificates signed by Let's Encrypt for all of my internal services that use TLS, including web servers, mail servers, LDAPS server, etc. I use [[https://www.freshports.org/security/acme.sh/|security/acme.sh]] to help generate and automatically renew these certificates. Upstream instructions for how to use this tool are available at https://wiki.acme.sh/. ===== Step 1 - Install security/acme.sh ===== # pkg install acme.sh ===== Step 2 - Configure acme.sh to use DNS API for Validation ===== Let's Encrypt will sign your certificate if you can demonstrate that you control the domain. It does this by issuing the client software with a challenge... For more information about how Let's Encrypt works, visit https://github.com/Neilpang/acme.sh/wiki/dnsapi. I use Gandi as my DNS provider, so I have followed the instructions at https://github.com/Neilpang/acme.sh/wiki/dnsapi#18-use-gandi-livedns-api. ===== Step 3 - Generate and sign new certificates ===== After this, acme.sh can generate a new Let's Encrypt account key and certificate, get them signed, and install them with the following command: ... This will give verbose output and perform the following: * create a new 4096-bit RSA account key, and save it as .../privkey.pem (can be changed with -f) * create a new 4096-bit RSA domain key, and save it as .../privkey.pem (can be changed with -k) * request Let's Encrypt to sign the new certificate, and automatically satisfy any challenges ... * save the signed public domain certificate (cert.pem), chain (chain.pem), and full-chain (fullchain.pem) in .../acme/ ===== Step 4 - Copy certificate into place and restart service ===== ===== Step 5 - Configure automatic renewals using cron ===== ===== Example - Website with Nginx ===== ==== Configure nginx to use https and re-direct http traffic ==== Now that you have a signed certificate, re-configure nginx.conf to instead listen for HTTPS connections on port 443, and re-direct HTTP connections to HTTPS. Note that you must keep the directory alias for responding to Let's Encrypt challenges on HTTP port 80. server { listen 80; server_name example.com www.example.com; # Lets encrypt location ^~ /.well-known/acme-challenge/ { alias /usr/local/www/acme/; } # Redirect other HTTP connections to HTTPS location / { return 301 https://example.com$request_uri; } } server { listen 443 ssl; server_name example.com www.example.com; ssl_certificate /usr/local/etc/ssl/acme/fullchain.pem; ssl_certificate_key /usr/local/etc/ssl/acme/private/privkey.pem; ... MOVE REMAINDER OF NGINX CONFIG FOR WEBSITE HERE } Restart nginx with: # service nginx restart ==== Test website with SSL Labs ==== In a web browser, go to http://example.com/ and confirm it re-directs to https://example.com/ and the browser trusts the certificate. Now visit https://www.ssllabs.com/ssltest/ to see how your website scores, and close any security flaws as necessary. Two of the common fixes that need to be applied are: * Tighten the SSL configuration (limiting the protocols and ciphers) - refer to the [[https://mozilla.github.io/server-side-tls/ssl-config-generator/|Mozilla SSL Configuration Generator]] * Using audited and resistant Diffie-Hellman groups to prevent the initial handshake from being hijacked - see the [[https://wiki.mozilla.org/Security/Server_Side_TLS#Pre-defined_DHE_groups|pre-defined DH groups ffdhe2048, ffdhe3072 or ffdhe4096 recommended by the IETF in RFC 7919]]