标准答案

  1. 通常先完成数据库事务,再删除缓存。这样下一次缓存未命中时读取的是已提交的新数据,不会把未提交或失败写入提前暴露给读请求。
  2. 若数据库成功而删除缓存失败,旧缓存会持续到 TTL;需要删除重试、消息通知、版本化 Key 或后台校对来缩短窗口。
  3. 并发读可能在数据库更新后、缓存删除前读到旧值,也可能在删除后回填旧值;对强一致性要求高的操作,应在写校验、版本号或事务边界上保证,不能只依赖缓存顺序。
  4. 不应把“先删缓存再写数据库”当默认方案,因为写失败会无意义地打穿缓存;也不应默认同时更新缓存和数据库,因为双写失败与并发覆盖更难收敛。

题目解析

缓存一致性通常是最终一致性问题。回答时要说清数据允许多长时间旧读、写成功后哪些读取必须走主库或版本校验、失败信号如何被监控。

事件驱动失效和 Outbox 可提高删除可靠性,但也需要处理消息重复、乱序和消费者延迟。它们是缩小不一致窗口的工程措施,不是瞬时强一致事务。

代码示例

下面的顺序强调提交成功后再触发缓存失效;删除失败必须进入可重试的补偿路径。

Text
begin transaction
  update database
commit
try cache.delete(product:{id})
catch -> persist retry task / emit invalidation event

常见误区

  • 声称“先更新数据库后删缓存”可以保证绝对强一致。
  • 删除失败只打印日志,不做重试、告警或校对。
  • 把缓存失效事件当作不能重复、不能乱序的一次性消息。

作者信息