首页
学习
活动
专区
工具
TVP
发布
精选内容/技术社群/优惠产品,尽在小程序
立即前往

缓存雪崩、缓存穿透、缓存预热、缓存更新缓存降级等问题

,今天给大家整理一篇关于Redis经常被问到的问题缓存雪崩、缓存穿透、缓存预热、缓存更新缓存降级等概念的入门及简单解决方案。...(2)还有一个解决办法解决方案是:给每一个缓存数据增加相应的缓存标记,记录缓存的是否失效,如果缓存标记失效,则更新数据缓存,实例伪代码如下: ?...这样,当缓存标记key过期后,实际缓存还能把旧数据返回给调用端,直到另外的线程在后台更新完成后,才会返回新缓存。...关于缓存崩溃的解决方法,这里提出了三种方案:使用锁或队列、设置过期标志更新缓存、为key设置不同的缓存失效时间,还有一各被称为“二级缓存”的解决方法,有兴趣的读者可以自行研究。...这样请求就绕过缓存直接查数据库,这也是经常提的缓存命中率问题

3.8K10

Redis缓存雪崩、缓存穿透、缓存预热、缓存更新缓存降级等问题

这样就导致用户查询的时候,在 缓存中找不到,每次都要去数据库再查询一遍,然后返回空(相当于进行了两次无用的查询)。这样请求就绕过缓存直接查数据库,这也是经常提的缓存命中率问题。...这样就可以避免在用户请求的时候,先查询数据库,然后再将数据缓存问题!...用户直接查询事先被预热的缓存数据 解决办法 (1)直接写个缓存刷新页面,上线时手工操作下; (2)数据量不大,可以在项目启动的时候自动进行加载; (3)定时刷新缓存; 四、缓存更新 除了缓存服务器自带的缓存失效策略之外...,过期的话就去底层系统得到新数 据并更新缓存。...因此,对于不重要的缓存数据,可以采取服务降级策略,例如一个比较常见的做法就是,Redis出现问题,不去数据库查询,而是直接返回默认值给用户。

