缓存穿透、缓存击穿、缓存雪崩
缓存穿透
指缓存和数据库中都没有的数据,而用户不断发起请求,导致数据库压力过大
解決方案:對查詢數據进行过滤,取不到数据也放个空字符在缓存中,加个失效时间,环境数据库压力
缓存击穿
数据库里面有数据,但是缓存中没有,(第一次加载的时候,瞬间大量用户请求,或者某个时间点,缓存失效,大量用户瞬间并发请求到数据库)
解决方案
- 设置热点数据永远不过期。
- 加互斥锁,互斥锁参考代码如下:
互斥锁代码
并发取数据,先加锁,能取到锁则继续操作,否则休眠一段时间重试
public String get(key) {
String value = redis.get(key);
if (value == null) { //代表缓存值过期
//设置3min的超时,防止del操作失败的时候,下次缓存过期一直不能load db
if (redis.setnx(key_mutex, 1, 3 * 60) == 1) { //代表设置成功
value = db.get(key);
redis.set(key, value, expire_secs);
redis.del(key_mutex);
} else { //这个时候代表同时候的其他线程已经load db并回设到缓存了,这时候重试获取缓存值即可
sleep(50);
get(key); //重试
}
} else {
return value;
}
}
缓存雪崩
大量缓存在同一时间,比如0点,失效,大量请求加载数据,造成数据库压力过大
解决方案
- 缓存数据的过期时间设置随机,防止同一时间大量数据过期现象发生。
- 如果缓存数据库是分布式部署,将热点数据均匀分布在不同搞得缓存数据库中。
- 设置热点数据永远不过期。
缓存预热
能解决缓存的击穿和雪崩
浙公网安备 33010602011771号