介绍

redis是一个开源的基于内存的数据存储系统,用作数据库缓存和消息队列等场景,也是热门noSql数据库之一

传统数据库面对高并发场景,硬盘io是缓慢的,而内存相比就快很多所以有了这个

Redis的优势:

  1. 性能极高
  2. 数据类型丰富,单键值对最大支持512M大小的数据
  3. 简单易用,支持所有主流编程语言
  4. 支持数据持久化、主从复制、哨兵模式等高可用特性

下载通过https://github.com/redis-windows/redis-windows

然后点image-20250612185303511

安装image-20250612185320223

然后运行install_redis_service.bat,选择需要安装的目录,可以继承默认路径,redis-cli.exe是客户端,启动后输入info可以查看信息,uninstall_redis_service.bat是卸载程序

用命令提示符启动是redis-server.exe,停止方法是ctrl+c,启动客户端是redis-cli

然后用https://redis.io/downloads/#:~:text=Redis-,Insight,-Download%20a%20powerful下载redisinsight

一路next,打开后添加本地的地址和端口号,

使用

String

redis中的数据是以键值对的形式存储的,redis中的键是区分大小写的,默认使用字符串存储数据,是二进制安全的

1
2
3
set设置 get获取 del删除 exists判断键是否存在
keys *查找所有键 keys *me查找所有以me结尾的键
flushall删除所有键

redis默认不支持中文,如果把键的值设置成中文,会看到把中文换成了二进制形式,\x是16进制,如果要显示中文,可以先quit退出,登录的时候再加上–raw就可以了
image-20251006023421818

TTL是Time To Live的缩写

1
2
3
4
TTL name查看name的过期时间,返回-1表示没有设置过期时间
EXPIRE name 10设置十秒过期
SETEX设置一个带有过期时间的键值对,比如SETEX name 5 啊啊啊
SETNX只有当键不存在时才设置键的值,如果存在则不做动作。比如SETNX name

List

用LPUSH或者RPUSH命令来将元素添加到列表的头部或尾部,这里添加是类似栈的形式,往头部添加,用RPUSH就是从尾部添加了,应该是双向链表

1
2
3
4
5
6
7
8
LPUSH letter a在头部添加a元素,letter是列表名
LRANG letter 0 -1获取列表内容,0是起始位置,-1是最后一个元素
RPOP letter删除最后一个元素
LPOP letter 2删除前两个元素
LLEN letter查看列表的长度
用RPOPLPUSH可以实现最后一个元素删除,添加一个新元素,也就是先进先出
LTRIM letter删除列表中指定范围以外的元素,TRIM是修剪的意思,比如
LTRIM letter 1 3也就是只保留13之间的元素

Set

set是无序集合,list列表元素可以重复set不可以重复,指令大多以S开头,如果再次添加已有元素会显示失败

1
2
3
4
5
SADD course redis 添加一个元素叫redis。course是集合的名称
SMEMBERS course查看集合中的元素,输出的是redis
SADD course redis再次添加会返回0,也就是添加失败了,因为set是不可重复集合
SISMEMBER course redis判断redis是否在集合中,返回的是1,没有就是0
SREM course redis删除一个元素,返回1代表成功

有序集合SortedSet

有序集合的每个元素都会关联一个浮点类型的分数,按照这个分数来对集合中的元素进行从小到大的排序

有序集合的成员是唯一的,分数是可以重复的

有序集合的相关命令以Z开头,后面是集合的名字,然后是分数和成员名

XREADGROUP GROUP读取组消息 组名称 消费者名称 一次读两条消息 没有消息就堵塞3秒 消息名 右箭头是从这个消息中读取最新的消息

1
2
3
4
5
6
7
8
9
10
11
12
13

## 地理空间Geospatial

地理位置指令都以GEO开头

~~~shell
GEOADD city 116.405285 39.904989 beijing 添加地理信息 city是key表示地理位置信息名字 后面是经纬度和城市名,也可以同时添加多个
GEOADD city 116.405285 39.904989 beijing 405285 39.904989 shanghai
GEOPOS city beijing获取北京的经纬度,返回结果第一个是经度第二个是维度
GEODIST city beijing shanghai计算北京到上海的距离,返回的是直线距离,默认单位是米,如果想换成千米就在shanhai后面加上 空格 KM

搜索指定范围内的成员并返回,可以以成员的位置或一个指定的经纬度为中心,按照圆形或者矩形的范围来搜索
GEOSEARCH city FROMMEMBER shanghai BYRADIUS 300 KM 搜索上海300km以内的城市,BYRADIUS是一个圆形的范围,300km是半径,BYBOX是矩形

