Replicación en memcached
En teoría los datos contenidos en un memcached deberían ser algo que la aplicación no dependa de su existencia: paginas cacheadas (se pueden regenerar) o sesiones de usuario (se deben volver a autenticar) Si la aplicación dependen mucho de ello o se estima muy importante no perder la sesión del usuario podemos usar replicación de memcached mediante el parche de repcached
Primero de todo vamos a necesitar, igual que cualquier memcached, libevent instalado:
cd /usr/local/src wget http://monkey.org/~provos/libevent-1.4.8-stable.tar.gz tar xzf libevent-1.4.8-stable.tar.gz cd libevent-1.4.8-stable ./configure --prefix=/usr/local/ --exec-prefix=/usr/local/ make && make install
A continuación podemos bajar una versión de memcached ja parcheada desde la web de repcached:
cd /usr/local/src wget http://sourceforge.net/projects/repcached/files/repcached/2.2-1.2.8/memcached-1.2.8-repcached-2.2.tar.gz/download tar xzf memcached-1.2.8-repcached-2.2.tar.gz cd memcached-1.2.8-repcached-2.2 ./configure --prefix=/usr/local/ --exec-prefix=/usr/local/ --enable-64bit --enable-replication
La opción enable-threads es incompatible con la enable-replication
enable-threads, por lo que el memcached resultante sera un solo proceso sin threads.
Para saber como funciona en el man no he visto nada, asi que me he ido a la función main del memcached.c, donde encontramos:
#ifdef USE_REPLICATION
case 'x':
if (inet_pton(AF_INET, optarg, &addr) <= 0) {
memset(&master_hint, 0, sizeof(master_hint));
master_hint.ai_flags = 0;
master_hint.ai_socktype = 0;
master_hint.ai_protocol = 0;
if(!getaddrinfo(optarg, NULL, &master_hint, &master_addr)){
settings.rep_addr = ((struct sockaddr_in *)(master_addr->ai_addr)) -> sin_addr;
freeaddrinfo(master_addr);
}else{
fprintf(stderr, "Illegal address: %s\n", optarg);
return 1;
}
} else {
settings.rep_addr = addr;
}
break;
case 'X':
settings.rep_port = atoi(optarg);
break;
case 'q':
settings.rep_qmax = atoi(optarg);
break;
#endif /* USE_REPLICATION */
Así entiendo que mediante la opción -x indicamos el peer y con el -X el puerto del peer, asi que lo probamos arrancando una instancia:
# /usr/local/bin/memcached -u memcached -p 11211 -m 64 -x 127.0.0.1 -v replication: connect (peer=127.0.0.1:11212) replication: marugoto copying replication: close replication: listen
Y una segunda para hacer la replicación:
# /usr/local/bin/memcached -u memcached -p 22322 -m 64 -x 127.0.0.1 -v replication: connect (peer=127.0.0.1:11212) replication: accept replication: marugoto copying replication: start
A continuación podemos ver los puertos que escucha y la conexión entre los dos memcacheds para replicar los datos:
# netstat -tpan | grep memcache tcp 0 0 0.0.0.0:22322 0.0.0.0:* LISTEN 20069/memcached tcp 0 0 0.0.0.0:11211 0.0.0.0:* LISTEN 20068/memcached tcp 0 0 127.0.0.1:11212 127.0.0.1:50480 ESTABLISHED 20068/memcached tcp 0 0 127.0.0.1:50480 127.0.0.1:11212 ESTABLISHED 20069/memcached
Podemos probar haciendo un set en el primer memcached:
# telnet localhost 11211 Trying ::1... Connected to localhost. Escape character is '^]'. set web 0 0 14 systemadmin.es STORED quit Connection closed by foreign host.
Y a continuación el get en el segundo:
# telnet localhost 22322 Trying ::1... Connected to localhost. Escape character is '^]'. get web VALUE web 0 14 systemadmin.es END quit Connection closed by foreign host.
Y el caso inverso, el set en el segundo:
# telnet localhost 22322 Trying ::1... Connected to localhost. Escape character is '^]'. set ejemplo 0 0 14 systemadmin.es STORED quit Connection closed by foreign host.
Y el get en el primero:
# telnet localhost 11211 Trying ::1... Connected to localhost. Escape character is '^]'. get ejemplo VALUE ejemplo 0 14 systemadmin.es END quit Connection closed by foreign host.
Podemos comprobar la replicación (la alta disponibilidad) matando al primero:
# jobs [1]- Running /usr/local/bin/memcached -u memcached -p 11211 -m 64 -x 127.0.0.1 -v & [2]+ Running /usr/local/bin/memcached -u memcached -p 22322 -m 64 -x 127.0.0.1 -v & # fg 1 /usr/local/bin/memcached -u memcached -p 11211 -m 64 -x 127.0.0.1 -v ^Creplication: cleanup start replication: close replication: cleanup complete replication: close replication: listen
Y intentando obtener los datos:
# telnet localhost 22322 Trying ::1... Connected to localhost. Escape character is '^]'. get web VALUE web 0 14 systemadmin.es END get ejemplo VALUE ejemplo 0 14 systemadmin.es END quit Connection closed by foreign host.
Es una forma cómoda de obtener una alta disponibilidad de los datos de memcached, pero evidentemente a costa de dividir por dos la memoria disponible para datos. Para repartir las queries de memcached en este escenario se puede hacer tanto a nivel de aplicación como mediante un balanceador como LVS.
Relacionados
Imprimir
Deja un comentario: