Pour partager les sessions PHP entre les serveurs web au sein d'un cluster il est fréquent d'utiliser le stockage des dites sessions dans un backend memcache. Si ce partage permet de servir un même client depuis n'importe quel serveur tout en conservant ses sessions cela introduit néanmoins un SPOF dans l'architecture, on va voir dans ce billet qu'il est possible de gérer le failover avec 2 ou plus serveurs memcache.

PHP gère depuis la version 3.0.0. de la librairie php-memcache le paramètre memcache.redundancy qui bien que non documenté est déjà fonctionnel, le principe est d'associer ce paramètre à memcache.allow_failover et de définir plusieurs serveurs memcache pour le stockage des sessions.

Dans l'exemple suivant on configure php pour utiliser 2 serveurs qui ont pour ip 10.0.42.1 et 10.0.42.2

; On indique à php de gérer les sessions dans memcache
session.save_handler = memcache

; le save_path est composé des adresses des 2 serveurs
; séparées par une virgule
session.save_path = "udp://10.0.42.1:11211?persistent=1&weight=1&timeout=1&retry_interval=15,udp://10.0.42.2:11211?persistent=1&weight=1&timeout=1&retry_interval=15"

; permet d'avoir les clés indiques sur tous les serveurs
memcache.hash_strategy = consistent

; force php à lire/écrire sur un autre serveur en cas de
; défaillance du premier appelé
memcache.allow_failover = 1

; nb de serveurs memcache + 1
memcache.session_redundancy=3

L'explication de session_redundancy qui vaut le nombre de serveurs memcache + 1 est issue de ce document

Dorénavant si l'un des serveurs memcache est coupé les sessions sont sauvegardées, et à son retour il récupérera les sessions utilisées au fil de l'eau. Cette solution est satisfaisante dans le cas des sessions à durée de vie limitée ; pour une durée de 30 minutes il vous faudra ne pas couper les 2 serveurs memcache à moins de 30 minutes d'intervalles afin d'avoir toujours les sessions actives dans l'un des memcache. Pour conserver des sessions ad vitam aeternam il faudra se tourner vers un stockage dans une base de données ou s'assurer de répliquer le serveur memcache renaissant avec les données du serveur actif.