HAProxy et MySQL, le couple parfait

Avoir un serveur MySQL c'est bien.
En avoir deux, c'est mieux. Mais encore faut-il que l'application cliente appelle un serveur disponible, et si possible pas toujours le même... Et c'est aussi à ça que sert HAProxy. (Ouf, le sujet tient la route, on peut continuer).

Si vous n'avez pas HAProxy, débrouillez-vous pour l'installer demandez-le à votre gestionnaire de paquets, il l'a sans doute en réserve ;-) (apt install haproxy sur Debian)

Note 1: les configurations sont fonctionnelles sans modifications, mais ne sont pas les plus adaptées : pas de panel de stats, par exemple.

Note 2: La configuration suppose que vous avez les mêmes privilèges sur chacun des serveurs. Si vous avez du Master-Slave (et donc un seul serveur capable de modifier les données), il vaut mieux utiliser mysql-proxy. Fonctionne aussi avec un cluster Multi-Master.


HAProxy écoute sur un port (frontend), reçoit les requêtes et les distribue entre les serveurs (backend).
Supposons que nous ayons deux serveurs MySQL : db-1.ungeek.fr et db-2.ungeek.fr.

HAProxy peut répartir la charge entre ces deux serveurs, avec la méthode Round Robin:

# /etc/haproxy/haproxy.cfg
global  
    log 127.0.0.1 local0 notice
    user haproxy
    group haproxy

defaults  
    log global
    retries 2
    timeout connect 3000
    timeout server 1m
    timeout client 1m
    option allbackups

listen mysql-cluster  
    bind 127.0.0.1:3307
    mode tcp
    balance roundrobin
    server mysql-1 db-1.ungeek.fr:3306
    server mysql-2 db-2.ungeek.fr:3306

Les parties global et default sont communes à toutes les configurations présentées ici et seront donc ignorées par la suite.

La configuration listen est assez simple à comprendre: HAProxy écoute sur le port 3307, dans le mode tcp (et non http), répartit les requêtes avec la méthode roundrobin entre deux serveurs nommés mysql-1 et mysql-2.


Cependant, il n'y a pas de détection de disponibilité : si le serveur 1 tombe, il sera toujours utilisé ... pas bien. Modifions donc la configuration pour prendre en compte ce détail.

listen mysql-cluster  
    bind 127.0.0.1:3307
    mode tcp
    balance roundrobin
    option mysql-check
    default-server fastinter 1000
    server mysql-1 db-1.ungeek.fr:3306 check
    server mysql-2 db-2.ungeek.fr:3306 check

La différence ? On active l'option mysql-check, et on ajoute check à chaque ligne de serveur. C'est tout. Et ça marche.

Il y a plein d'autres options détaillées dans la doc', en particulier backup, rise et weight.

En bonus, l'option fastinter 1000 permet d'améliorer la détection de changement d'état : par défaut, HAProxy vérifie toutes les 2 secondes que les services sont UP.
Avec cette option, à chaque fluctuation, une seconde vérification est lancée 1 seconde après. (Au bout de 2 vérifications échouées, le serveur est marqué DOWN et n'est plus utilisé).