背景
很多开发者在使用 Redis 时,习惯性地给 key 设置一个 TTL(Time To Live),认为"到期后 key 就会自动消失"。然而,Redis 的过期删除并不是"准时"的,而是结合了惰性删除 + 定期删除两种策略。如果对此不了解,可能导致:
- 内存未及时释放,OOM 风险;
- 业务逻辑误判"key 已过期",实则仍存在。
技术点详解
1. 惰性删除(Lazy Deletion)
- 当客户端尝试访问某个 key 时,Redis 才会检查该 key 是否已过期。
- 如果过期,则立即删除并返回 nil。
- 问题:如果一个 key 过期后长期无人访问,它会一直占用内存!
2. 定期删除(Periodic Deletion)
- Redis 默认每秒执行 10 次(即每 100ms 一次)定期删除任务。
- 每次随机抽查一部分设置了过期时间的 key,删除其中已过期的。
- 问题:抽查是概率性的,无法保证所有过期 key 被及时清理。
开发建议
- 不要依赖 Redis 过期时间做精确定时任务(如订单超时关闭),应配合定时扫描或延迟队列。
- 对于高频写入且大量短 TTL 的场景(如验证码缓存),需监控
used_memory和expired_keys指标,防止内存堆积。 - 可通过
INFO stats查看expired_keys和evicted_keys,评估过期策略效果。
