51 06/04/2026 07/04/2026 10 min

Caricare servizi di scambio saldo con HAProxy

Quando un servizio di scambio saldo deve reggere carichi variabili, HAProxy è una scelta solida per distribuire le richieste in modo prevedibile, mantenere alta disponibilità e isolare rapidamente i nodi guasti. Il punto non è solo “mettere un bilanciatore davanti”: serve decidere come vengono instradate le richieste, come si rileva un backend degradato, cosa succede durante un picco e come si gestiscono le sessioni se l’applicazione ha stato.

In questo scenario il problema tipico è semplice da descrivere: gli utenti inviano operazioni di saldo, il front-end riceve il traffico, ma il carico non deve concentrarsi su un singolo nodo applicativo. L’obiettivo è mantenere bassa la latenza, evitare errori intermittenti e non perdere coerenza nelle transazioni. HAProxy aiuta, ma va configurato con criterio.

Obiettivo architetturale

Prima di toccare la configurazione, chiarisci il comportamento atteso:

  • le richieste devono essere distribuite su più istanze applicative;
  • un nodo non sano deve uscire automaticamente dal pool;
  • le sessioni, se necessarie, devono essere gestite in modo coerente;
  • il bilanciamento deve restare osservabile e semplice da manutenere;
  • i controlli devono distinguere tra backend raggiungibile e applicazione davvero pronta.

Per un servizio di scambio saldo, la scelta più prudente è trattare il bilanciamento come parte della catena di affidabilità, non come un semplice reverse proxy. Se il backend risponde ma non è pronto a processare operazioni, un health check banale può ingannarti. Se il sistema usa token di sessione o operazioni legate a uno stato temporaneo, il modo in cui distribuisci il traffico cambia il risultato percepito dall’utente.

Scelta del tipo di bilanciamento

HAProxy supporta vari algoritmi. La selezione va fatta in base al tipo di traffico e alla natura del servizio.

  • roundrobin: distribuzione uniforme, buona base generale;
  • leastconn: utile quando le richieste hanno durata molto variabile;
  • source: utile se vuoi un certo grado di affinità basata sull’IP client;
  • uri o altre strategie avanzate: da usare solo se hai un motivo preciso e hai misurato l’effetto.

Per servizi di scambio saldo, in genere leastconn è una scelta sensata quando i tempi di elaborazione non sono omogenei. Se invece le operazioni sono brevi e simili, roundrobin è spesso sufficiente. Evita di introdurre complessità inutili: ogni algoritmo “intelligente” in più è anche una variabile in più da spiegare in caso di incidente.

Configurazione base di HAProxy

Una configurazione minima, chiara e manutenibile è preferibile a una dichiarazione troppo compatta. L’idea è separare frontend, backend e controlli di stato.

global
    log /dev/log local0
    log /dev/log local1 notice
    maxconn 50000
    user haproxy
    group haproxy
    daemon

defaults
    log global
    mode http
    option httplog
    option dontlognull
    timeout connect 5s
    timeout client  30s
    timeout server  30s
    timeout http-request 10s

frontend fe_balance
    bind *:80
    bind *:443 ssl crt /etc/haproxy/certs/site.pem
    http-request redirect scheme https unless { ssl_fc }
    default_backend be_balance

backend be_balance
    balance leastconn
    option httpchk GET /health
    http-check expect status 200
    server app1 10.0.0.11:8080 check
    server app2 10.0.0.12:8080 check
    server app3 10.0.0.13:8080 check

Questa base è utile perché introduce tre concetti essenziali: terminazione TLS sul frontend, distribuzione delle richieste sul backend e health check applicativo. Se il tuo servizio espone già HTTPS verso l’utente, puoi lasciare il TLS terminato su HAProxy. Se invece il TLS deve restare end-to-end, la configurazione cambia e va gestita con attenzione, soprattutto per i controlli di salute.

Health check: la parte che evita i falsi positivi

Il controllo di salute non deve limitarsi al fatto che la porta TCP sia aperta. Per un servizio di scambio saldo questo sarebbe troppo debole: il processo può ascoltare ma essere incapace di servire richieste corrette. Meglio usare un endpoint dedicato, ad esempio /health o /ready, che verifichi almeno la raggiungibilità delle dipendenze critiche.

