《Redis开发与运维》- API的使用-3-键管理

Posted zczpeng

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了《Redis开发与运维》- API的使用-3-键管理相关的知识,希望对你有一定的参考价值。

《Redis开发与运维》- API的使用-3-键管理

键管理

单个键的命令,如type,del,object,exists,expire等

1:键重命名

rename key newkey
【renamenx命令,确保只有在key不存在时才被覆盖,返回0代表没有重命名完成】
【使用重命名时需要注意:由于重命名键期间会执行del命令删除旧的键,如果键对应的值比较大,会存在堵塞可能性】

2:随机返回一个键

random key

3:键过期

expire key seconds 【在seconds秒后过期】
expireat key timestamp 【在秒级时间戳后过期】
【ttl 命令和 pttl命令都可以查询键的剩余过期时间,但是 pttl精度更高,可以返回毫秒数,返回值如果大于等于零的整数,则是键剩余的过期时间,如果是-1 则键没有设置过期时间,-2则键不存在】

pexpire key millisecords 【键在millisecords毫秒后过期】
【无论是使用秒级和毫秒级,内部都是使用的pexpireat】

使用Redis相关过期命令时,需要注意以下几点:
1:expire key 的键不存在,返回结果为0
2:如果过期时间为负值,键会被立刻删除,和del一样。
3:persist命令可以将键的过期时间清除。
4:对于字符串类型键,执行set命令会去掉过期时间。
5:redis不支持二级数据结构的元素设置过期功能,例如不能对列表内的某个元素设置过期。
6:setex命令作为 set+expire的组合,是原子执行。

4:迁移键

1:move命令

在Redis内部数据库之间迁移数据,不建议使用。

2:dump+restore

可以实现在不同redis实例之间进行数据迁移的功能。
dump key
restore key ttl value

在源Redis上,dump命令会将减值序列化,格式采用的是RDB格式。
在目标Redis上,restore命令会将序列化啊的值进行复原,其中ttl参数代表过期时间,如果ttl = 0代表没有过期时间。
如图:

有关dump+restore有两点要注意:
1:整个迁移过程并非原子性的,而是通过客户端分步完成。
2:迁移过程是开启了两个客户端连接,所以dump的结果不是在源Redis和目标Redis之间传输。

3:migrate

migrate targethost targetport key|"" destination-db timeout [copy] [replace] [keys key [key …]]

migrate 命令时用于redis实例间进行数据迁移的,实际上migrate命令就是讲dump+restore,del三个命令进行组合,从而简化了操作流程,且命令具有原子性,有效提高了迁移效率。

4:遍历键

redis提供了两种遍历键的方式:keys 和 scan
1:全量遍历键
keys pattern
pattern: 使用
*,代表匹配任意字符
?,代表匹配一个字符
[],代表匹配部分字符,例如[1,3]代表匹配1,3,[1-10]代表匹配1到10的任意数字。
\\x 用来做转义,例如需要匹配星号、问号需要进行转义。

当需要遍历并删除某种格式的键时,可以使用命令:
redis-cli keys video
| xargs redis-cli del
*

keys命令很可能会造成堵塞,一般不建议在生产环境使用。
如果非要执行,要在一个不对外提供服务的redis从节点上执行,这样不会堵塞客户端的请求,但是会影响到主从复制。
如果键总数确实比较小,可以执行该命令。

2:渐进式遍历
scan cursor [match pattern] [count number]
scan命令,与keys命令执行时会遍历所有键不用,scan采用渐进式来解决keys可能带来的堵塞问题。,每次scan命令的时间复杂度是O(1),但是要实现keys的命令,需要执行多次scan。
Redis存储键值对实际使用的是hashtable的数据结构,简化模型如图:

注意:渐进式遍历可以有效解决keys命令可能带来的堵塞问题,但是scan过程中如果有键的变化,如增删改,那么可能会出现新增的key没有被遍历到,遍历出了重复键的情况,这也是要注意的。

数据库管理

几个面向数据库的操作:dbsize ,select ,flushdb/flushall命令
1:切换数据库(0~15)
select dbIndex
select 0 将切换到第一个数据库。

Redis 已经逐渐弱化这个功能了,Redis Clushter 只允许使用0号数据库:原因:
1:Redis是单线程的。如果使用多个数据库,则这些数据库还是使用一个CPU,彼此之间还会受影响。
2:多数据库的使用方式,会让调试和运维更加困难。如果一个慢查询存在,依然会影响其他数据库。
3:客户端不支持,开发时来回切容易出问题。

2:flushdb/flushall
命令用于清除数据库,两者区别是flushdb只清除当前数据库,flushall会清除所有数据库。数据较多时也会堵塞。
【一旦误操作后果严重,一定要谨慎】

API的使用重点回顾:

1:提供5中数据结构,每种数据结构都有多种内部编码实现。
2:纯内存存储,IO多路复用技术,单线程架构。造就redis高性能。
3:每个命令能快速执行完,才是不堵塞redis的关键。
4:批量操作(mget,mset,hmset等)能够有效提高命令执行效率。但是要注意每次操作的个数和字节数。
5:了解每个命令的时间复杂度,如使用 keys,hgetall,smember,zrange等时间复杂度较高的命令时,需要考虑数据规模对redis的影响。
6:persist命令可以删除任意类型的键过期时间。但是set命令也会删除字符串类型键的过期时间。
7:move,dump+restore,migrate是redis发展过程中的三个迁移键的方式,move已废弃,migrate命令用原子性的方式实现了dump+restore,并且支持批量操作,是Redis Cluster 实现水平扩容的重要工具。
8:scan 命令可以解决keys命令带来的堵塞问题,同时redis还提供了hscan,sscan,zscan渐进式的遍历 hash,set,zset.

以上是关于《Redis开发与运维》- API的使用-3-键管理的主要内容,如果未能解决你的问题,请参考以下文章

《Redis开发与运维》- API的使用-2-五种常用数据结构

《Redis开发与运维》- API的使用-2-五种常用数据结构

《Redis开发与运维》- API的使用-1-全局命令

《Redis开发与运维》- API的使用-1-全局命令

Redis 开发与运维客户端

Redis 开发与运维Redis 的噩梦:阻塞