清理一个包含几十万元素的集合时,接口出现明显卡顿,监控显示命令耗时异常。日志里能对上时间点,这种反而好排。
删除大 key 需要释放大量内存,单线程模型下会阻塞其他命令执行。这一点先确认清楚,后面就不用反复试。
UNLINK big:set
# 分批
for i in range(100):
redis.srem('big:set', *members[i*1000:(i+1)*1000])
「Redis 大key删除」确认了原因之后,改动尽量只碰那一处,顺手改的东西后面最容易出问题。偶发问题先统计频率,一小时几次和一天一次,查法完全不同。
改完顺手把文档补一句,省得下次自己重新推一遍。监控和日志的时间要对上,时区不一致会多绕很大一圈。
临时改动用注释写上日期和原因,过两周自己都记不清为什么这么写。动手前把原文件复制一份带时间戳,出问题立刻换回去,比现场分析快得多。
处理上按这个顺序:先分批删除元素再删键;使用异步删除命令;清理前评估大小并选择低峰执行。
结果对不对很好判断,清理过程接口无卡顿,键被删除且内存占用下降。