HyperLogLog

这是一种用来做基数统计的算法,如果集合中每个元素都是唯一且不重复的,那么这个集合的基数就是集合中元素的个数,比如1122334455,基数就是5,原理是用随机算法计算,优点占用内存小,缺点会有误差。命令都以PF开头

1
2
3
4
5
PFADD course git docker redis 添加一个叫课程的元素
PFCOUNT course 查看基数 返回3

新增一个课程,然后合并
PFMEAGE result course course2 把course course2合并到result里

位图Bitmap

位图是字符串的扩展,可以使用一个String来模拟一个bit数组,数组的下标就是偏移量,值只有0和1,也支持一些位运算,比如与或非,异或等,命令以SET开头

1
2
3
4
5
6
7
8
9
SETBIT dianzan 0 1     SETBIT设置某个偏移量的值,dianzan是键的名字,把偏移量0的位置上设置为1
SETBIT dianzan 0 1 再把偏移量为1的地方设置为0
GETBIT dianzan 0 获取偏移量的值

重新设置点赞的值,让它前四位都为1,后面四位都为0,我们可以使用16进制来表示一个二进制的数,这里的\xF0表示11110000,可以一次性设置8个
SET dianzan "\xF0"

BITCOUNT dianzan统计某一个key的值里面有多少个bit是1,这里返回的是4
BITPOS dianzan 0可以获取某个key里面第一个出现的0或者1的位置,返回的是4,后面还可以添加开始和结束这个范围

位域Bitfield

位域能将很多小的整数存储到一个较大的位图中,这样可以较高效的使用内存

1
2
3
4
5
这里设置一个游戏角色
BITFIELD player:1 set u8 #0 1 player:1这个key表示id,u8表示等级,意思是一个8位无符号整数,#0表示第一个位置,等级为1
GET player:1 返回\x01表示等级为1
BITFIELD player:1 get u8 #0 这里把set换成get就可以返回等级1了,而不是16进制
BITFIELD player:1 incrby u8 #0 10 增加了十级,返回11

Redis事务

主要是通过MULTI和EXEC这两个实现,一个是开启事务一个是执行

在关系型数据库中事务一般是一个原子操作,要么全部执行成功,要么全部执行失败

而在redis中事务并不能保证所有的命令都会执行成功,但是redis可以保证三点:

  1. 在发送exec命令之前,所有的命令都会被放入到一个队列中缓存起来,不会立即执行
  2. 在收到exec命令之后,事务开始执行,事务中任何一个命令执行失败,其他命令依然会被执行,就是说不会因为某一个命令执行失败而导致其他命令不会被执行的情况发生
  3. 在事务执行的过程中,其他客户端提交的命令请求并不会被插入到事务的执行命令序列中
1
2
3
4
MULTI 回车后返回ok,进入到事务模式(TX)
SET k1 v1 返回QUEUED表示放在队列中
SET k2 v2
EXEC执行

Redis持久化

如果没有持久化,之前所有的数据都会丢失

redis有两种方式

1:RDB(Redis Database),是指在指定时间间隔内将内存中的数据快照写入磁盘,它是某一个时间点上数据的完整副本,可以通过配置文件中的save参数来配置,指令是vi redis.conf

image-20251011013924855

后面的参数是时间和修改次数的组合,第一个参数是秒数,第二个是修改次数,

image-20251011014036278

第一行就表示3600秒也就是一个小时之内只要有一次修改就进行一次快照,第二行就表示300秒内有100次修改的话才进行一次快照,第三条表示60秒内有1万次修改的话才进行一次快照,也可以通过save命令手动触发快照。

image-20251011014532405

快照文件的缺点是如果服务器在快照之后宕机了,那么最后一次快照之后的所有修改内容都会丢失掉,所以 RDB更适合用来做备份,比如我们可以在每天凌晨的时候通过crontab来执行一次save命令,然后将快照文件备份到其他地方,这样就可以保证数据的安全了

还有一个问题就是由于生产环境中我们为Redis开辟的内存区域一般都比较大,那么内存中的数据同步到硬盘这个过程就会持续比较长的时间,这段时间内Redis都是处于一个阻塞的状态,不能接受任何请求,于是Redis又提供了一个叫做bgsave的命令,这个命令会单独创建一个子进程来负责将内存中的数据写入到硬盘中,这样的话主进程就可以继续处理请求了,但是这个过程中还会有一定的性能损耗,因为fork一个子进程也是需要时间的,这段时间内Redis还是不能处理任何请求,做不到秒级快照,为了解决问题Redis又提供了另一种叫做AOF的持久化方式

