Redis is a popular in-memory key-value store known for its speed and flexibility. As a developer, you may often need to know the total number of keys stored in your Redis instances for monitoring and debugging purposes. This guide will demonstrate multiple methods to count keys in Redis.

Introduction to Redis Keyspaces

Before we jump into the key counting methods, let‘s first understand Redis keyspaces.

Redis stores data in databases that are isolated keyspaces. By default, there are 16 databases numbered 0 to 15. You can switch between these databases using the SELECT command. For example:

127.0.0.1:6379> SELECT 5  
OK
127.0.0.1:6379[5]>

This switches to database 5.

Each database has its own separate keyspace with no relation to other databases. So keys in database 0 are completely separate from keys in database 5.

This is an important distinction to understand before counting keys in Redis. When you count keys, you are counting keys in the currently selected database only.

Count Keys using DBSIZE

The simplest way to count total keys is using the DBSIZE command:

127.0.0.1:6379> DBSIZE
(integer) 100

DBSIZE returns the total number of keys in the currently selected database. It‘s extremely fast since Redis just returns an integer without having to scan the keyspace.

Keep in mind this counts all key types – strings, hashes, lists, sets, sorted sets, streams, etc.

To count keys in a specific database:

127.0.0.1:6379> SELECT 5 
OK
127.0.0.1:6379[5]> DBSIZE
(integer) 302  

So database 5 contains 302 keys. The DBSIZE result is instant since it‘s not actually counting, just returning a pre-calculated integer value.

One thing to note about DBSIZE is that expired keys which have not yet been evicted will still be counted in the total. So you may see a discrepancy between DBSIZE and actual in-use keys. We‘ll discuss how to analyze memory breakdowns later on.

Count Keys using KEYS

The KEYS command can match keys based on a pattern and return all matching keys. To get total keys, we can use the * wildcard which matches everything:

127.0.0.1:6379> KEYS * 
1) "key1"  
2) "key2"
3) "foo" 
...

It‘s important to note that KEYS actually scans and returns every single key, so it can get slow in large databases.

For example, this can take seconds or even minutes on databases with millions of keys:

127.0.0.1:6379> KEYS *   
... hangs ...

To count total keys with KEYS, you would have to do:

127.0.0.1:6379> KEYS * | GREP -c . 
(integer) 100302

The pipe to GREP -c counts lines returned by KEYS *. This gives the total key count but can get slow on huge databases.

In most cases, it‘s better to use DBSIZE unless you specifically need to retrieve all keys for something.

One other danger of KEYS is that since it blocks the server while processing, it can cause availability issues in production environments. On Redis Cluster, this is not as much of an issue since queries go to different nodes, but standalone Redis can be blocked fully until KEYS completes.

So avoid executing blocking KEYS queries in production scenarios.

Count Key Types

Sometimes you may want to count specific key types like hashes, lists or sorted sets.

This returns all hash key names:

127.0.0.1:6379> KEYS h* 
1) "hash1"
2) "somehash" 
3) "user:1000:hash"

We can combine this with GREP -c to count:

127.0.0.1:6379> KEYS h* | GREP -c .  
(integer) 200

There are 200 hash keys in this database. This can be done for lists, sets, sorted sets etc.

Understanding cardinalities of your different data types helps analyze storage breakdowns and utilization more effectively.

For example, here‘s a sample keyspace breakdown:

Type Count Avg Size Total % Memory
Hash 200 512 KB 102 GB 38%
List 100 128 KB 12 GB 5%
Set 1500 64 KB 96 GB 36%
String 500 4 KB 2 GB 1%
Sorted Set 50 256 KB 12 GB 5%
Stream 10 1 MB 10 GB 4%
Total 2360 256 KB 234 GB 100%

Having output like above helps identify keys taking up excess memory that could use eviction or other policies applied.

Using SCAN for Counting Keys

If KEYS is too slow on massive databases, Redis provides cursor based iteration using SCAN .

Basic syntax is:

127.0.0.1:6379> SCAN 0 MATCH * COUNT 1000 

This iterates through the keyspace 1000 keys at a time, matching all keys.

