Certificate pinning adds an extra layer of security by associating a host with its expected X.509 certificate or public key. This prevents man-in-the-middle attacks even if a certificate authority is compromised.
How Certificate Pinning Works
Instead of trusting any certificate signed by a trusted CA, pinning ensures only specific certificates or public keys are accepted for a given hostname. This is particularly important for API services and internal communications.
Implementing with Nginx
# Generate the pin hash from your certificate
openssl x509 -in /etc/ssl/certs/server.crt -pubkey -noout | \
openssl pkey -pubin -outform der | \
openssl dgst -sha256 -binary | base64
# Add to Nginx configuration
add_header Public-Key-Pins x27pin-sha256="BASE64_HASH"; max-age=5184000; includeSubDomainsx27 always;
Considerations
- Always pin a backup key to prevent lockout during certificate rotation
- Start with a short max-age value during testing
- Monitor certificate expiry dates carefully
- Consider using Certificate Transparency logs as an alternative
Summary
Certificate pinning provides strong protection against MITM attacks but requires careful management to avoid service disruptions during certificate renewals.