Fri, 19 Jun 2009

Python-memcache errors en la selecció del servidor en cas de caiguda

Quan inspeccionava les problemàtiques intrínseques de memcached com a servidor de cache no bloquejant amb funcions de hash no consistents i les problemàtiques que això podia comportar - volia escriure un article al voltant d'això, vaig trobar-me que no podia reproduir alguns dels problemes que creien que es produirien mitjançant unes petites proves amb el modul de python-memcache.

Primer vaig pensar, vaig errat segurament he confós l'arquitectura. Però tot i la nocturnitat dels fets vaig estirar el fil. De fet el codi de pyton-memcache es un sol arxiu i seguir el fil de les funcions no es excessivament problemàtic. La idea principal del joc de proves era veure com es podien produir inconsistències de cache per culpa de la reasignació de claus a un o altre servidor en cas de caiguda d'un d'aquests. i La prova en si hauria d'haver sigut d'allò més senzilla però per casualitats de la vida no funcionava.

Mirant el codi actual de python-memcache vaig descobrir que utilitzava l'algoritme CRC32 per a calcular un hash "únic" a partir d'un string i que fent el mòdul d'aquest amb el número de servidors actuals s'obtenia a quin servidor connectar. Fins aquí tot correcte. El problema venia si aquell servidor no estava disponible, l'actual codi de python-memcache torna a calcular la hash concatenant un nou "digit" amb el valor de la iteració a la clau original. Per exemple, si la clau original es ABCDEF, el conjunt d'iteracions o claus provades seran ABCDEF1, ABCDEF12, ABCDEF123 i d'aquesta manera fins un màxim de 10 vegades - valor per defecte a Client._SERVER_RETRIES. Clar recordem que ha cada iteració es calcula el valor o hash d'ells. Que podria ser per exemple 100, 200, 300 i 400. Un cop es té aquest valor es fa servir el modul amb el numero de servidors, si en el nostre cas comptem amb dos servidors memcached tindrem 100 % 2, 200 % 2, 300 % 2, 400 % 2 que en tots els casos dona 0.

Si portem aquests valors a la realitat el que esta passant es que la possibilitat de trobar un servidor es redueix a la possibilitat de calcular un número que estigui en el rang de projecció de la funció hash, si tenim dos servidors tenim un 50% de possibilitats de calcular un valor que caigui en el rang d'actuació del servidor x.

Evidentment això es un problema, les ajudes de memcache ja diuen que si un servidor cau les claus associades a un servidor hauran de ser allotjades en un altre servidor - aquí rau un dels problemes de l'us de funcions hash no consitents. L'aproximació obvia que hauria d'haver efectuat el codi es la de la simple increment del valor inicial de la HASH. Per exemple començar per ABCDEF = 100, si falla 101 i d'aquesta manera fins arribar al nombre màxim de servidors disponibles.

Mes tard vaig estar revisant el codi de l'antiga llibreria oficial de memcache i utilitzava el mecanisme descrit en el pàrraf anterior. Mare de deu quines coses que es veuen a les 4 de la matinada.

Posted at: 04:41 | category: /memcached | Comments (0)


Name:


E-mail:


URL:


Comment: