数据库和缓存一致性问题

1、假设操作都能成功:
写:先更新数据库,后删除缓存
读:先读缓存,如果不存在读数据库,再写缓存

只要操作都成功,大部分时间可以做到缓存一致

除一种情况,2 个线程并发读写数据:

1、缓存中 X 不存在(数据库 X = 1)
2、线程 A 读取数据库,得到旧值(X = 1)
3、线程 B 更新数据库(X = 2)
4、线程 B删除缓存
5、线程 A 将旧值写入缓存(X = 1)
最终 X 的值在缓存中是 1(旧值),在数据库中是 2(新值),发生不一致。

其实概率「很低」,这是因为它必须满足 3 个条件:
1、缓存刚好已失效
2、读请求 + 写请求并发
3、更新数据库 + 删除缓存的时间(步骤 3-4),要比读数据库 + 写缓存时间短(步骤 2 和 5)
仔细想一下,条件 3 发生的概率其实是非常低的。因为写数据库一般会先「加锁」,所以写数据库,通常是要比读数据库的时间更长的。

2、假设有操作失败
程序在执行过程中发生异常,最简单的解决办法:异步重试。
其实就是把重试请求写到「消息队列」中,然后由专门的消费者来重试,直到成功。
或者订阅数据库变更日志,再操作缓存。

在「先更新数据库,再删除缓存」方案下,「读写分离 + 主从库延迟」也会导致缓存和数据库不一致,缓解此问题的方案是「延迟双删」,发送「延迟消息」到队列中,延迟删除缓存,同时也要控制主从库延迟,尽可能降低不一致发生的概率。
但是,这个时间在分布式和高并发场景下,其实是很难评估的。
很多时候,我们都是凭借经验大致估算这个延迟时间,例如延迟 1-5s,只能尽可能地降低不一致的概率。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值