dsp_099
dsp_099

Reputation: 6121

Count redis keys without fetching them in Ruby

I'm keeping a list of online users in Redis with one key corresponding to one user. Keys are set to time out in 15 minutes, so all I have to do to see how many users have roughly been active in the past 15 minutes, I can do:

redisCli.keys('user:*').count

The problem is as the number of keys grows, the time it takes to fetch all the keys before counting them is increasing noticeably. Is there a way to count the keys without actually having to fetch all of them first?

Upvotes: 1

Views: 2100

Answers (2)

antirez
antirez

Reputation: 18504

There is an alternative to directly indexing keys in a Set or Sorted Set, which is to use the new SCAN command. It depends on the use case, memory / speed tradeoff, and required precision of the count.

Another alternative is that you use Redis HyperLogLogs, see PFADD and PFCOUNT.

Upvotes: 3

Uri Agassi
Uri Agassi

Reputation: 37409

Redis does not have an API for only counting keys with a specific pattern, so it is also not available in the ruby client.

What I can suggest is to have another data-structure to read to number of users from.

For instance, you can use redis's SortedSet, where you can keep each user with the timestamp of its last TTL set as the score, then you can call zcount to get the current number of active users:

redisCli.zcount('active_users', 15.minutes.ago.to_i, Time.now.to_i)

From time to time you will need to clean up the old values by:

redisCli.zremrangebyscore 'active_users', 0, 15.minutes.ago.to_i 

Upvotes: 2

Related Questions