2:AOF(Append only File),指追加文件,它的原理是在执行写命令的时候,不仅会将命令写入到内存中,还会将命令写入到一个追加的文件中,这个追加的文件就是aof,它会以日志的形式来记录每一个写操作,当Redis重启的时候就会通过重新执行AOF文件中的命令来在内存中重建整个数据库的内容

开启方式:配置文件中image-20251011015257555 no改成yes

主从复制

是指将一台Redis服务器的数据复制到其他Redis服务器,也叫主节点和从节点

一个主节点可以有多个从节点,而每个从节点只能有一个主节点,数据的复制是单向的,只能由主节点到从节点,主节点负责写操作,从节点负责读操作。

主节点会将自己的数据变化通过异步的方式发送给从节点,从节点接收到主节点的数据之后更新自己的数据,这样就达到了数据一致的目的

配置:主节点不需要修改任何配置因为默认的配置就是主节点,只需要修改从节点的配置就可以了

  1. 通过命令行执行命令

    1
    slaveof直接指定主节点的IP和端口(旧版,不常用)
  2. 通过配置文件修改

    redis配置文件是redis.conf,一般在安装目录里

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    cd /opt/homebrew/etc
    ls -ltr
    找到redis.conf,用cp redis.conf ~复制到根目录一份
    cd回到根目录再复制一个6380文件
    cp redis.conf redis-6380.conf,把这个作为从节点配置文件,6380就是待会要使用的从节点端口号,用vscode打开这个配置文件
    找到port 6379改为6380
    找到pidfile /var/run/redis_6379.pid也改6380,pid也就是进程id,redis是以守护进程的方式运行,系统默认会把pid写入到这个文件里面,因为这里我们要启动多个Redis服务,所以要把两个Redis的pid文件区分开
    再找到一个dbfilename这个配置项
    dbfilename dump-6380.rdb这个就是之前我们说的持久化文件了,当我们执行save或者bgsave命令的时候,就会把内存中的数据保存到这个文件里面。为了区分开主节点和从节点的数据我们也要把这个文件名加上端口号
    最后再找到-个replicaof这个配置项,它是用来指定主节点的,默认是注释掉的,我们把它复制一行加到下面,IP地址改成127.0.0.1,端口号改成6379,表示我们现在配置的这个节点是6379这个库的从节点
    然后保存

    启动一个客户端,执行第一行,再启动一个执行第二行连接这个从节点

    1
    2
    3
    redis-server redis-6380.conf
    redis-cli -p 6380
    info replication查看信息,可以看到从节点角色是slave,port端口号是6379,这样就成功了

    如果主节点有密码,从节点要设置masterauth

    从节点也可以配置多个,把刚刚的6380复制出来变成6381

    1
    2
    3
    4
    cp redis-6380.conf redis-6381.conf
    vi redis-6381.conf使用vi编辑器将6380整体替换6381
    :1,$s/6380/6381/g回车会提示替换了四个位置
    :wq保存退出

哨兵模式Sentinel

如果主节点宕机就需要人工干预把从节点变成主节点,这样就不能实现真正的高可用

哨兵会以一个独立的进程运行在Redis集群中,用来监控Redis集群中的各个节点中是否运行正常。功能如下:

  1. 监控:通过不断地发送命令来检查Redis节点是否正常
  2. 通知:如果发现某个节点出了问题,那么哨兵就会通过发布订阅模式来通知其他节点
  3. 自动故障转移:当主节点不能正常工作的时候,哨兵会开始一个自动故障转移的操作,它会将一个从节点升级为新的主节点,然后再将其他从节点指向新的主节点

配置:首先需要在Redis集群中添加一个哨兵节点

1
2
3
4
5
6
7
启动哨兵节点,需要添加配置文件sentinel.conf
vi sentinel.conf使用vim新建一个sentinel.conf文件
然后在文件添加配置
sentinel monitor master 127.0.0.1 6379 1 master就是要监控的主节点的名称,可以自己定义,后面加上主节点的IP地址和端口号,最后一个参数1表示只需要一个哨兵节点同意就可以进行故障转移了
:wq
redis -sentinel启动哨兵节点

哨兵本身也是一个进程,它自己也会有单节点故障的问题,所以一般在实际的生产环境会使用三个哨兵节点来保证高可用,这三个哨兵节点会通过选举的方式来选出一个领导者,然后由领导者来监控其他节点,如果领导者挂了那么其他哨兵节点会重新选举出一个领导者,这样就可以保证哨兵的高可用了

Cluster

Cluster是Redis提供的分布式数据库解决方案
自动将你的数据切分给多个节点存储,然后让节点去认领
即使这些节点中一部分宕机,也可以继续执行数据操作