Why Let’s Encrypt?
Let’s Encrypt provides free, automated SSL/TLS certificates that are trusted by all major browsers. Before Let’s Encrypt, SSL certificates cost $50-300/year and required manual renewal. Now, any website can have HTTPS for free with automatic renewal.
Certbot is the official client for Let’s Encrypt. It handles certificate issuance, installation, and renewal automatically for Nginx, Apache, and other web servers.
Prerequisites
- A Linux server with a public IP address.
- A domain name with DNS pointing to your server.
- Nginx or Apache installed and serving your site on port 80.
- Port 80 (HTTP) and 443 (HTTPS) open in your firewall.
Step-by-Step Solution
1. Install Certbot
Ubuntu/Debian:
sudo apt update
sudo apt install -y certbot python3-certbot-nginx
# Or for Apache:
# sudo apt install -y certbot python3-certbot-apache
CentOS/RHEL:
sudo dnf install -y certbot python3-certbot-nginx
2. Obtain a Certificate (Nginx)
sudo certbot --nginx -d example.com -d www.example.com
Certbot will:
- Verify domain ownership via an HTTP-01 challenge.
- Obtain the certificate from Let’s Encrypt.
- Automatically configure your Nginx server block with SSL.
- Set up a redirect from HTTP to HTTPS.
For Apache:
sudo certbot --apache -d example.com -d www.example.com
For manual/standalone mode (no web server plugin):
sudo certbot certonly --standalone -d example.com
3. Verify the Certificate
# Check the certificate details
sudo certbot certificates
# Test SSL configuration
curl -vI https://example.com 2>&1 | grep -A5 "SSL certificate"
4. Configure Auto-Renewal
Certbot installs a systemd timer automatically. Verify it:
sudo systemctl list-timers | grep certbot
Or test renewal manually:
sudo certbot renew --dry-run
For custom post-renewal hooks (e.g., reloading Nginx):
# Create a renewal hook
sudo mkdir -p /etc/letsencrypt/renewal-hooks/deploy
cat << 'EOF' | sudo tee /etc/letsencrypt/renewal-hooks/deploy/reload-nginx.sh
#!/bin/bash
systemctl reload nginx
EOF
sudo chmod +x /etc/letsencrypt/renewal-hooks/deploy/reload-nginx.sh
Troubleshooting
Validation Failed: “Connection Refused” or “Timeout"
# Verify DNS points to your server
dig +short example.com
# Verify port 80 is open
sudo ufw status | grep 80
curl -I http://example.com
"Too Many Failed Authorizations” Rate Limit
Let’s Encrypt rate-limits after 5 failed validations per hour. Fix the underlying issue and wait 1 hour. For testing, use the staging environment:
sudo certbot --nginx -d example.com --staging
Certificate Renewal Fails in Cron
# Check the renewal log
sudo cat /var/log/letsencrypt/letsencrypt.log
# Common fixes:
# 1. Make sure the web server is running
# 2. Ensure port 80 is still open
# 3. Check that the renewal config hasn't been modified
sudo cat /etc/letsencrypt/renewal/example.com.conf
Wildcard Certificates (DNS-01 Challenge)
Wildcard certificates (*.example.com) require DNS-01 validation:
sudo certbot certonly --manual --preferred-challenges dns -d "*.example.com" -d example.com
For automated DNS-01 with Cloudflare:
sudo apt install python3-certbot-dns-cloudflare
sudo certbot certonly --dns-cloudflare \
--dns-cloudflare-credentials /etc/letsencrypt/cloudflare.ini \
-d "*.example.com" -d example.com
Best Practices
- Always test with
--dry-runbefore running renewal commands in production. - Use the
--nginxor--apacheplugin instead of standalone mode for automatic configuration. - Monitor certificate expiry with tools like Prometheus
ssl_exporteror a simple cron script. - Enable HSTS after confirming SSL works: add
Strict-Transport-Security: max-age=31536000to your server config. - Enable OCSP stapling for faster TLS handshakes.
- Back up
/etc/letsencrypt/— it contains your private keys and account credentials.
Summary
- Let’s Encrypt provides free 90-day SSL certificates via Certbot.
- Certbot auto-configures Nginx/Apache and sets up automatic renewal.
- Troubleshoot validation by checking DNS, ports 80/443, and web server status.
- Use DNS-01 challenges for wildcard certificates.
- Always back up
/etc/letsencrypt/and test renewals with--dry-run.