We have to iterate the entire database to count keys:

127.0.0.1:6379> SCAN 0 MATCH * COUNT 1000
1) "536"  
2) 1) "key:453" 
   2) "key:23" 
   3) "key:9092"
   ...
127.0.0.1:6379> SCAN 536 MATCH * COUNT 1000
...

The first integer returned by SCAN is a cursor to the next iteration. We repeat SCAN using this cursor until the cursor returns 0, indicating end of database.

To count keys, we have to increment a counter each SCAN and add up totals from each. This requires code instead of a simple command.

Most Redis client libraries have SCAN wrappers that handle the iteration automatically.

For example, in Python:

import redis

r = redis.Redis()
cursors = ‘0‘ 
count = 0

while cursors != 0:
   cursors, keys = r.scan(cursors=cursors, match=‘*‘, count=1000)  
   count += len(keys)

print(count) 

This performs incremental counting using SCAN behind the scenes.

Similar wrappers are available in most languages. But even with SCAN, counting keys has more overhead than a simple DBSIZE call. Use SCAN when you need to retrieve large keysets that don‘t fit in memory or avoid blocking.

Key Information using INFO

The INFO command provides tons of insight into a Redis server. We can use it to get keyspace information also.

This returns information for the currently selected database:

127.0.0.1:6379> INFO keyspace  
# Keyspace
db0:keys=36000,expires=190,avg_ttl=1528044

The important bits here are:

  • keys=36000 – Total number of keys
  • expires=190 – Number of keys with expiration set
  • avg_ttl=1528044 – Average TTL of keys with expiration

So there are 36000 total keys, out of which 190 keys have expiration set.

This provides useful insight into keys without having to crawl the entire keyspace.

We can also use INFO memory to understand storage breakdown between data types:

# Memory
used_memory:497393864
used_memory_human:474.42M
used_memory_rss:549178368
used_memory_peak:X
used_memory_peak_human:X
used_memory_lua:35840
mem_fragmentation_ratio:1.10
mem_allocator:jemalloc-5.1.0
active_defrag_running:0
lazyfree_pending_objects:0

# Memory by key type
hash_type:251
stream_type:3
set_type:2
zset_type:1
list_type:1
string_type:2

This provides storage used by hashes, lists, sets etc. Useful for deeper analysis.

Other Tips for Counting Keys

Here are some additional tips when counting keys in Redis:

  • Enabling RDB / AOF persistence provides exact key counts on restarts for database reconstruction.
  • Client side caching of counts can help avoid heavy server side counting.
  • Some Redis GUI tools like RedisInsight provide ways to visualize or count keys.
  • Key namespaces can help categorize subsets of keys for easier analysis.
  • Exporting metrics to Prometheus lets you graph and query keyspaces.

Performance Comparison

In general for counting keys, the performance profile looks like:

Method Relative Speed Use Case
DBSIZE Fastest Simple total count
INFO Fast When data breakdown needed without full scan
SCAN + Client Moderate Retrieving large keysets without blocking
KEYS Slow Avoid in production, can block/crash Redis

So in most cases DBSIZE should be enough to get total keys. For more complex cases, consider using SCAN, INFO or other approaches outlined earlier.

Conclusion

Counting keys is a vital part of managing Redis. We covered different ways to get total keys:

  • Use DBSIZE when you just need total keys
  • Retrieve entire keysets with KEYS * (avoid in production)
  • Incrementally count keys with SCAN in client code
  • Gain insights into memory utilization with INFO memory and INFO keyspace

Understanding the performance tradeoffs allows selecting the right approach. DBSIZE works great in most cases due to its speed and simplicity.

Analyzing your keyspaces and memory utilization over time helps identify areas to optimize and improve Redis efficiency. Both counts of total keys as well as drilling into breakdowns across data types provide valuable insights.

Hopefully this provides you a good overview of counting keys in Redis! Let me know if you have any other questions.

Written by John Doe, Full Stack Developer and Redis Expert

Similar Posts

Leave a Reply

Your email address will not be published. Required fields are marked *