Configuration Reference
This document provides detailed configuration references for all components of the PQC SSL deployment. All examples are based on our production deployment at pqcnow.com.
Table of Contents
1. HAProxy Configuration 2. Nginx Configuration 3. Apache Configuration 4. systemd Service Configuration 5. Docker Deployment 6. Advanced Scenarios
---
HAProxy Configuration
HAProxy acts as a layer-4 (TCP) proxy that routes traffic based on Server Name Indication (SNI) without decrypting SSL/TLS.
Complete HAProxy Configuration
File: \/etc/haproxy/haproxy.cfg\
\\\haproxy
global
# Logging configuration
log /dev/log local0
log /dev/log local1 notice
# Security: run in chroot jail
chroot /var/lib/haproxy
# Admin socket for runtime management
stats socket /run/haproxy/admin.sock mode 660 level admin
stats timeout 30s
# User/group to run as
user haproxy
group haproxy
# Run as daemon
daemon
# Maximum concurrent connections
maxconn 2000
# SSL/TLS tuning (optional)
# tune.ssl.default-dh-param 2048
defaults log global mode tcp # Layer 4 (TCP) mode for SNI routing option tcplog # TCP-specific logging option dontlognull # Don't log null connections timeout connect 5000 # 5 seconds to establish connection timeout client 50000 # 50 seconds client inactivity timeout server 50000 # 50 seconds server inactivity # Error handling retries 3 option redispatch
Main HTTPS frontend - routes based on SNI
frontend https_front bind *:443 # Listen on all interfaces, port 443 mode tcp option tcplog # SNI inspection settings tcp-request inspect-delay 5s # Wait up to 5s to inspect SNI tcp-request content accept if { req_ssl_hello_type 1 } # ACLs for routing based on SNI # Add your PQC domain here acl is_pqc_demo req_ssl_sni -i demo.pqcnow.com acl is_pqc_demo req_ssl_sni -i pqc.pqcnow.com # Routing logic use_backend pqc_demo if is_pqc_demo default_backend main_siteBackend for traditional SSL website
backend main_site mode tcp balance roundrobin # Load balancing algorithm # Backend server(s) server nginx1 127.0.0.1:8080 check inter 2000 rise 2 fall 3 # Add more servers for load balancing: # server nginx2 127.0.0.1:8081 check inter 2000 rise 2 fall 3 # Health check settings option tcp-checkBackend for PQC demo website
backend pqc_demo mode tcp balance roundrobin # Backend PQC server(s) server pqc1 127.0.0.1:9443 check inter 2000 rise 2 fall 3 # Add more servers for load balancing: # server pqc2 127.0.0.1:9444 check inter 2000 rise 2 fall 3 # Health check settings option tcp-checkOptional: HAProxy statistics page
listen stats bind *:8404 # Stats page on port 8404 mode http stats enable stats uri /stats # Access via http://server:8404/stats stats refresh 30s stats auth admin:your-password-here # Change this! \\\HAProxy ACL Examples
Different SNI matching patterns:
\\\haproxy
Exact match
acl is_pqc req_ssl_sni -i pqc.example.com
Multiple domains
acl is_pqc req_ssl_sni -i pqc.example.com demo.example.comWildcard matching
acl is_pqc req_ssl_sni -m end .pqc.example.comRegex matching
acl is_pqc req_ssl_sni -m reg ^pqc[0-9]+\.example\.com$ \\\Testing HAProxy Configuration
\\\bash
Check configuration syntax
haproxy -c -f /etc/haproxy/haproxy.cfg
Reload without downtime
systemctl reload haproxyView logs
journalctl -u haproxy -f \\\---
Nginx Configuration
Main Site Configuration (Traditional SSL)
File: \/etc/nginx/sites-available/pqcnow.com\ (Production Example)
\\\nginx
HTTP to HTTPS redirect
server {
listen 80;
listen [::]:80;
server_name pqcnow.com www.pqcnow.com;
# ACME challenge for Let's Encrypt
location /.well-known/acme-challenge/ {
root /var/www/letsencrypt;
}
# Redirect all other traffic to HTTPS
location / {
return 301 https://\$host\$request_uri;
}
}
HTTPS server on backend port 8080
HAProxy forwards :443 traffic here based on SNI
server { listen 8080 ssl http2; listen [::]:8080 ssl http2; server_name pqcnow.com www.pqcnow.com;# Document root root /var/www/pqcnow-laravel/public; index index.php index.html index.htm;
# Let's Encrypt SSL certificate ssl_certificate /etc/letsencrypt/live/pqcnow.com-0001/fullchain.pem; ssl_certificate_key /etc/letsencrypt/live/pqcnow.com-0001/privkey.pem;
# SSL configuration ssl_protocols TLSv1.2 TLSv1.3; ssl_ciphers HIGH:!aNULL:!MD5; ssl_prefer_server_ciphers on; ssl_session_cache shared:SSL:10m; ssl_session_timeout 10m;
# Security headers add_header Strict-Transport-Security "max-age=31536000; includeSubDomains" always; add_header X-Frame-Options "SAMEORIGIN" always; add_header X-Content-Type-Options "nosniff" always; add_header X-XSS-Protection "1; mode=block" always;
# Laravel specific location / { try_files \$uri \$uri/ /index.php?\$query_string; }
# PHP-FPM configuration location ~ \.php$ { include snippets/fastcgi-php.conf; fastcgi_pass unix:/var/run/php/php8.2-fpm.sock; fastcgi_param SCRIPT_FILENAME \$realpath_root\$fastcgi_script_name; include fastcgi_params; }
# Deny access to hidden files location ~ /\. { deny all; access_log off; log_not_found off; }
# Logging access_log /var/log/nginx/pqcnow.com.access.log; error_log /var/log/nginx/pqcnow.com.error.log;
# WebSocket support (if needed)
location /ws {
proxy_pass http://127.0.0.1:6001;
proxy_http_version 1.1;
proxy_set_header Upgrade \$http_upgrade;
proxy_set_header Connection "upgrade";
proxy_set_header Host \$host;
proxy_cache_bypass \$http_upgrade;
}
}
\\\
PQC Demo HTTP Redirect
File: \/etc/nginx/sites-available/demo.pqcnow.com\
\\\nginx
HTTP to HTTPS redirect for PQC demo
server {
listen 80;
listen [::]:80;
server_name demo.pqcnow.com;
# Redirect to HTTPS # HAProxy will route HTTPS traffic to BoringSSL server location / { return 301 https://\$server_name\$request_uri; }
# Optional: serve ACME challenge if using Let's Encrypt for PQC cert
location /.well-known/acme-challenge/ {
root /var/www/letsencrypt;
}
}
\\\
Advanced Nginx Features
#### Rate Limiting
\\\nginx
In http block
limit_req_zone \$binary_remote_addr zone=general:10m rate=10r/s;
limit_req_zone \$binary_remote_addr zone=api:10m rate=2r/s;
In server block
location / { limit_req zone=general burst=20 nodelay; # ... rest of config }location /api/ {
limit_req zone=api burst=5 nodelay;
# ... rest of config
}
\\\
#### Caching Static Assets
\\\nginx
\Cache static files
location ~* \.(jpg|jpeg|png|gif|ico|css|js|svg|woff|woff2|ttf|eot|webp)$ {
expires 1y;
add_header Cache-Control "public, immutable";
access_log off;
}
\\
---
Apache Configuration
Main Site Configuration (Traditional SSL)
File: \/etc/apache2/sites-available/example.com-ssl.conf\
\\\apache
Listen on backend port 8080
Listen 8080
\
PQC Demo Apache Configuration
File: \/etc/apache2/sites-available/demo-pqc-apache.conf\ (Production Example)
\ Listen 9443\\apache
\PQC Demo Site with ML-DSA Certificate
Serves on port 9443 with PQC certificate
\
HTTP Redirect for Apache
File: \/etc/apache2/sites-available/000-default.conf\
\\\apache
\\
---
systemd Service Configuration
PQC Demo Server Service
File: \/etc/systemd/system/pqc-demo.service\ (Production Example)
\\\ini
[Unit]
Description=PQC HTTPS Demo Server
Documentation=https://pqcnow.com/docs/
After=network.target network-online.target
Wants=network-online.target
[Service] Type=simple User=root Group=root WorkingDirectory=/home/pqc
Command to start the PQC server
Arguments: certificate-bundle key port [web-root]
ExecStart=/home/pqc/bssl_https_server_pqc demo.pqcnow.com-bundle.crt demo.pqcnow.com.key 9443 /var/www/html/demoRestart policy
Restart=always RestartSec=5 StartLimitInterval=0Output to journal
StandardOutput=journal StandardError=journal SyslogIdentifier=pqc-demoSecurity settings
PrivateTmp=yes NoNewPrivileges=true ProtectSystem=strict ProtectHome=yes ReadWritePaths=/var/log/pqc-demoResource limits
LimitNOFILE=65536[Install]
WantedBy=multi-user.target
\\\
Managing the Service
\\\bash
Reload systemd after changes
systemctl daemon-reload
Enable service (start on boot)
systemctl enable pqc-demoStart service
systemctl start pqc-demoCheck status
systemctl status pqc-demoView logs
journalctl -u pqc-demo -fRestart service
systemctl restart pqc-demoStop service
systemctl stop pqc-demo \\\---
Docker Deployment
Docker Compose Configuration
File: \docker-compose.yml\
\\\yaml
version: '3.8'
services: # HAProxy SNI router haproxy: image: haproxy:2.8-alpine container_name: haproxy ports: - "80:80" - "443:443" volumes: - ./haproxy.cfg:/usr/local/etc/haproxy/haproxy.cfg:ro networks: - web restart: unless-stopped
# Main website (Nginx + traditional SSL) main-site: image: nginx:alpine container_name: main-site volumes: - ./nginx/nginx.conf:/etc/nginx/nginx.conf:ro - ./nginx/ssl:/etc/nginx/ssl:ro - ./www:/var/www/html:ro networks: - web expose: - "8080" restart: unless-stopped
# PQC demo server pqc-demo: build: context: . dockerfile: Dockerfile.pqc container_name: pqc-demo volumes: - ./pqc-certs:/opt/pqc/certificates:ro - ./pqc-www:/opt/pqc/www:ro networks: - web expose: - "9443" restart: unless-stopped command: [ "/opt/pqc/bssl_https_server_pqc", "/opt/pqc/certificates/pqc.example.com-bundle.crt", "/opt/pqc/certificates/pqc.example.com.key", "9443", "/opt/pqc/www" ]
networks:
web:
driver: bridge
\\\
Dockerfile for PQC Server
File: \Dockerfile.pqc\
\\\dockerfile
FROM ubuntu:22.04
Install dependencies
RUN apt-get update && apt-get install -y \ ca-certificates \ && rm -rf /var/lib/apt/lists/*Copy pre-built BoringSSL server
COPY bssl_https_server_pqc /opt/pqc/bssl_https_server_pqc RUN chmod +x /opt/pqc/bssl_https_server_pqcCreate directories
RUN mkdir -p /opt/pqc/certificates /opt/pqc/wwwWORKDIR /opt/pqc
EXPOSE 9443
Will be overridden by docker-compose command
CMD ["/opt/pqc/bssl_https_server_pqc", "--help"] \\\---
Advanced Scenarios
Multiple PQC Demo Sites
HAProxy configuration for multiple PQC sites:
\\\haproxy
frontend https_front
bind *:443
mode tcp
option tcplog
tcp-request inspect-delay 5s
tcp-request content accept if { req_ssl_hello_type 1 }
# Route different PQC demos to different backends
use_backend pqc_demo1 if { req_ssl_sni -i pqc1.example.com }
use_backend pqc_demo2 if { req_ssl_sni -i pqc2.example.com }
use_backend pqc_demo3 if { req_ssl_sni -i pqc3.example.com }
default_backend main_site
backend pqc_demo1 mode tcp server pqc1 127.0.0.1:9443 check
backend pqc_demo2 mode tcp server pqc2 127.0.0.1:9444 check
backend pqc_demo3
mode tcp
server pqc3 127.0.0.1:9445 check
\\\
Load Balancing
HAProxy configuration with multiple backend servers:
\\\haproxy
backend main_site
mode tcp
balance roundrobin
option httpchk GET /health
server web1 10.0.1.10:8080 check
server web2 10.0.1.11:8080 check
server web3 10.0.1.12:8080 check backup
backend pqc_demo
mode tcp
balance leastconn
server pqc1 10.0.2.10:9443 check
server pqc2 10.0.2.11:9443 check
\\\
Firewall Configuration
\\\bash
UFW (Ubuntu/Debian)
ufw allow 80/tcp
ufw allow 443/tcp
ufw allow 8404/tcp # HAProxy stats (if enabled)
iptables
iptables -A INPUT -p tcp --dport 80 -j ACCEPT iptables -A INPUT -p tcp --dport 443 -j ACCEPT \\\---
Configuration Testing
Test HAProxy
\\\bash
haproxy -c -f /etc/haproxy/haproxy.cfg
\\\
Test Nginx
\\\bash
nginx -t
\\\
Test Apache
\\\bash
apachectl configtest
\\\
Test SSL/TLS
\\\bash
Test traditional SSL
openssl s_client -connect example.com:443 -servername example.com
Test PQC server locally
openssl s_client -connect localhost:9443 -servername pqc.example.com \\\---
Related Documentation
- Installation Guide - Step-by-step setup
- Testing Guide - Verification procedures
- Troubleshooting - Common issues
Support
- Technical Support: support@pqcnow.com
- Website: https://pqcnow.com