当前位置:首页 > 问答 > 正文

Redis里怎么快速查当前有多少Key,简单又实用的方法分享

说到在Redis里快速查有多少个Key,这确实是一个很常见但又不能太随便的操作,你可能第一个想到的就是用KEYS *这个命令,因为它最直接,输入之后好像就能看到所有key,然后自己数一下个数就行,但这里要非常明确地告诉你:*在生产环境中,绝对不要使用`KEYS `命令来统计key的数量。**

这是为什么呢?原因来自Redis一个关键的设计特点:Redis是单线程的,你可以把Redis想象成一个只有一个收银员的超级市场,这个收银员效率非常高,能同时处理很多人的结账请求,但前提是任务都是短平快的。KEYS *这个命令,就像是让这个收银员放下手头所有工作,去盘点整个超市里所有货架上每一种商品的具体数量和位置,在这个过程中,收银台就完全停摆了,后面所有排队等待结账的顾客(也就是新的读写命令)全部会被阻塞住,直到盘点工作全部完成,如果你的Redis里存了几百万甚至上千万个key,这个盘点过程可能会长达几秒甚至几十秒,这对于一个在线服务来说简直是灾难性的,很可能导致服务超时、应用崩溃。

既简单实用又安全的方法是什么呢?答案是使用DBSIZE命令。

使用 DBSIZE 命令(首选推荐)

这个方法是最简单、最快速的,你只需要在Redis的命令行界面(CLI)里输入:

DBSIZE

然后Redis会立刻返回一个数字,这个数字就是当前数据库中key的总数。

为什么DBSIZE这么快而且不阻塞呢?根据Redis官方文档的说明,这是因为Redis在内部维护了一个计数器,每当增加或删除一个key时,这个计数器都会相应地更新,当你执行DBSIZE时,Redis根本不需要去遍历所有的key,它只需要看一眼这个计数器的当前值,然后马上告诉你结果,这个过程是常数时间复杂度O(1)的,速度极快,对Redis服务器的性能没有任何影响。

如果你只是想快速知道整个数据库里总共有多少个key,DBSIZE是你的不二之选。

有时候我们的需求会更复杂一点,我们可能只想知道以某个前缀开头的key有多少个,比如所有以user:session:开头的会话key,这时候DBSIZE就无能为力了,因为它只提供总数。

使用 SCAN 命令(用于模式匹配统计)

对于需要统计符合特定模式的key数量的情况,我们就需要用到SCAN命令。SCAN命令是KEYS命令的安全替代品,它的设计初衷就是为了解决KEYS命令的阻塞问题。

SCAN命令的工作原理是增量式迭代,它不会一次性遍历整个key空间,而是每次只遍历一小部分,然后返回一个游标(cursor)和一部分匹配的key,你可以拿着这个游标,再次调用SCAN,继续上一次的遍历,直到游标返回0,表示遍历完成。

这个过程还是用超市收银员的比喻:SCAN命令不是让收银员一次性盘点完所有商品,而是让他每次趁着一两个顾客结账的间隙,快速跑进去统计几个货架的商品,统计完几个就马上回到收银台继续工作,等下个间隙再进去统计几个,这样虽然总的盘点时间可能变长了,但收银台的服务基本上没有被中断,顾客无需长时间等待。

怎么用SCAN来统计以user:session:开头的key数量呢?你可以按照以下步骤操作:

  1. 你需要一个Redis客户端,比如命令行工具redis-cli
  2. 由于我们需要进行模式匹配,所以使用SCAN命令的变体:SCAN cursor [MATCH pattern]
  3. 我们从一个游标0开始,匹配模式是user:session:*

实际操作起来像这样:

第一次扫描:

SCAN 0 MATCH user:session:*

这个命令会返回两部分内容:

  • 下一个迭代的游标,17
  • 本次迭代扫描到的key列表,可能是一个空列表,也可能包含一些key。

第二次扫描,使用返回的新游标:

SCAN 17 MATCH user:session:*

继续这个过程,直到返回的游标是0,表示迭代结束。

显然,在命令行里手动一次次执行并自己累加数量是很麻烦的,一个更实用的方法是利用redis-cli工具本身的特性来一键完成,你可以使用下面这个命令:

redis-cli --scan --pattern "user:session:*" | wc -l

让我解释一下这个命令的各个部分(根据Redis官方文档中关于redis-cli工具的说明):

  • redis-cli:调用Redis命令行客户端。
  • --scan:告诉客户端使用SCAN命令而不是危险的KEYS命令。
  • --pattern "user:session:*":设置要匹配的模式。
  • :这是一个Linux/Unix系统的管道符,将前一个命令的输出作为后一个命令的输入。
  • wc -l:一个系统命令,用于计算输入的行数(line count),因为--scan模式输出的每个key占一行,所以行数就是key的数量。

执行这个组合命令后,终端会直接输出一个数字,就是所有匹配user:session:*的key的数量,这个方法既利用了SCAN的非阻塞特性,又通过管道命令自动化了计数过程,非常实用。

  • 只想看总key数:直接用SCAN命令,简单直接,这个管道符后面的wc命令来处理。
  • wc -lwc是单词计数命令,-l参数表示统计行数,因为--scan模式输出的每个key占一行,所以统计行数就等于统计key的数量。

这样,执行这一条命令,你就可以安全、快速地得到所有以user:session:开头的key的数量了。

  • 要总数,用 DBSIZE:快如闪电,毫无压力。
  • 按模式找数量,用 redis-cli --scan --pattern 配合 wc -l:安全可靠,不影响服务。

在Redis的世界里,避开KEYS命令,是你从入门到进阶的关键一步,希望这个分享对你有帮助。

Redis里怎么快速查当前有多少Key,简单又实用的方法分享