Como criar um bloqueio distribuído com o Redis?

Na documentação do redis, descobri que um bloqueio primitivo pode ser implementado via SETNX:

http://redis.io/commands/setnx

C4 envia SETNX lock.foo para obter o bloqueio

O cliente com falha C3 ainda o mantém, portanto o Redis responderá com 0 a C4.

C4 envia GET lock.foo para verificar se o bloqueio expirou. Caso contrário, ele será suspenso por algum tempo e tentará novamente desde o início.

Em vez disso, se o bloqueio expirar porque o horário do Unix em lock.foo é mais antigo que o horário atual do Unix, o C4 tenta executar:

GETSET lock.foo

Por causa da semântica GETSET, C4 pode verificar se o valor antigo armazenado na chave ainda é um carimbo de data / hora expirado. Se for, o bloqueio foi adquirido.

Se outro cliente, por exemplo C5, foi mais rápido que C4 e adquiriu o bloqueio com a operação GETSET, a operação C4 GETSET retornará um carimbo de data / hora não expirado. O C4 simplesmente será reiniciado a partir do primeiro passo. Observe que, mesmo que C4 ajuste a tecla alguns segundos no futuro, isso não é um problema.

No entanto, como alguns usuários comentaram, usar um registro de data e hora do UNIX como expiração exige que o tempo do cliente e do servidor seja perfeitamente sincronizado. Existe uma alternativa melhor para criar um bloqueio global / distribuído no Redis?

questionAnswers(5)

yourAnswerToTheQuestion