Что произойдет, если 2 рабочих вызовут ZREM на один и тот же элемент сортированного набора в одно и то же время? Вернет ли он true для рабочего, который фактически удаляет элемент, а false - другому, чтобы указать, что он не существует или он вернет true для обоих? Другими словами, внутренний атом ZREM?ZREM на Redis Sorted Set
1
A
ответ
3
Redis (в основном) однопоточный, поэтому все его операции являются атомарными, а ZREM не является исключением. Однако ваш вопрос заключается в том, чтобы сделать «ZPOP» атомарно, поэтому есть два возможных способа сделать это.
Вариант 1: ЧАСЫ/MULTI/EXEC
В псевдокоде это как оптимист сделка будет выглядеть:
:start
WATCH somekey
member = ZREVRANGE somekey 0 0
MULTI
ZREM somekey member
if not EXEC goto :start // or quit trying
Вариант 2: Lua скрипт
zpop.lua:
local member = redis.call('ZREVRANGE', KEYS[1], 0, 0)
return redis.call('ZREM', KEYS[1], member)
redis-cli --eval zpop.lua somekey
Примечание - Значение атома Если вы решили не использовать эти механизмы, которые обеспечивают атомарность, вы столкнетесь с проблемами раньше, чем вы думаете. Вот возможный сценарий:
Process A Redis Server Process B
ZREVRANGE ------------>
<------------- foo
<--------- ZADD +inf bar
OK --------->
ZREM foo -------------->
<-------------- 1
В приведенном выше примере, после того, как получает Foo, В вставляет строку с абсурдно высоким баллом, так что становится верхним элементом в наборе. A, однако, будет продолжаться и удалять предыдущее foo.
Это означает, что он ОК, чтобы получить самый верхний элемент, удалить его, а затем проверить, удалось ли это или нет? Это будет сделано только для того, чтобы каждый работник получал другой элемент. – umair
Если ответ ZREM равен 1 (предполагается, что вы пытаетесь удалить один элемент), это означает, что он был удален. Не нужно проверять и не беспокоиться о том, что другой рабочий получает тот же элемент - его больше не будет. –
Да, но перед удалением мне нужно знать, какой элемент удалить. Это будет сделано путем запроса диапазона, чтобы получить элемент с наивысшим результатом. Проблема в том, что если 2 работника получают один и тот же элемент, его можно удалить только, чтобы другой знал, что мне нужно повторно выбрать другой элемент. В основном, я пытаюсь реализовать ZPOP, которого нет. – umair