2.2K20
  • 您找到你想要的搜索结果了吗?
    是的
    没有找到

    谈谈缓存更新

    试想,两个并发操作,一个是更新操作,另一个是查询操作,更新操作删除缓存后,查询操作没有命中缓存,先把老数据读出来后放到缓存中,然后更新操作更新了数据库。...更新:先把数据存到数据库中,成功后,再让缓存失效。 注意,我们的更新是先更新数据库,成功后,让缓存失效。那么,这种方式是否可以没有文章前面提到过的那个问题呢?我们可以脑补一下。...而不会像文章开头的那个逻辑产生的问题,后续的查询操作一直都在取老的数据。...那么,是不是Cache Aside这个就不会有并发问题了?...4、上面,我们没有考虑缓存(Cache)和持久层(Repository)的整体事务的问题。比如,更新Cache成功,更新数据库失败了怎么吗?或是反过来。

    1.1K20

    漫谈缓存更新之道

    许多人在更新缓存时,先删除缓存,然后再更新数据库,而后续的操作会把数据再装载入缓存中。 然而,这个逻辑是错误的!!!...试想,两个并发操作,一个更新,一个查询,更新删除缓存后,查询没有命中缓存,先把旧数据读出来后放到缓存中,然后更新操作更新了数据库。于是,在缓存中的数据还是旧数据,导致缓存中持续地产生脏数据....而不会像文章开头的那个逻辑产生的问题,后续的查询操作一直都在取老的数据。...那么,是不是Cache Aside这个就不会有并发问题了?...但是,其带来的问题是,数据不是强一致性的,而且可能会丢失(我们知道Unix/Linux非正常关机会导致数据丢失,就是因为这个事)。

    3.2K31

    缓存更新的套路

    试想,两个并发操作,一个是更新操作,另一个是查询操作,更新操作删除缓存后,查询操作没有命中缓存,先把老数据读出来后放到缓存中,然后更新操作更新了数据库。...更新:先把数据存到数据库中,成功后,再让缓存失效。 ? ? 注意,我们的更新是先更新数据库,成功后,让缓存失效。那么,这种方式是否可以没有文章前面提到过的那个问题呢?我们可以脑补一下。...而不会像文章开头的那个逻辑产生的问题,后续的查询操作一直都在取老的数据。...那么,是不是Cache Aside这个就不会有并发问题了?...4)上面,我们没有考虑缓存(Cache)和持久层(Repository)的整体事务的问题。比如,更新Cache成功,更新数据库失败了怎么吗?或是反过来。

    1.3K130

    缓存更新的套路

    试想,两个并发操作,一个是更新操作,另一个是查询操作,更新操作删除缓存后,查询操作没有命中缓存,先把老数据读出来后放到缓存中,然后更新操作更新了数据库。...更新:先把数据存到数据库中,成功后,再让缓存失效。 ? 注意,我们的更新是先更新数据库,成功后,让缓存失效。那么,这种方式是否可以没有文章前面提到过的那个问题呢?我们可以脑补一下。...而不会像文章开头的那个逻辑产生的问题,后续的查询操作一直都在取老的数据。...那么,是不是Cache Aside这个就不会有并发问题了?...4)上面,我们没有考虑缓存(Cache)和持久层(Repository)的整体事务的问题。比如,更新Cache成功,更新数据库失败了怎么吗?或是反过来。

    2.2K70

    缓存更新的套路

    试想,两个并发操作,一个是更新操作,另一个是查询操作,更新操作删除缓存后,查询操作没有命中缓存,先把老数据读出来后放到缓存中,然后更新操作更新了数据库。...更新:先把数据存到数据库中,成功后,再让缓存失效。 ? 注意,我们的更新是先更新数据库,成功后,让缓存失效。那么,这种方式是否可以避免文章前面提到过的那个问题呢?...这样一来就能避免用文章开头的那个逻辑产生的问题,也就是后续的查询操作一直都在取老的数据。...那么,是不是 Cache Aside 这个就不会有并发问题了?...4)上面,我们没有考虑缓存(Cache)和持久层(Repository)的整体事务的问题。比如,更新 Cache 成功,更新数据库失败了怎么吗?或是反过来。

    1.3K20

    缓存更新策略

    问题:项目中,Redis用了缓存热点数据,持久化数据在MySQL DB中;那么Redis缓存数据什么时候更新呢? 方法A: 步骤:1....删除缓存,2.更新DB , 3.下一次读操作没有命中缓存时,更新缓存; 存在的问题:如果另外一个读任务发生在"更新DB"之前,那么缓存就"更新DB"之前的“脏数据”; 方法B:...步骤:1.更新DB,2.更新缓存; 存在的问题:如果发生并发“更新数据”,程序不能保证“更新缓存”的先后顺序,存在“脏数据”的可能性; 方法C:...下一次读操作没有命中缓存时,更新缓存; 存在的问题:如果在步骤1“更新DB”之前,有一个并发读任务没有命中缓存,从DB读取到“老数据”,在步骤2之后才把“老数据”更新缓存,那么缓存中就是...“脏数据”; 思考:方法C采取的策略,在实际场景中发送的概率比前两种方法小很多;但是怎么完全杜绝这种问题呢?

    1.5K00

    数据库事务环境下表级缓存更新问题

    例如现在有一个金币兑换物品的场景,用户兑换的流程如下: 用户信息表:扣除用户金币 用户的兑换表:新增一行记录,状态为:“已扣金币;未创建订单” 用户金币流水表:新增用户扣除金币记录 进行实际下单兑换的接口调用 更新用户兑换表状态为...这种场景下,什么时候删除旧的缓存就显得很重要,更新缓存的时机不当,会留下缓存数据与数据库数据不一致的隐患。...更新用户兑换表状态为:已扣除金币 在并发的情况下,可能会出现: 下单兑换的线程删除了用户信息表缓存 另一个请求的线程重新读取用户信息表数据并更新缓存 此时下单兑换的线程下单失败进行了金币回滚 此时缓存中的用户金币与数据库表中的用户金币是不一致的...将缓存删除的位置处于以下位置时: 用户信息表:扣除用户金币 用户的兑换表:新增一行记录,状态为:“已扣金币;未创建订单” 用户金币流水表:新增用户扣除金币记录 进行实际下单兑换的接口调用 更新用户兑换表状态为...在使用表级缓存 + 数据库事务 的环境下 需要注意这个问题。 同理的,在更新表级缓存的时候,在数据库的数据成功更新后,再删除缓存,才是稳妥的操作。

    1K20

    为什么是删除缓存,而不是更新缓存

    另外更新缓存的代价有时候是很高的。是不是说,每次修改数据库的时候,都一定要将其对应的缓存更新一份?也许有的场景是这样,但是对于比较复杂的缓存数据计算的场景,就不是这样了。...如果你频繁修改一个缓存涉及的多个表,缓存也频繁更新。但是问题在于,这个缓存到底会不会被频繁访问到?...2)最初级的缓存不一致问题及解决方案 问题:先更新数据库,再删除缓存。如果删除缓存失败了,那么会导致数据库中是新数据,缓存中是旧数据,数据就出现了不一致。 解决思路:先删除缓存,再更新数据库。...如果数据库更新失败了,那么数据库中是旧数据,缓存中是空的,那么数据不会不一致。因为读的时候缓存没有,所以去读了数据库中的旧数据,然后更新缓存中。...3)比较复杂的数据不一致问题分析 数据发生了变更,先删除了缓存,然后要去修改数据库,此时还没修改。一个请求过来,去读缓存,发现缓存空了,去查询数据库,查到了修改前的旧数据,放到了缓存中。

    15410

    缓存层场景实战读缓存,如何更新缓存+缓存的高可用设计+监控

    ◆ 如何更新缓存 更新缓存的步骤特别简单,共两步:更新数据库和更新缓存。但这简单的两步中需要考虑很多问题。 1)先更新数据库还是先更新缓存更新缓存时先删除还是直接更新?...◆ 组合2:先删除缓存,再更新数据库 使用这种方案,即使更新数据库失败了也不需要回滚缓存。这种做法虽然巧妙规避了失败回滚的问题,却引出了两个更大的问题。 1)假设线程A先删除缓存,再更新数据库。...◆ 组合3:先更新数据库,再更新缓存 对于组合3,同样需要考虑两个问题。 1)假设第一步(更新数据库)成功,第二步(更新缓存)失败了怎么办?...除了组合3会碰到的问题,组合4还会碰到别的问题吗?是的。假设线程A要更新数据,先完成第一步更新数据库,在线程A删除缓存之前,线程B要访问缓存,那么取得的就是旧数据。这是一个小小的缺陷。...那么,以上问题有办法解决吗? ◆ 组合5:先删除缓存更新数据库,再删除缓存 还有一个方案,就是先删除缓存,再更新数据库,再删除缓存

    79610

    缓存层场景实战读缓存,如何更新缓存+缓存的高可用设计+监控

    如何更新缓存 更新缓存的步骤特别简单,共两步:更新数据库和更新缓存。但这简单的两步中需要考虑很多问题。 1)先更新数据库还是先更新缓存更新缓存时先删除还是直接更新?...组合2:先删除缓存,再更新数据库 使用这种方案,即使更新数据库失败了也不需要回滚缓存。这种做法虽然巧妙规避了失败回滚的问题,却引出了两个更大的问题。 1)假设线程A先删除缓存,再更新数据库。...组合3:先更新数据库,再更新缓存 对于组合3,同样需要考虑两个问题。 1)假设第一步(更新数据库)成功,第二步(更新缓存)失败了怎么办?...除了组合3会碰到的问题,组合4还会碰到别的问题吗?是的。假设线程A要更新数据,先完成第一步更新数据库,在线程A删除缓存之前,线程B要访问缓存,那么取得的就是旧数据。这是一个小小的缺陷。...那么,以上问题有办法解决吗? 组合5:先删除缓存更新数据库,再删除缓存 还有一个方案,就是先删除缓存,再更新数据库,再删除缓存

    82230

    缓存设计问题

    引入多级缓存时,需要考虑数据一致性 提前考虑扩容问题 常见的缓存问题 缓存雪崩 很多使用场景,查询的缓存数据都是由定时任务取刷新,然后缓存查不到从 DB 查了在更新缓存。...其次如果缓存差不到,数据库也查不到的数据也缓存起来。将 value 存个null, 过期时间短一点(如30s,如果设置太长肯恶搞导致正常的情况数据没法及时更新)。...针对这种情况可以: 异步设置热点key过期时间, 提前续上 缓存失效的时候, 加上一个全局的锁再去load db, 避免所有线程都打到db上 hot key 问题 对于某些 key 有非常大的访问量,...每次请求时,客户端随机访问一个即可 big key 问题 当访问缓存时,如果key对应的value过大,读写、加载很容易超时,容易引发网络拥堵。...在另一篇博客有详细的介绍: MySQL与缓存一致性问题

    34910

    Redis 缓存问题

    # Redis 缓存问题 缓存穿透 问题描述 解决方案 缓存击穿 问题描述 解决方案 缓存雪崩 问题描述 解决方案 总结 # 缓存穿透 # 问题描述 在默认情况下,用户请求数据时,会先在缓存(Redis...)中查找,若没找到即缓存未命中,再在数据库中进行查找,数量少可能问题不大,可是一旦大量的请求数据(例如秒杀场景)缓存都没有命中的话,就会全部转移到数据库上,造成数据库极大的压力,就有可能导致数据库崩溃。...# 缓存击穿 # 问题描述 相较于缓存穿透,缓存击穿的目的性更强,一个存在的 key,在缓存过期的一刻,同时有大量的请求,这些请求都会击穿到 DB,造成瞬时 DB 请求量大、压力骤增。...# 问题描述 大量的 key 设置了相同的过期时间,导致在缓存在同一时刻全部失效,此时若有大量并发请求过来,立即造成瞬时 DB 请求量大、压力骤增,引起雪崩。...设置过期标志更新缓存 记录缓存数据是否过期(设置提前量),如果过期会触发通知另外的线程 在后台去更新实际 key 的缓存

    1.2K30

    Mybatis 缓存问题

    先查询二级缓存,再去查询一级缓存,都没有命中才会去查询数据库 二级缓存是以配置文件 为单位的开启的,是在SqlSession 共享的,容易出现赃读、脏写,不建议使用!!!...一级缓存是SqlSession独享的,默认开启,建议开启 什么是一级缓存?...默认开启) 当我们连续通过Mybatis 查询同一条Sql的时候两次,在短时间内,只会在第一次查询时会走SQL,第二次查询,就不会出现连接数据库(Opening JDBC Connection)查询的问题了...第二次使用的是 一级缓存! 什么是二级缓存?(默认不开启) 如何开启呢?在mapper.xml 添加 缓存陷井?...特殊说明: 解决问题的光鲜,藏着磕Bug的痛苦。 万物皆入轮回,谁也躲不掉! 以上文章,均是我实际操作,写出来的笔记资料,不会出现全文盗用别人文章!烦请各位,请勿直接盗用!

    41310
    领券