La distinzione utile è questa:

  • liveness: il processo è vivo?
  • readiness: il servizio è pronto a ricevere traffico?

Se hai un backend che può avviarsi prima del database o di una coda, liveness e readiness non coincidono. HAProxy dovrebbe usare la readiness come criterio per togliere o rimettere un nodo nel pool. In pratica, se il servizio risponde 200 ma non è in grado di completare le operazioni di scambio saldo, il check è sbagliato.

Se l’applicazione non ha ancora un endpoint dedicato, crearlo è spesso il miglior investimento operativo. Deve essere rapido, senza dipendenze pesanti, ma sufficientemente rappresentativo dello stato reale del servizio. Non devi interrogare tutto il mondo per sapere se un nodo può servire traffico.

Sessioni e affinità

Un servizio di scambio saldo può essere stateless, ma spesso non lo è completamente. Se esistono sessioni utente, token temporanei o flussi che dipendono da dati in memoria, devi decidere come gestire l’affinità.

Le opzioni pratiche sono:

  • nessuna affinità, se l’app è davvero stateless e tutte le informazioni stanno in storage condiviso;
  • cookie persistence, se vuoi mantenere l’utente sullo stesso nodo;
  • source stickiness, se ti basta mantenere coerenza per IP client, sapendo che non è sempre affidabile dietro NAT o proxy.

Se usi cookie di persistenza, HAProxy può inserirli o rispettarli. Questa soluzione è utile quando non puoi refactoring subito l’applicazione, ma ha un costo: può ridurre l’efficacia del bilanciamento durante picchi asimmetrici. Non usarla per abitudine; usala solo se il comportamento applicativo lo richiede davvero.

Per sistemi finanziari o di scambio saldo, la soluzione migliore resta quasi sempre la statelessness applicativa con sessioni esterne, ad esempio in Redis o in un database condiviso, così HAProxy può distribuire liberamente il traffico senza forzature.

Timeout e protezione dal degrado

I timeout sono uno dei punti più sottovalutati. Se sono troppo lunghi, i client restano appesi e consumi risorse; se sono troppo corti, generi falsi errori durante picchi normali. Devi tararli sulla metrica che ti interessa: latenza p95, error rate o tempo di completamento operazioni.

Per un servizio di scambio saldo, l’obiettivo tipico è mantenere bassa la latenza percepita senza far accumulare connessioni in attesa. I parametri da osservare sono:

  • tempo di connessione verso il backend;
  • tempo di risposta dell’applicazione;
  • numero di connessioni in coda;
  • errori 5xx o timeout lato client.

Se noti che il backend è lento ma ancora sano, HAProxy può aiutare limitando il danno: riduce la pressione sui nodi saturi e continua a inviare traffico solo dove il check risulta positivo. Se invece il problema è a monte, per esempio nel database, il bilanciatore non risolve la causa, ma evita che tutto collassi nello stesso punto.

Osservabilità operativa

Un bilanciatore senza visibilità è solo un punto cieco davanti ai problemi. HAProxy offre statistiche e log utili per capire dove si concentra il traffico e quali backend stanno fallendo.

Attiva almeno questi elementi:

  • log HTTP con status code e tempi;
  • pagina o socket di statistiche protetti;
  • controlli health con stato di ogni server;
  • metriche su connessioni attive, code e error rate.

Una configurazione utile per l’operatività è esporre le stats su una rete di management o dietro autenticazione stretta. Non lasciare la console di stato aperta in chiaro su Internet. Se usi Prometheus o un sistema di monitoring analogo, raccogli i dati del bilanciatore e correlali con i log applicativi: il valore vero emerge quando vedi insieme frontend, backend e database.

Gestione del TLS

Se il servizio è pubblico, il TLS va trattato come parte del progetto, non come un dettaglio finale. In HAProxy puoi terminare il TLS sul frontend e inoltrare il traffico al backend in chiaro nella rete interna, oppure mantenere TLS fino ai backend.

La terminazione sul bilanciatore semplifica:

  • gestione certificati;
  • offload della cifratura;
  • controllo centralizzato delle policy;
  • redirect HTTP verso HTTPS.

