HAProxy 2.0: reintentar algunas de las solicitudes según la URL

HAProxy 2.0: reintentar algunas de las solicitudes según la URL

Tengo instalada la versión 2.0.14 de HAProxy y estoy buscando un caso de uso peculiar que aún no he logrado configurar correctamente.

Básicamente tengo una interfaz que escucha en un puerto y dos servidores backend. Una vez que se inicia una sesión, se utilizan cookies, por lo que una sesión está vinculada a un servidor backend particular y no se puede compartir con otro servidor. Para lograr esto stick-table, estoy usando stick onpalabras clave y un script LUA para obtener el valor requerido de las solicitudes.

Sin embargo, cuando llega la primera solicitud, si el servidor backend seleccionado no responde a tiempo, debemos realizar una conmutación por error al otro, ya que en ese momento la cookie aún no está configurada.

Hasta ahora tengo la siguiente configuración:

global
   log 127.0.0.1 len 10000 local2 debug
   chroot /var/lib/haproxy
   user haproxy
   group haproxy
   daemon
   lua-load /opt/LUA/myparser.lua

   stats socket /etc/haproxy/haproxysock level admin

defaults
   log global
   option httplog
   option dontlognull
   mode http
   timeout connect 5000
   timeout client 50000
   timeout server 50000
   log-format "Client IP:port = [%ci:%cp], Start Time = [%tr], Frontend Name = [%ft], Backend Name = [%b], Backend Server = [%s], Time to receive full request = [%TR ms], Response time = [%Tr ms], Status Code = [%ST], Bytes Read = [%B]"

frontend chatgw_front
   bind *:8776

   option http-buffer-request
   declare capture request len 40000
   http-request capture req.body id 0
   http-request capture req.hdrs len 2048

   http-request track-sc0 src table my_back
   use_backend my_back

backend my_back
   balance roundrobin

   stick-table type string len 32 size 30k expire 30m
   stick on "lua.parseId" table my_back

   server server1 x.x.x.1:8080 check
   server server2 x.x.x.2.8080 check

Lo que esto hace es que si el servidor backend seleccionado no responde en 50 segundos, genera un tiempo de espera de puerta de enlace HTTP 504 al cliente. En cambio, lo que necesitaría es, si esta es la primera solicitud en una sesión, entonces (y solo entonces) una conmutación por error a otro servidor backend. Podemos decir que esta es la primera solicitud según la URL.

Intenté cambiar el backend así:

backend my_back
   balance roundrobin

   stick-table type string len 32 size 30k expire 30m
   stick on "lua.parseId" table my_back

# Check if this is "init" request: in this case URL contains "/init"
   acl is_init path_sub /init

# In case of "init" request, enable redispatch to other backend server in case failure
   option redispatch if is_init

# In case of other requests (not "init"), we are already tied to a selected backend server due to session cookie, so disable redispatch
   no option redispatch if !is_init

   server server1 x.x.x.1:8080 check
   server server2 x.x.x.2.8080 check

Sin embargo, obtuve exactamente el mismo comportamiento. Entonces intenté agregar "reintentar":

backend my_back
   balance roundrobin

   stick-table type string len 32 size 30k expire 30m
   stick on "lua.parseId" table my_back

   acl is_init path_sub /init

   option redispatch if is_init

   no option redispatch if !is_init

   retry-on conn-failure empty-response response-timeout

   server server1 x.x.x.1:8080 check
   server server2 x.x.x.2.8080 check

Ahora, es diferente: intentó la solicitud inicial 4 veces en el mismo servidor y luego devolvió el HTTP 504. Luego recibió la siguiente solicitud (que no es "init", por lo que no debería apegarse al servidor backend seleccionado ), y esto se envió al otro servidor.

Básicamente, mi problema es: ¿cómo implementar la conmutación por error solo en la primera solicitud? Cualquier otra solicitud siempre debe ceñirse al servidor backend seleccionado.

información relacionada