目标
总结积累redis常用的使用场景,不断完善
举例
- 分布式锁
加锁:
//避免多次操作redis造成事务不一致问题
String result = jedis.set(lockKey, requestId, SET_IF_NOT_EXIST, SET_WITH_EXPIRE_TIME, expireTime);
if (LOCK_SUCCESS.equals(result)) {
return true;
}
return false;
解锁:
//避免多次操作redis造成事务不一致问题
String script = "if redis.call('get', KEYS[1]) == ARGV[1] then return redis.call('del', KEYS[1]) else return 0 end";
Object result = jedis.eval(script, Collections.singletonList(lockKey), Collections.singletonList(requestId));
if (RELEASE_SUCCESS.equals(result)) {
return true;
}
return false;
- 并发流量控制
采用公平信号量实现,借用redis中的zset数据结构,并为了解决分布式环境中可能存在的时间不一致情况,引入计数器作为sort,实现zset形式的公平信号量,如下图.
在使用时
- 新增 : 计数器获取排序,插入zset中value,判断value位置,是否超过预定并发阈值
- 删除操作,包含两种
1. 对于业务处理完,自己清楚自己的信号量
2. 由于异常情况导致超时,系统检测超时时间删除过期信号信号量
![](https://img.haomeiwen.com/i5397939/bacb1898071ad08e.jpg)
- 秒杀系统
系统常见要求:
-
限流: 鉴于只有少部分用户能够秒杀成功,所以要限制大部分流量,只允许少部分流量进入服务后端。
-
削峰:对于秒杀系统瞬时会有大量用户涌入,所以在抢购一开始会有很高的瞬间峰值。高峰值流量是压垮系统很重要的原因,所以如何把瞬间的高流量变成一段时间平稳的流量也是设计秒杀系统很重要的思路。实现削峰的常用的方法有利用缓存和消息中间件等技术。
-
异步处理:秒杀系统是一个高并发系统,采用异步处理模式可以极大地提高系统并发量,其实异步处理就是削峰的一种实现方式。
-
内存缓存:秒杀系统最大的瓶颈一般都是数据库读写,由于数据库读写属于磁盘IO,性能很低,如果能够把部分数据或业务逻辑转移到内存缓存,效率会有极大地提升。
-
可拓展:当然如果我们想支持更多用户,更大的并发,最好就将系统设计成弹性可拓展的,如果流量来了,拓展机器就好了。像淘宝、京东等双十一活动时会增加大量机器应对交易高峰。
而redis在秒杀系统是常见的缓存手段,减少数据库交互,订单异步入库,限流削峰设计等可以通过redis实现.
- 缓存
利用redis等高吞吐量,适合的缓存系统
- 任务队列
让生产者使用lpush 命令加入到某个键中,另一个消费者不断使用rpop从该键中取出任务,实现任务队列的生产者和消费者模式.
6.计数器
常见场景,基于redis的insr线程安全的自增性.
网友评论