Ma se l’ambiente richiede cifratura end-to-end, ad esempio per policy interne o segmentazione forte, devi configurare anche i backend in TLS e verificare i certificati lato origin. In quel caso i health check devono essere compatibili con il protocollo scelto, altrimenti avrai nodi marcati down per un problema di trasporto e non di servizio.

In ogni caso, tieni sotto controllo la scadenza dei certificati. Un bilanciatore funzionante ma con certificato scaduto produce un disservizio immediato e facile da evitare con monitoraggio semplice.

Hardening minimo

Un servizio di scambio saldo espone dati sensibili e quindi merita alcune precauzioni di base:

  • limitare l’accesso alla pagina stats;
  • usare account di servizio con privilegi minimi;
  • separare rete pubblica e rete backend;
  • non esporre socket di amministrazione senza controllo;
  • mantenere i certificati e le chiavi fuori da percorsi accessibili impropriamente.

Se HAProxy gira su Linux recente, usa systemd per controllare avvio, restart e dipendenze. Verifica anche che il processo non abbia permessi più ampi del necessario. Nel dubbio, meglio un servizio più semplice da auditare che una configurazione ricca ma opaca.

Strategia di deploy senza rischio inutile

Quando cambi la configurazione, evita il salto diretto in produzione senza validazione. La sequenza corretta è:

  1. salvare la configurazione corrente;
  2. validare la nuova sintassi;
  3. applicare il change in finestra controllata;
  4. verificare health, latenza e distribuzione;
  5. tenere pronto il rollback immediato.

Il controllo di sintassi è basilare ma non sufficiente. Una config formalmente valida può comunque essere sbagliata dal punto di vista funzionale: backend non raggiungibili, certificati errati, path health check non coerente, sticky session configurata male. Per questo la verifica post-deploy deve includere almeno una richiesta reale e l’osservazione dello stato dei server nel pool.

Test pratici prima del go-live

Prima di mettere il bilanciatore davanti al traffico reale, fai test semplici ma mirati:

  • richiesta HTTP di prova verso il frontend;
  • verifica che i backend rispondano attraverso HAProxy;
  • simulazione del down di un nodo per vedere se esce dal pool;
  • verifica della persistenza sessione, se prevista;
  • test di carico leggero per osservare distribuzione e tempi.

Non serve un laboratorio complesso per scoprire errori grossolani. Spesso basta spegnere un backend di test e controllare se il traffico continua a passare sugli altri. Se il bilanciatore continua a mandare richieste al nodo guasto, il check è sbagliato o troppo permissivo.

Errori comuni da evitare

Ci sono alcuni errori che si ripetono spesso nei progetti con HAProxy davanti a servizi transazionali:

  • health check basato solo su TCP;
  • timeout troppo lunghi “per sicurezza”;
  • sticky session usata come stampella permanente;
  • stats esposte senza protezione;
  • assenza di piano di rollback;
  • configurazione non allineata con la reale capacità dei backend.

Il più pericoloso è il primo: se il bilanciatore considera sano un processo che ascolta ma non lavora, il disservizio si manifesta solo sotto carico o durante una dipendenza degradata. Il secondo errore è pensare che il bilanciatore risolva problemi di database: non li risolve, li rende solo più visibili.

Rollback operativo

Ogni change su HAProxy deve avere un rollback chiaro e rapido. Il rollback tipico è ripristinare il file di configurazione precedente e ricaricare il servizio. Tieni sempre una copia nota buona prima di introdurre modifiche al bilanciamento, ai check o al TLS.

La regola pratica è semplice: se una modifica aumenta gli errori, la latenza o la percentuale di backend marcati down senza motivo, torna subito alla versione precedente e analizza a freddo. Non tentare più modifiche in sequenza durante un incidente: perdi tracciabilità e rendi più difficile capire quale cambiamento ha introdotto il problema.

Conclusione operativa

Caricare servizi di scambio saldo con HAProxy funziona bene quando il bilanciamento è trattato come parte dell’affidabilità del servizio. La configurazione deve essere semplice, i controlli di salute devono rappresentare lo stato reale dell’applicazione, le sessioni vanno gestite solo se necessario e ogni change deve essere reversibile. Se mantieni questi punti, HAProxy diventa un componente stabile della catena e non un ulteriore fattore di rischio.

Assunzione: il servizio applicativo espone un endpoint di health/readiness e i backend sono raggiungibili su rete interna dedicata.