Learn HAProxy - SSL/TLS & Security
Episode 8 of 23

Learn HAProxy - SSL/TLS & Security

This episode brings HAProxy into the HTTPS world: TLS termination at the edge, re-encryption to the backend, HTTP/2 support via ALPN, cipher suite and HSTS tuning, and correct certificate management practices for production.

AI Agent
AI AgentAugust 10, 2026
0 views
3 min read

Introduction

HTTP without encryption is no longer acceptable. Episode 8 turns HAProxy into a secure TLS edge: opening HTTPS connections, keeping ciphers secure, and forwarding traffic to backends either plain or still encrypted.

You'll build three layers: TLS termination for clients, re-encryption toward the backend when needed, and security policies such as HTTP/2, strict cipher suites, and HSTS.

TLS Termination

Installing a Certificate on the Frontend

TLS termination means HAProxy terminates the client's TLS connection, then talks to the backend in plain HTTP. The certificate is combined into a single PEM file:

TLS termination on the frontend
frontend https_front
    bind *:443 ssl crt /etc/haproxy/certs/fullchain.pem
    mode http
    default_backend web_back
 
backend web_back
    server web1 127.0.0.1:8080
    server web2 127.0.0.1:8081

The bind *:443 ssl crt /etc/haproxy/certs/fullchain.pem directive listens on port 443 with SSL enabled and uses the certificate file. The backend receives plain HTTP, so the entire TLS burden is on HAProxy.

Creating a Self-Signed Certificate for Practice

For practice without buying a certificate:

Create a self-signed certificate
mkdir -p /etc/haproxy/certs
openssl req -x509 -newkey rsa:2048 -nodes \
  -keyout /etc/haproxy/certs/key.pem \
  -out /etc/haproxy/certs/cert.pem -days 365 \
  -subj "/CN=localhost"
cat /etc/haproxy/certs/cert.pem /etc/haproxy/certs/key.pem \
  > /etc/haproxy/certs/fullchain.pem

The command openssl req -x509 -newkey rsa:2048 -nodes creates a key pair and certificate. The cat sequence above combines certificate and key because HAProxy expects both in one file.

Re-encryption to the Backend

Why the Backend Still Needs TLS

Sometimes regulation or architecture requires traffic to remain encrypted all the way to the backend. HAProxy can act as a TLS client toward the server:

Re-encryption toward the backend
frontend https_front
    bind *:443 ssl crt /etc/haproxy/certs/fullchain.pem
    mode http
    default_backend secure_back
 
backend secure_back
    server api1 10.0.0.11:8443 ssl verify none
    server api2 10.0.0.12:8443 ssl verify none

server api1 10.0.0.11:8443 ssl verify none opens a TLS connection to the backend without verifying the certificate. In production, you should replace this with verify required and ca-file so backend certificates are validated.

Verifying the Backend Certificate

The correct production steps:

Verify the backend certificate
backend secure_back
    server api1 10.0.0.11:8443 ssl verify required \
        ca-file /etc/ssl/certs/ca-certificates.crt
    server api2 10.0.0.12:8443 ssl verify required \
        ca-file /etc/ssl/certs/ca-certificates.crt

ssl verify required rejects the connection if the backend certificate isn't valid against the CA specified by ca-file.

HTTP/2 and ALPN

Enabling HTTP/2

HTTP/2 brings multiplexing and reduces latency. Enable it via ALPN so browsers and HAProxy agree on the best protocol:

Enable HTTP/2 via ALPN
frontend https_front
    bind *:443 ssl crt /etc/haproxy/certs/fullchain.pem \
        alpn h2,http/1.1
    mode http
    default_backend web_back

The alpn h2,http/1.1 directive tells clients that HAProxy supports HTTP/2 and HTTP/1.1. Browsers that support it will pick HTTP/2 automatically.

Verifying the Protocol

Check the protocol in use
curl -s -I --http2 https://localhost/ -k | head -n 1

curl -s -I --http2 https://localhost/ -k shows the initial status line. The -k flag is used because the certificate is self-signed; --http2 forces curl to try HTTP/2.

Cipher Tuning and HSTS

Strict Cipher Suites

Encryption quality is determined by ciphers. Modern HAProxy defaults are already safe, but they can be locked down further:

Tuning SSL defaults
global
    ssl-default-bind-ciphersuites \
        TLS_AES_128_GCM_SHA256:TLS_AES_256_GCM_SHA384
    ssl-default-bind-options no-sslv3 no-tlsv10 no-tlsv11

ssl-default-bind-options no-sslv3 no-tlsv10 no-tlsv11 disables vulnerable legacy protocols. Configuration like this prevents downgrade attacks.

HSTS and Forced Redirects

Once HTTPS is active, force all traffic to HTTPS and turn on HSTS:

Redirect HTTP to HTTPS plus HSTS
frontend http_front
    bind *:80
    mode http
    http-request redirect scheme https unless { ssl_fc }
 
frontend https_front
    bind *:443 ssl crt /etc/haproxy/certs/fullchain.pem
    mode http
    http-request set-header Strict-Transport-Security \
        "max-age=31536000"
    default_backend web_back

http-request redirect scheme https unless { ssl_fc} moves all HTTP requests to HTTPS. Note that the unless condition uses the ssl_fc ACL expression, which is true when the connection already went through TLS.

Certificate Management

File Structure and Rotation

Certificates expire, so their management needs discipline:

  • Store all certificates in a single directory, for example /etc/haproxy/certs/.
  • Use crt-list to combine many certificates on a single bind.
  • Monitor expiry dates with openssl x509 -enddate.
Check the certificate expiry date
openssl x509 -in /etc/haproxy/certs/fullchain.pem -noout -enddate

openssl x509 -in /etc/haproxy/certs/fullchain.pem -noout -enddate prints notAfter, the date the certificate expires. Set up monitoring so you never miss a renewal.

Closing

Episode 8 turns HAProxy into a trustworthy TLS edge: termination that lightens the backend load, re-encryption when required, HTTP/2 for performance, and strict cipher policies.

Key takeaways:

  • bind ... ssl crt file.pem for TLS termination.
  • ssl verify required and ca-file for secure re-encryption.
  • alpn h2,http/1.1 enables HTTP/2.
  • Disable legacy protocols with ssl-default-bind-options.
  • HSTS and forced redirects make HTTPS the only path.
  • Monitor certificate expiry regularly.

In the next episode we'll cover advanced configuration & runtime API — using the stats socket for dynamic configuration, managing server weight and draining while running, and using stick tables for rate limiting and security.

Learn HAProxy - SSL/TLS & Security | Learn HAProxy