基础概念

Redis 全称 Remote Dictionary Server。Redis集群没有使用一致性hash,而是引入了哈希槽的概念,Redis集群有16384个哈希槽,每个key通过CRC16校验后对16384取模来决定放置哪个槽,集群的每个节点负责一部分hash槽。所以Redis集群最多有16384个节点。

数据类型

String

最常规的 set/get 操作,Value 可以是 String 也可以是数字。一般做一些复杂的计数功能的缓存,最大存储 512M

Hash

这里 Value 存放的是结构化的对象,比较方便的就是操作其中的某个字段。

我在做单点登录的时候,就是用这种数据结构存储用户信息,以 CookieId 作为 Key,设置 30 分钟为缓存过期时间,能很好的模拟出类似 Session 的效果。

List

使用 List 的数据结构,可以做简单的消息队列的功能。另外还有一个就是,可以利用 lrange 命令,做基于 Redis 的分页功能,性能极佳,用户体验好。

Set

因为 Set 堆放的是一堆不重复值的集合。所以可以做全局去重的功能。为什么不用 JVM 自带的 Set 进行去重?

因为我们的系统一般都是集群部署,使用 JVM 自带的 Set,比较麻烦,难道为了一个做一个全局去重,再起一个公共服务,太麻烦了。

另外,就是利用交集、并集、差集等操作,可以计算共同喜好,全部的喜好,自己独有的喜好等功能。

Sorted Set

Sorted Set多了一个权重参数 Score,集合中的元素能够按 Score 进行排列。

可以做排行榜应用,取 TOP N 操作。Sorted Set 可以用来做延时任务。最后一个应用就是可以做范围查找。

这里 Value 存放的是结构化的对象,比较方便的就是操作其中的某个字段。

过期策略

Redis 采用的是定期删除+惰性删除策略

定期删除Redis 默认每个 100ms 检查,是否有过期的 Key,有过期 Key 则删除。每次检查是随机抽取检查,不是全部检查。

惰性删除是获取某个 Key 的时候,Redis 会检查一下,这个 Key 如果设置了过期时间且已经过期,则会删除。

内存淘汰机制

定期删除+惰性删除策略下,仍旧可能会有很多Key没有删除,内存占用会越来越高。

# redis 配置文件
maxmemory-policy [淘汰策略]

内存淘汰策略(逐出算法)

maxmemory <memory usage limit(byte)>
maxmemory-policy <逐出算法> # The default is noeviction
maxmemory-samples <每次选取待删除数据的参数>
  • noeviction:当内存不足以容纳新写入数据时,新写入操作会报错(OOM(Out Of Memory)。
  • allkeys - 检测所有数据

    • allkeys-lru:当内存不足以容纳新写入数据时,挑选最近没有使用的数据淘汰(推荐使用)
    • allkeys-lfu: 当内存不足时,移除最近最少使用的 Key。
    • allkeys-random:当内存不足以容纳新写入数据时,在键空间中,随机移除某个 Key。
  • volatile - 检测设置了过期时间的键

    • volatile-lru:当内存不足以容纳新写入数据时,移除最近最少使用的 Key。
    • volatile-lfu:当内存不足以容纳新写入数据时,挑选最近使用次数最少的数据淘汰。
    • volatile-random:当内存不足以容纳新写入数据时,移除。
    • volatile-ttl:当内存不足以容纳新写入数据时,删除将要过期的数据。

关于 lrulfu

lfu - least frequently used - 使用频率最少的键

lru - least recently used - 最久没有使用的键

如果没有设置 expireKey不满足先决条件(prerequisites) 那么 volatile-lruvolatile-randomvolatile-ttl 策略的行为,和 noeviction基本上一致


持久化

命令

SAVE - 执行一个同步保存操作,将当前实例的所有数据快照(snapshot)以 RDB 文件的形式保存到硬盘

BGSAVE - 在后台异步(Asynchronously)保存当前数据库的数据到磁盘

BGREWRITEAOF - 重新创建一个当前 AOF 文件的体积优化版本(2.4后自动触发)

LASTSAVE - 返回最近一次 Redis 成功将数据保存到磁盘上的时间

RDB的性能高,但是数据不是高可用的,且大量数据时做存储处理会很慢,AOF的启动速度比较慢但是数据高可用,且写入过程中宕机不会破坏已有数据。

RDB

RDB持久化是指在指定的时间间隔内将内存中的数据集快照写入磁盘,实际操作过程是fork一个子进程,先将数据集写入临时文件,写入成功后,再替换之前的文件,用二进制压缩存储。

save M N # M秒内数据集存在N次修改时,自动触发bgsave进行数据保存
     ""  # 停用自动保存


stop-writes-on-bgsave-error yes
# 当启用了RDB且最后一次后台保存数据失败,Redis是否停止接收数据

rdbcompression yes
# 如果是的话,redis会采用LZF算法对存储到磁盘中的快照进行压缩

dbfilename <文件名.rdb>
# 快照的文件名

dir <PATH>
# 快照文件的存储路径

AOF

AOF持久化以文本日志的形式记录服务器所处理的每一个写、删除操作,不记录查询操作。

appendfsync always      #每次有数据修改发生时都会写入AOF文件。
            everysec    #每秒钟同步一次(缺省策略)。
            no          #从不同步。高效但是数据不会被持久化。
        

集群

主从复制

SLAVEOF - 在 Redis 运行时动态地修改复制(replication)功能的行为

ROLE - 返回实例在复制中担任的角色

slaveof <主服务器IP> 6379 
# 设置主服务器

slave-read-only yes 
# set 操作的数据不会被放在从节点的槽上,会被放到某主节点的槽上

masterauth <密码>
# 设置主从的密码

哨兵模式

当使用sentinel模式的时候,客户端就不要直接连接Redis,而是连接sentinel的ip和port,由sentinel来提供具体的可提供服务的Redis实现,这样当master节点挂掉以后,sentinel就会感知并将新的master节点提供给使用者。

Cluster模式


脚本

EVAL

EVALSHA

SCRIPT_LOAD

SCRIPT_EXISTS

SCRIPT_FLUSH

SCRIPT_KILL


发布与订阅

PUBLISH - 发布消息

SUBSCRIBE - 订阅消息

PSUBSCRIBE - 订阅一个或多个符合给定模式的频道

UNSUBSCRIBE - 指示客户端退订给定的频道

PUNSUBSCRIBE - 指示客户端退订所有给定模式

PUBSUB - 是一个查看订阅与发布系统状态的内省命令, 它由数个不同格式的子命令组成


事务

如果Redis服务器宕机或以某种方式停止运行,那么Redis可能只执行了事务中的一部分操作。Redis将会在重新启动时检查上述状态,然后退出运行并输出报错信息。使用 redis-check-aof 工具可以修复上述的只增文件,这个工具将会从上述文件中删除执行不完全的事务,这样Redis服务器才能再次启动。

MULTI - 标记一个事务块的开始

EXEC - 执行所有事务块内的命令

DISCARD - 取消事务,放弃执行事务块内的所有命令

WATCH - 监视一个(或多个) key ,如果在事务执行之前这个(或这些) key 被其他命令所改动,那么事务将被打断。

UNWATCH - 取消 WATCH命令对所有 key 的监视。