Search code examples
redisluasortedsetzset

Get random item from sorted set in Redis


I was needed to implement set of items with individual expiration, so I used zsetwith score of expiration timestamp. Now I want to get random item from range of not expired items, or at least from all items in set. How can I do it?

Can I get min and max rank of range and random rank in between of it via LUA scripting?

Redis version: 5.0.2


Solution

  • I solve this via following script:

    -- KEYS[1] - set key
    -- ARGV[1] - seed timestamp
    
    local count = redis.call('ZCARD', KEYS[1]) 
    if count ~= 0 then
        math.randomseed(ARGV[1]) 
        local rank = math.random(0, count - 1) 
        local range = redis.call('ZRANGE', KEYS[1], rank, rank)
        return range[1]
    else
        return ''
    end
    

    And because I search among all items I do sanitization from expired items every n seconds.