The method in Redis to count the various data sizes
- 2020-05-07 20:38:36
- OfStack
If the MySQL database is large, we can easily find out which tables are taking up space. But if Redis has a lot of memory, it's not easy to figure out which keys are taking up the space.
There are some tools that can provide the necessary help, such as redis-rdb-tools, which can directly analyze RDB files to generate reports. Unfortunately, it can't fulfill my requirements 100%, and I don't want to develop on top of it twice. In fact, the development of a dedicated tool is very simple, using SCAN and DEBUG commands, not many lines of code to achieve:
<?php
$patterns = array(
'foo:.+',
'bar:.+',
'.+',
);
$redis = new Redis();
$redis->setOption(Redis::OPT_SCAN, Redis::SCAN_RETRY);
$result = array_fill_keys($patterns, 0);
while ($keys = $redis->scan($it, $match = '*', $count = 1000)) {
foreach ($keys as $key) {
foreach ($patterns as $pattern) {
if (preg_match("/^{$pattern}$/", $key)) {
if ($v = $redis->debug($key)) {
$result[$pattern] += $v['serializedlength'];
}
break;
}
}
}
}
var_dump($result);
?>
Of course, if you need to summarize possible key patterns in advance, the simple but less rigorous approach is MONITOR:
shell> /path/to/redis-cli monitor |
awk -F '"' '$2 ~ "ADD|SET|STORE|PUSH" {print $4}'
Also, it is important to note that because DEBUG returns serializedlength as a serialized length, the final calculated value is less than the actual footprint, but it is still useful to consider the relative size.