Configure HAProxy with connection pooling, advanced load balancing algorithms, and performance tuning for high-throughput workloads. Learn to implement least-conn, URI hashing, and buffer optimization.
Prerequisites
- Root access to Linux server
- At least 2GB RAM
- Multiple backend servers for load balancing
- Basic HAProxy knowledge
What this solves
HAProxy performance bottlenecks often stem from inefficient connection handling, suboptimal load balancing algorithms, and poorly tuned buffer sizes. This tutorial optimizes HAProxy for high-throughput environments by implementing connection pooling, advanced load balancing methods like least-conn and URI hashing, and fine-tuning timeout values and buffer configurations for maximum performance.
Prerequisites
You'll need a Linux server with root access and at least 2GB RAM. This guide assumes you have basic HAProxy knowledge and existing backend servers to load balance. For foundational HAProxy setup, refer to our HAProxy installation tutorial.
Step-by-step configuration
Install HAProxy with performance extensions
Install the latest HAProxy version with performance-oriented features enabled.
sudo apt update
sudo apt install -y haproxy=2.8.*
sudo systemctl enable haproxyConfigure global performance settings
Set up global HAProxy parameters optimized for high-performance scenarios with increased connection limits and efficient threading.
global
log stdout local0
chroot /var/lib/haproxy
stats socket /run/haproxy/admin.sock mode 660 level admin
stats timeout 30s
user haproxy
group haproxy
daemon
# Performance optimizations
nbthread 4
cpu-map auto:1/1-4 0-3
maxconn 50000
tune.maxaccept 1024
tune.bufsize 32768
tune.rcvbuf.client 1048576
tune.rcvbuf.server 1048576
tune.sndbuf.client 1048576
tune.sndbuf.server 1048576
# Connection pooling
tune.idle-pool.shared on
tune.pool-high-fd-ratio 25
tune.pool-low-fd-ratio 10
defaults
mode http
log global
option httplog
option dontlognull
option log-health-checks
option redispatch
# Connection pooling and keep-alive
option http-server-close
option http-keep-alive
option prefer-last-server
# Performance timeouts
timeout connect 5000ms
timeout client 50000ms
timeout server 50000ms
timeout http-request 5000ms
timeout http-keep-alive 10000ms
timeout check 3000ms
# Advanced options
retries 3
option abortonclose
maxconn 10000Configure advanced load balancing algorithms
Set up different backend configurations using advanced load balancing methods for optimal traffic distribution.
# Frontend configuration
frontend web_frontend
bind *:80
bind *:443 ssl crt /etc/ssl/certs/example.com.pem
redirect scheme https if !{ ssl_fc }
# Route based on URI patterns
acl api_path path_beg /api/
acl static_content path_end .css .js .png .jpg .gif .ico
acl dynamic_content path_beg /app/ /user/
use_backend api_servers if api_path
use_backend static_servers if static_content
use_backend app_servers if dynamic_content
default_backend web_servers
Least connections algorithm for API servers
backend api_servers
balance leastconn
option httpchk GET /health
http-check expect status 200
# Connection pooling settings
option http-server-close
option http-reuse aggressive
# Server pool with connection limits
server api1 203.0.113.10:8080 check maxconn 1000 pool-max-conn 200
server api2 203.0.113.11:8080 check maxconn 1000 pool-max-conn 200
server api3 203.0.113.12:8080 check maxconn 1000 pool-max-conn 200
URI hashing for session consistency
backend app_servers
balance uri depth 2
hash-type consistent
option httpchk GET /status
# Advanced connection pooling
option http-reuse always
option prefer-last-server
server app1 203.0.113.20:8080 check weight 100 pool-max-conn 300
server app2 203.0.113.21:8080 check weight 100 pool-max-conn 300
server app3 203.0.113.22:8080 check weight 150 pool-max-conn 400
Round-robin with source IP persistence for static content
backend static_servers
balance source
option httpchk HEAD /ping
# Optimized for static content delivery
timeout server 30000ms
option http-reuse safe
server static1 203.0.113.30:80 check pool-max-conn 500
server static2 203.0.113.31:80 check pool-max-conn 500
RDP cookie-based balancing for applications requiring session affinity
backend web_servers
balance rdp-cookie
cookie SERVERID insert indirect nocache
option httpchk GET /
# Connection reuse configuration
option http-reuse aggressive
option http-server-close
server web1 203.0.113.40:80 check cookie s1 pool-max-conn 400
server web2 203.0.113.41:80 check cookie s2 pool-max-conn 400
server web3 203.0.113.42:80 check cookie s3 pool-max-conn 400Optimize system resource limits
Configure system limits to support HAProxy's high-performance requirements and prevent connection bottlenecks.
[Service]
LimitNOFILE=1048576
LimitNPROC=1048576
LimitMEMLOCK=infinitysudo mkdir -p /etc/systemd/system/haproxy.service.d/
sudo systemctl daemon-reloadConfigure advanced buffer tuning
Fine-tune HAProxy buffer sizes for high-throughput workloads and optimize memory usage patterns.
# Add to global section for advanced buffer tuning
global
# ... existing config ...
# Advanced buffer optimizations
tune.buffers.limit 1048576
tune.buffers.reserve 1024
tune.comp.maxlevel 6
tune.h1.zero-copy-fwd-recv on
tune.h1.zero-copy-fwd-send on
tune.http.cookielen 4096
tune.http.logurilen 2048
tune.http.maxhdr 200
# Memory pool optimizations
tune.pattern.cache-size 1000000
tune.vars.global-max-size 1048576
tune.vars.proc-max-size 1048576
tune.vars.reqres-max-size 1048576
tune.vars.sess-max-size 1048576
tune.vars.txn-max-size 1048576Enable performance monitoring
Set up HAProxy statistics interface for monitoring connection pooling efficiency and load balancing performance.
# Add statistics frontend
frontend stats
bind *:8404
stats enable
stats uri /stats
stats refresh 10s
stats show-legends
stats show-desc High Performance HAProxy
stats admin if TRUE
# Enable detailed statistics
option httplog
capture request header Host len 64
capture request header User-Agent len 128Configure SSL optimization
Optimize SSL/TLS performance with session caching and efficient cipher suites for secure high-performance connections.
# Add to global section
global
# ... existing config ...
# SSL optimizations
ssl-default-bind-ciphers ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384
ssl-default-bind-options ssl-min-ver TLSv1.2 no-tls-tickets
ssl-default-server-ciphers ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256
ssl-default-server-options ssl-min-ver TLSv1.2
# SSL session cache
tune.ssl.cachesize 1000000
tune.ssl.lifetime 300
tune.ssl.maxrecord 1460
tune.ssl.default-dh-param 2048Apply kernel network optimizations
Configure kernel parameters to support HAProxy's high-performance networking requirements.
# Network buffer optimizations
net.core.rmem_default = 262144
net.core.rmem_max = 16777216
net.core.wmem_default = 262144
net.core.wmem_max = 16777216
net.ipv4.tcp_rmem = 4096 87380 16777216
net.ipv4.tcp_wmem = 4096 16384 16777216
Connection handling
net.core.somaxconn = 65535
net.core.netdev_max_backlog = 30000
net.ipv4.tcp_max_syn_backlog = 65535
net.ipv4.tcp_syncookies = 1
TCP optimizations
net.ipv4.tcp_fin_timeout = 10
net.ipv4.tcp_keepalive_time = 120
net.ipv4.tcp_keepalive_intvl = 10
net.ipv4.tcp_keepalive_probes = 6
net.ipv4.tcp_tw_reuse = 1
File descriptor limits
fs.file-max = 1048576sudo sysctl -p /etc/sysctl.d/99-haproxy-performance.confRestart and verify configuration
Apply the configuration changes and verify HAProxy starts successfully with performance optimizations.
sudo haproxy -f /etc/haproxy/haproxy.cfg -c
sudo systemctl restart haproxy
sudo systemctl status haproxyVerify your performance setup
Test your HAProxy performance configuration and verify connection pooling is working effectively.
# Check HAProxy is running with optimizations
sudo systemctl status haproxy
haproxy -vv | grep -E "nbthread|maxconn"
Verify connection pooling statistics
curl -s http://your-server-ip:8404/stats | grep -E "pool|reuse"
Test load balancing with different algorithms
for i in {1..10}; do curl -s -o /dev/null -w "Server: %{remote_ip}\n" http://example.com/; done
Monitor active connections
watch "echo 'show stat' | socat /run/haproxy/admin.sock stdio | grep -E 'scur|smax'"
Check SSL performance
openssl s_client -connect example.com:443 -reconnect 2>/dev/null | grep -E "Reuse|New"Monitor performance metrics
HAProxy provides comprehensive metrics for monitoring connection pooling efficiency and load balancing performance.
| Metric | Command | Optimal Value |
|---|---|---|
| Connection reuse rate | echo "show stat" | socat /run/haproxy/admin.sock stdio | >80% reused |
| Pool usage | echo "show pools" | socat /run/haproxy/admin.sock stdio | <50% allocated |
| Response time | echo "show stat" | socat /run/haproxy/admin.sock stdio | grep ttime | <100ms average |
| Queue depth | echo "show stat" | socat /run/haproxy/admin.sock stdio | grep qcur | Near 0 |
Common performance issues
| Symptom | Cause | Fix |
|---|---|---|
| High response times | Insufficient connection pooling | Increase pool-max-conn and enable http-reuse aggressive |
| Connection refused errors | Resource limits too low | Increase maxconn and system file descriptor limits |
| Uneven load distribution | Wrong algorithm for workload | Switch to leastconn for dynamic content, source for sessions |
| SSL handshake delays | Missing SSL session cache | Configure tune.ssl.cachesize and disable TLS tickets |
| Memory usage growing | Connection pool misconfiguration | Tune tune.pool-high-fd-ratio and tune.idle-pool.shared |
| Backend server overload | Poor health checking | Adjust timeout check and health check intervals |
Load balancing algorithm comparison
Choose the optimal algorithm based on your application characteristics and performance requirements.
| Algorithm | Best For | Connection Overhead | Session Awareness |
|---|---|---|---|
| leastconn | API endpoints, varying request times | Medium | No |
| uri depth/hash | Content caching, file serving | Low | Yes (URI-based) |
| source | Session-based applications | Low | Yes (IP-based) |
| rdp-cookie | Web applications with cookies | Medium | Yes (cookie-based) |
| roundrobin | Uniform workloads, simple setup | Low | No |
For additional system optimization tips that complement HAProxy performance, see our guides on Linux memory optimization and I/O performance tuning.
Next steps
Automated install script
Run this to automate the entire setup
#!/usr/bin/env bash
set -euo pipefail
# Colors for output
RED='\033[0;31m'
GREEN='\033[0;32m'
YELLOW='\033[1;33m'
NC='\033[0m'
# Default values
DOMAIN="${1:-example.com}"
BACKEND_IPS="${2:-203.0.113.10,203.0.113.11,203.0.113.12}"
# Usage message
usage() {
echo "Usage: $0 [domain] [backend_ips]"
echo "Example: $0 example.com '203.0.113.10,203.0.113.11,203.0.113.12'"
exit 1
}
# Check if running as root
if [[ $EUID -ne 0 ]]; then
echo -e "${RED}This script must be run as root${NC}"
exit 1
fi
# Error cleanup trap
cleanup() {
echo -e "${RED}Installation failed. Cleaning up...${NC}"
systemctl stop haproxy 2>/dev/null || true
rm -f /etc/haproxy/haproxy.cfg.bak
}
trap cleanup ERR
# Auto-detect distribution
if [ -f /etc/os-release ]; then
. /etc/os-release
case "$ID" in
ubuntu|debian)
PKG_MGR="apt"
PKG_UPDATE="apt update"
PKG_INSTALL="apt install -y"
FIREWALL_CMD="ufw"
;;
almalinux|rocky|centos|rhel|ol|fedora)
PKG_MGR="dnf"
PKG_UPDATE="dnf update -y"
PKG_INSTALL="dnf install -y"
FIREWALL_CMD="firewall-cmd"
;;
amzn)
PKG_MGR="yum"
PKG_UPDATE="yum update -y"
PKG_INSTALL="yum install -y"
FIREWALL_CMD="firewall-cmd"
;;
*)
echo -e "${RED}Unsupported distro: $ID${NC}"
exit 1
;;
esac
else
echo -e "${RED}Cannot detect distribution${NC}"
exit 1
fi
echo -e "${GREEN}[1/7] Updating package repositories...${NC}"
$PKG_UPDATE
echo -e "${GREEN}[2/7] Installing HAProxy...${NC}"
$PKG_INSTALL haproxy
echo -e "${GREEN}[3/7] Backing up original configuration...${NC}"
cp /etc/haproxy/haproxy.cfg /etc/haproxy/haproxy.cfg.bak
echo -e "${GREEN}[4/7] Creating optimized HAProxy configuration...${NC}"
cat > /etc/haproxy/haproxy.cfg << 'EOF'
global
log stdout local0
chroot /var/lib/haproxy
stats socket /run/haproxy/admin.sock mode 660 level admin
stats timeout 30s
user haproxy
group haproxy
daemon
# Performance optimizations
nbthread 4
cpu-map auto:1/1-4 0-3
maxconn 50000
tune.maxaccept 1024
tune.bufsize 32768
tune.rcvbuf.client 1048576
tune.rcvbuf.server 1048576
tune.sndbuf.client 1048576
tune.sndbuf.server 1048576
# Connection pooling
tune.idle-pool.shared on
tune.pool-high-fd-ratio 25
tune.pool-low-fd-ratio 10
defaults
mode http
log global
option httplog
option dontlognull
option log-health-checks
option redispatch
# Connection pooling and keep-alive
option http-server-close
option http-keep-alive
option prefer-last-server
# Performance timeouts
timeout connect 5000ms
timeout client 50000ms
timeout server 50000ms
timeout http-request 5000ms
timeout http-keep-alive 10000ms
timeout check 3000ms
# Advanced options
retries 3
option abortonclose
maxconn 10000
frontend web_frontend
bind *:80
# Route based on URI patterns
acl api_path path_beg /api/
acl static_content path_end .css .js .png .jpg .gif .ico
acl dynamic_content path_beg /app/ /user/
use_backend api_servers if api_path
use_backend static_servers if static_content
use_backend app_servers if dynamic_content
default_backend web_servers
# Least connections algorithm for API servers
backend api_servers
balance leastconn
option httpchk GET /health
http-check expect status 200
# Connection pooling settings
option http-server-close
option http-reuse aggressive
server api1 BACKEND_IP1:8080 check maxconn 1000 pool-max-conn 200
server api2 BACKEND_IP2:8080 check maxconn 1000 pool-max-conn 200
server api3 BACKEND_IP3:8080 check maxconn 1000 pool-max-conn 200
# URI hashing for session consistency
backend app_servers
balance uri depth 2
hash-type consistent
option httpchk GET /status
# Advanced connection pooling
option http-reuse always
option prefer-last-server
server app1 BACKEND_IP1:8080 check weight 100 pool-max-conn 300
server app2 BACKEND_IP2:8080 check weight 100 pool-max-conn 300
server app3 BACKEND_IP3:8080 check weight 150 pool-max-conn 400
# Round-robin with source IP persistence for static content
backend static_servers
balance roundrobin
stick-table type ip size 200k expire 30m
stick on src
option httpchk GET /ping
server static1 BACKEND_IP1:8080 check pool-max-conn 100
server static2 BACKEND_IP2:8080 check pool-max-conn 100
# Default backend
backend web_servers
balance roundrobin
option httpchk GET /
server web1 BACKEND_IP1:80 check pool-max-conn 200
server web2 BACKEND_IP2:80 check pool-max-conn 200
server web3 BACKEND_IP3:80 check pool-max-conn 200
listen stats
bind *:8404
stats enable
stats uri /stats
stats refresh 30s
stats hide-version
EOF
# Replace backend IPs in configuration
IFS=',' read -ra IPS <<< "$BACKEND_IPS"
if [ ${#IPS[@]} -ge 1 ]; then
sed -i "s/BACKEND_IP1/${IPS[0]}/g" /etc/haproxy/haproxy.cfg
fi
if [ ${#IPS[@]} -ge 2 ]; then
sed -i "s/BACKEND_IP2/${IPS[1]}/g" /etc/haproxy/haproxy.cfg
else
sed -i "s/BACKEND_IP2/${IPS[0]}/g" /etc/haproxy/haproxy.cfg
fi
if [ ${#IPS[@]} -ge 3 ]; then
sed -i "s/BACKEND_IP3/${IPS[2]}/g" /etc/haproxy/haproxy.cfg
else
sed -i "s/BACKEND_IP3/${IPS[0]}/g" /etc/haproxy/haproxy.cfg
fi
echo -e "${GREEN}[5/7] Setting up system limits...${NC}"
cat > /etc/security/limits.d/haproxy.conf << EOF
haproxy soft nofile 65536
haproxy hard nofile 65536
haproxy soft nproc 32768
haproxy hard nproc 32768
EOF
echo -e "${GREEN}[6/7] Configuring firewall...${NC}"
if command -v ufw >/dev/null 2>&1; then
ufw --force enable
ufw allow 80/tcp
ufw allow 443/tcp
ufw allow 8404/tcp
elif command -v firewall-cmd >/dev/null 2>&1; then
systemctl enable firewalld
systemctl start firewalld
firewall-cmd --permanent --add-port=80/tcp
firewall-cmd --permanent --add-port=443/tcp
firewall-cmd --permanent --add-port=8404/tcp
firewall-cmd --reload
fi
# Set proper permissions
chmod 644 /etc/haproxy/haproxy.cfg
chown root:root /etc/haproxy/haproxy.cfg
chmod 644 /etc/security/limits.d/haproxy.conf
echo -e "${GREEN}[7/7] Starting and enabling HAProxy...${NC}"
systemctl enable haproxy
systemctl restart haproxy
echo -e "${GREEN}Verifying installation...${NC}"
if systemctl is-active --quiet haproxy; then
echo -e "${GREEN}✓ HAProxy is running${NC}"
else
echo -e "${RED}✗ HAProxy failed to start${NC}"
exit 1
fi
if haproxy -f /etc/haproxy/haproxy.cfg -c; then
echo -e "${GREEN}✓ Configuration is valid${NC}"
else
echo -e "${RED}✗ Configuration has errors${NC}"
exit 1
fi
echo -e "${GREEN}Installation completed successfully!${NC}"
echo -e "${YELLOW}Stats available at: http://$(hostname -I | awk '{print $1}'):8404/stats${NC}"
echo -e "${YELLOW}Load balancer listening on port 80${NC}"
Review the script before running. Execute with: bash install.sh