SSL/TLS
Set up TLS certificates for oCore using Let's Encrypt, Caddy, or self-signed certificates.
TLS encryption is essential for protecting authentication tokens, API requests, and SSH credentials in transit. This guide covers several approaches to obtaining and managing certificates.
Let's Encrypt with Certbot
Certbot is the standard tool for obtaining free TLS certificates from Let's Encrypt. Use this approach with Nginx or standalone.
Install Certbot
# Ubuntu/Debian
sudo apt update
sudo apt install certbot python3-certbot-nginx
# Rocky Linux / RHEL
sudo dnf install certbot python3-certbot-nginxObtain a Certificate
With Nginx already configured and running:
sudo certbot --nginx -d ocore.example.comCertbot automatically modifies your Nginx configuration to use the obtained certificate. For a standalone certificate (without modifying Nginx):
# Stop any service on port 80 first
sudo certbot certonly --standalone -d ocore.example.comThe certificate files are stored at:
| File | Path |
|---|---|
| Full chain | /etc/letsencrypt/live/ocore.example.com/fullchain.pem |
| Private key | /etc/letsencrypt/live/ocore.example.com/privkey.pem |
Automatic Renewal
Certbot installs a systemd timer or cron job for automatic renewal. Verify it is active:
# Check the renewal timer
sudo systemctl list-timers | grep certbot
# Test renewal without making changes
sudo certbot renew --dry-runIf the timer is not active, add a cron job:
# Edit crontab
sudo crontab -e
# Add renewal check twice daily
0 0,12 * * * certbot renew --quiet --deploy-hook "systemctl reload nginx"The --deploy-hook reloads Nginx after a successful renewal so the new certificate is picked up without downtime.
Let's Encrypt with Caddy
If you use Caddy as your reverse proxy, TLS is fully automatic. Caddy obtains and renews certificates from Let's Encrypt or ZeroSSL without any configuration.
Simply specify your domain in the Caddyfile:
ocore.example.com {
reverse_proxy localhost:8080
}Caddy will:
- Obtain a certificate on the first request to the domain
- Serve HTTPS by default (HTTP is automatically redirected)
- Renew the certificate before expiration
- Use OCSP stapling for improved performance
No cron jobs, no manual certificate management, no renewal hooks.
Certificate Storage
Caddy stores certificates at:
~/.local/share/caddy/certificates/Or when running as a systemd service:
/var/lib/caddy/.local/share/caddy/certificates/Self-Signed Certificates
For internal networks, development environments, or air-gapped deployments where Let's Encrypt is not available.
Generate a Self-Signed Certificate
# Create a directory for certificates
sudo mkdir -p /etc/ocore/tls
# Generate a private key and self-signed certificate (valid for 365 days)
sudo openssl req -x509 -nodes -days 365 \
-newkey rsa:2048 \
-keyout /etc/ocore/tls/ocore.key \
-out /etc/ocore/tls/ocore.crt \
-subj "/CN=ocore.example.com" \
-addext "subjectAltName=DNS:ocore.example.com,IP:10.0.0.1"Replace 10.0.0.1 with your server's internal IP if accessing by IP address.
Use with Nginx
server {
listen 443 ssl http2;
server_name ocore.example.com;
ssl_certificate /etc/ocore/tls/ocore.crt;
ssl_certificate_key /etc/ocore/tls/ocore.key;
# ... proxy configuration
}Trust the Certificate
Clients connecting to oCore will see a certificate warning unless they trust the self-signed certificate.
On the server (for API health checks):
sudo cp /etc/ocore/tls/ocore.crt /usr/local/share/ca-certificates/ocore.crt
sudo update-ca-certificatesOn client machines, import the .crt file into the system or browser trust store.
TLS Best Practices
Protocol and Cipher Configuration
Restrict to TLS 1.2 and 1.3 with strong cipher suites:
ssl_protocols TLSv1.2 TLSv1.3;
ssl_ciphers ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384;
ssl_prefer_server_ciphers off;HSTS
Enable HTTP Strict Transport Security to prevent protocol downgrade attacks:
add_header Strict-Transport-Security "max-age=63072000; includeSubDomains" always;Only enable includeSubDomains if all subdomains also serve HTTPS.
OCSP Stapling (Nginx)
ssl_stapling on;
ssl_stapling_verify on;
resolver 1.1.1.1 8.8.8.8 valid=300s;Testing Your Configuration
Use SSL Labs to verify your TLS configuration after deployment:
# Quick local check with OpenSSL
openssl s_client -connect ocore.example.com:443 -tls1_3An A+ rating on SSL Labs indicates a properly hardened configuration.