Lua 中 Cache 冷数据的落地
这篇讲的是如何在 Lua 虚拟机中,为缓存模块设计一个安全的冷数据落地机制。作者从一个实际 bug 讨论出发,详细分析了不同方案的演进。 文章最初提出一个基于时间戳的朴素方案,但发现其无法保证业务正在使用数据时,数据不会被错误地异步写回。随后,作者引入 Lua 弱表和 `__gc` 元方法进行改进,利用垃圾回收机制来判断数据是否“冷”。然而,这个方案存在一个微妙的“第三状态”漏洞:当对象被 GC 回收、但其 `__gc` 方法尚未将其“复活”到待处理表时,系统会短暂地失去对该数据的追踪,导致可能从数据库加载出旧版本的数据。 为解决这个并发与状态管理的核心难题,文章最终提出了基于元表代理的方案。通过让 cache 表存储代理对象,将真正的数据隔离在另一个全局表中,从而稳定了数据从缓存中移除的时机,并使冷数据落地流程可以清晰地通过集合差集来识别目标,避免了复杂的状态竞争问题。这实质上是用间接层换取了状态管理的清晰与安全。