当Redis内存用完后,会发生以下几种情况:
一、写入操作失败
Redis达到最大内存限制后,默认行为是拒绝新的写入操作并返回错误。此时SET、HSET等写命令会报错”OOM command not allowed when used memory > ‘maxmemory'”,但读操作和删除操作仍可正常执行。这是为了保护数据一致性,防止数据丢失。
二、触发内存淘汰策略
如果配置了内存淘汰策略,Redis会根据策略自动删除数据来腾出空间。Redis提供了8种淘汰策略:
全局键空间策略:
allkeys-lru:淘汰所有键中最近最少使用的键(推荐通用场景)allkeys-lfu:淘汰所有键中使用频率最低的键(Redis 4.0+)allkeys-random:随机淘汰任意键
过期键空间策略:
volatile-lru:仅淘汰设置了过期时间的键中最近最少使用的键volatile-lfu:仅淘汰设置了过期时间的键中使用频率最低的键volatile-random:随机淘汰设置了过期时间的键volatile-ttl:优先淘汰剩余生存时间最短的键
不淘汰策略:
noeviction:默认策略,内存满时拒绝写入并报错
三、性能显著下降
当内存接近满时,Redis需要频繁进行数据淘汰操作,这会增加CPU负载,导致响应时间延长和吞吐量下降。如果启用了操作系统的内存交换(Swap),Redis会将部分数据交换到硬盘,由于硬盘读写速度远低于内存,性能会急剧下降。
四、数据丢失风险
根据淘汰策略,一些数据可能会被删除以释放内存,这意味着应用程序可能无法再访问这些数据。如果配置了持久化(RDB或AOF),在内存满时如果服务器崩溃,最近保存在内存中但尚未持久化到磁盘的数据将会丢失。
五、系统级OOM Killer
如果Redis内存使用超过系统可用物理内存+Swap空间,Linux内核的OOM Killer可能会终止Redis进程。Redis默认的oom_score_adj通常为0,当系统内存不足时,Redis作为内存占用大户,被Kill的风险极高。
六、内存碎片化
频繁的数据淘汰和内存分配会导致内存碎片化,即内存中存在不连续的空闲块,无法被大的数据对象使用,进一步加剧内存不足的问题。
应对建议
- 合理配置内存限制:设置maxmemory为物理内存的70-80%
- 选择合适的淘汰策略:根据业务场景选择allkeys-lru或volatile-lru
- 设置过期时间:为临时数据设置合理的TTL
- 监控内存使用:定期使用INFO memory命令查看内存状态
- 优化数据结构:拆分大Key,避免使用KEYS命令,改用SCAN
- 考虑集群部署:通过Redis Cluster将数据分散到多个节点