DEV Community

Ramer Labs
Ramer Labs

Posted on

The Ultimate Checklist for Securing Nginx with TLS and HTTP/2

Introduction

As an SRE, you know that a mis‑configured web server is an open invitation for attackers. Nginx is a popular reverse proxy and static file server, but out‑of‑the‑box it ships with permissive TLS settings and no HTTP/2 optimizations. This checklist walks you through the essential steps to lock down Nginx, enable modern TLS, and squeeze performance out of HTTP/2—all while keeping operational overhead low.


1. Acquire a Trusted Certificate

  • Use a reputable CA – Let’s Encrypt offers free, automated certificates that renew every 90 days. For production workloads, consider a paid CA for extended validation.
  • Automate renewal – Install certbot or acme.sh and add a cron job:
0 3 * * * /usr/bin/certbot renew --quiet --post-hook "systemctl reload nginx"
Enter fullscreen mode Exit fullscreen mode
  • Store keys securely – Keep private keys in /etc/ssl/private with permissions 600 and owned by root:root.

2. Enforce Strong TLS Versions and Cipher Suites

Older protocols (TLS 1.0/1.1) are vulnerable to POODLE and BEAST. Limit Nginx to TLS 1.2 and TLS 1.3 only:

ssl_protocols TLSv1.2 TLSv1.3;
ssl_ciphers "EECDH+AESGCM:EDH+AESGCM:AES256+EECDH";
ssl_prefer_server_ciphers on;
Enter fullscreen mode Exit fullscreen mode
  • Prefer server ciphers – This prevents clients from downgrading to weak suites.
  • Use forward‑secrecy – Include ECDHE/ECDH groups. Tools like SSL Labs can verify your score.

3. Enable HTTP/2 for Faster Page Loads

HTTP/2 multiplexes streams over a single TLS connection, reducing latency. Activate it with the http2 flag on the listen directive:

listen 443 ssl http2;
Enter fullscreen mode Exit fullscreen mode

Make sure your TLS configuration meets the HTTP/2 requirements (no TLSv1.0, no RC4 ciphers). Test with curl -I --http2 https://yourdomain.com.


4. Harden Headers and Enable HSTS

Security‑related response headers add another layer of protection:

add_header Strict-Transport-Security "max-age=31536000; includeSubDomains" always;
add_header X-Content-Type-Options nosniff;
add_header X-Frame-Options DENY;
add_header Referrer-Policy no-referrer-when-downgrade;
Enter fullscreen mode Exit fullscreen mode
  • HSTS tells browsers to always use HTTPS for the next year.
  • always ensures the header is added even on error responses.

5. Deploy OCSP Stapling

OCSP stapling reduces the TLS handshake time and protects against certificate revocation attacks:

ssl_stapling on;
ssl_stapling_verify on;
resolver 8.8.8.8 8.8.4.4 valid=300s;
resolver_timeout 5s;
Enter fullscreen mode Exit fullscreen mode

Check the status with openssl s_client -connect yourdomain.com:443 -status.


6. Restrict Cipher Suites for Older Clients (Optional)

If you have legacy browsers, you can create a separate server block listening on a non‑HTTP/2 port (e.g., 8443) with a more permissive cipher suite, then redirect all traffic to the hardened 443 block.


7. Firewall and Rate‑Limiting

  • UFW/iptables – Allow only ports 80 and 443 from the internet, block everything else.
  • Fail2Ban – Protect against brute‑force attempts on the admin endpoint:
[nginx-http-auth]
enabled = true
filter = nginx-http-auth
logpath = /var/log/nginx/error.log
maxretry = 5
bantime = 3600
Enter fullscreen mode Exit fullscreen mode
  • Rate limit connections to mitigate DoS attacks:
limit_req_zone $binary_remote_addr zone=one:10m rate=30r/s;
limit_req zone=one burst=10 nodelay;
Enter fullscreen mode Exit fullscreen mode

8. Logging and Monitoring

  • Enable request and error logs with a JSON format for easy ingestion into ELK or Loki:
log_format json_escape '{"time":"$time_iso8601","remote_addr":"$proxy_protocol_addr","host":"$host","request":"$request","status":$status,"bytes_sent":$body_bytes_sent,"request_time":$request_time}';
access_log /var/log/nginx/access.json json_escape;
Enter fullscreen mode Exit fullscreen mode
  • Set up alerts for sudden spikes in 4xx/5xx responses using Prometheus + Alertmanager.

9. Regular Patch Management

Nginx vulnerabilities surface regularly. Automate OS and package updates:

apt-get update && apt-get upgrade -y
systemctl restart nginx
Enter fullscreen mode Exit fullscreen mode

On Debian/Ubuntu, enable unattended upgrades for security patches only.


10. Verify Your Hardening

Run these checks after each change:

  1. SSL Labs test – Aim for an A+ rating.
  2. Qualys SSL Server Test – Confirms OCSP stapling and HSTS.
  3. curl -I -s -D - https://yourdomain.com – Verify headers.
  4. nginx -t – Ensure config syntax is correct before reload.

Conclusion

By following this checklist you’ll have a Nginx front‑end that speaks TLS 1.3, streams over HTTP/2, and resists the most common web‑based attacks. The combination of strong ciphers, HSTS, OCSP stapling, and proactive monitoring creates a defense‑in‑depth posture without sacrificing performance.

If you’re looking for a reliable hosting partner that can help you implement these hardening steps on a managed platform, consider checking out https://lacidaweb.com for a smooth, developer‑friendly experience.

Top comments (0)