redis进阶使用

分布式锁

redis实现是非公平锁,ectd、zk用来实现公平锁

获取不到锁的客户端阻塞等待,阻塞连接返回

set lock uuid nx ex 30 #不存在才能设置,定义加锁行为,占用锁,30s超时。或者用setnx

if (get(lock) == uuid)    #释放锁 

        del(lock)

非公平锁:自旋锁,独占cpu不断尝试获取锁

公平锁:互斥锁,按照请求顺序得到锁

阻塞连接

使用list数据结构,队首入队LPUSH,用队尾弹出命令RPOP,这个命令会在list为空时阻塞连接

BRPOP key timeout # 超时时间 + 延时队列

在超时时间内如果有数据则弹出,timeout为0则永远阻塞

可以用于实现redis的一个公平锁

固定窗口限流

list链表中push的数据固定大小,防止链表过长

LPUSH入队,RPOP出队,如何只保存最近n条数据

ltrim listkey 0 49          #裁剪最近50条记录

lrange listkey 0 49        #获取最近50条记录

可应用于保存n条最新实时数据,比如战绩、排行

有序集合

使用zset数据结构,用于实现排行榜,热度,范围查找,元素有序且唯一

#添加到键为key的有序集合(sorted set)里面

ZADD key [NX|XX] [CH] [INCR] score member [score member ...]

#返回存储在有序集合key中的指定范围的元素

ZRANGE key start stop [WITHSCORES]

#返回有序集合key中,指定区间的成员(逆序)

ZREVRANGE key start stop [WITHSCORES]

内部使用的是跳表的数据结构

延时队列

将消息序列化成一个字符串作为 zset 的 member;这个消息的到期处理时间作为 score,然后用 多个线程轮询 zset 获取到期的任务进行处理。

分布式定时器

redis进阶使用_第1张图片

 生产者将定时任务 hash 到不同的 redis 实体中,为每一个 redis 实体分配一个 dispatcher 进程, 用来定时获取 redis 中超时事件并发布到不同的消费者中;

时间窗口限流

系统限定用户的某个行为在指定的时间范围内(动态)只能发生N次;

事务

redis的事务有两种模式,MUTLI命令和lua脚本。

MULTI:开启事务

EXEC:提交事务

DISCARD:取消事务

WATCH:检测某个key的变动,若在事务执行中,key被其他客户端变动则取消事务;在事务开启前调用,乐观锁实现(cas);若被取消则事务返回nil

lua脚本实现原子性;redis中加载了一个lua虚拟机,用来执行redis lua脚本;redis lua脚本的执行是原子性的;当某个脚本正在执行时,不会有其他命令或其他脚本被执行;

# 从文件中读取 lua脚本内容
cat test1.lua | redis-cli script load --pipe
# 加载 lua脚本字符串 生成 sha1
> script load 'local val = KEYS[1]; return val'
"b8059ba43af6ffe8bed3db65bac35d452f8115d8"
# 检查脚本缓存中,是否有该 sha1 散列值的lua脚本
> script exists "b8059ba43af6ffe8bed3db65bac35d452f8115d8"
1) (integer) 1
# 清除所有脚本缓存
> script flush
OK
# 如果当前脚本运行时间过长,可以通过 script kill 杀死当前运行的脚本
> script kill
(error) NOTBUSY No scripts in execution right now.

# 测试使用
EVAL script numkeys key [key ...] arg [arg ...]

# 线上使用
EVALSHA sha1 numkeys key [key ...] arg [arg ...]

# 1: 项目启动时,建立redis连接并验证后,先加载所有项目中使用的lua脚本(script load);
# 2: 项目中若需要热更新,通过redis-cli script flush;然后可以通过订阅发布功能通知所有服
务器重新加载lua脚本;
# 3:若项目中lua脚本发生阻塞,可通过script kill暂停当前阻塞脚本的执行;

发布订阅

为了支持消息的多播机制,redis 引入了发布订阅模块;消息不一定可达;分布式消息队列;stream的方式确保一定可达

# 订阅频道 subscribe 频道

# 订阅模式频道 psubscribe 频道

# 取消订阅频道 unsubscribe 频道

# 取消订阅模式频道 punsubscribe 频道

# 发布具体频道或模式频道的内容 publish 频道 内容

# 客户端收到具体频道内容 message 具体频道 内容

# 客户端收到模式频道内容 pmessage 模式频道 具体频道 内容

你可能感兴趣的:(redis)