“ARIES 在 预写日志 和 steal/no force 缓冲管理 上运行。更新日志通常含 LSN、事务 ID、、页 ID、redo/undo 信息;每个数据页记录 。重启按三阶段执行。”
形式陈述 ​
预写日志为每条日志记录分配单调递增的日志序列号 LSN,并区分易失缓冲区与稳定存储。为把 数据库事务 扩展到可重启的 崩溃故障 模型,WAL 规定两条不同的先行关系。
第一条约束数据页:若内存页
在允许覆盖旧值的 steal/undo 恢复设计中,这要求恢复所需的 before-image 或逻辑 undo 信息先安全存在,未提交脏页才可提前落盘。WAL 本身并不强制所有系统物理撤销未提交更新;多版本系统可以通过事务状态与可见性排除未提交版本,其日志内容须匹配自己的恢复设计。
第二条约束承诺崩溃后仍保留的提交确认:在向客户端报告这种持久提交成功前,必须把该事务的 commit 记录以及此前的日志前缀刷到稳定日志。它不要求事务修改的每个数据页同时落盘;这些页可在崩溃后由 redo 恢复。某些系统允许异步提交,即在日志稳定前回复,并明确接受最近已回复事务在崩溃后丢失;这是减弱持久性承诺,不能沿用本页的持久提交结论。
日志按前缀刷盘意味着一次顺序写可以同时覆盖多个事务的 commit,形成 group commit。共享 I/O 不改变每个事务的持久承诺点:只有包含其 commit LSN 的前缀稳定后,系统才可确认持久提交。缓存中的日志记录数量不能替代 flushedLSN 证据。
直觉
日志像数据页修改的可追溯收据。仓库可以先把货物搬到货架,但收据必须先入保险柜;否则断电后只看见变化,却不知道它属于已提交交易还是应撤销的半次尝试。对客户说“交易完成”前,盖有 commit 章的收据也必须进保险柜。
WAL 规定顺序,不规定完整恢复算法。日志中记录物理 before/after image、逻辑操作还是混合信息,恢复从哪里开始、怎样避免重复执行,都需要进一步协议。
页写与日志写是两条独立流水线,LSN 把它们接成可检查的不等式。这个接口让缓冲管理器无需理解事务业务,也让日志管理器无需决定哪一页最适合换出;双方只在 pageLSN 与 flushedLSN 上协调。
例子与边界
页
LSN 40: T, P, before=7, after=9
LSN 50: T, COMMIT
内存页更新为 pageLSN=40。若缓冲管理器在 commit 前写回
这两个故障点展示不同责任。只满足第一条便确认持久 commit,可能在日志 50 丢失后把已回复客户的事务当成 loser;只满足第二条却允许 page 40 先于日志 40 落盘,则本例中止事务的脏页没有可靠撤销依据。若日志 50 已持久化、但确认消息发送前服务器崩溃,恢复仍应保留提交;客户端此时只是结果未知,并非事务中止。
恢复本身也可能再次崩溃。对本例的物理 redo,可在页面 LSN 小于 40 时写入 after-image 并更新 pageLSN;若页面已包含该记录,就跳过它。这样重复扫描日志不会把同一更新反复作用。若日志只记录“余额减 2”,则须用版本或去重条件判断操作是否已经发生,否则重放会再次扣款。物理 after-image 较容易重复写入,但可能增加日志量;记录内容是否足够恢复,仍须随恢复算法逐项证明。
WAL 默认稳定日志本身按声明方式写入。扇区撕裂、控制器谎报 flush、日志介质永久损坏或主机与存储的缓存语义不一致,都需要校验、冗余和真实持久化屏障。它也不处理媒体恢复所需的备份基线。
推论与应用
steal/no-force 缓冲管理正利用两条规则:steal 依靠已预写的 undo 信息,no-force 依靠已持久化的 redo 与 commit 证据。ARIES 恢复算法在此基础上加入 LSN 链、脏页表、重复历史和补偿日志。
与 WAL 相对,影子分页恢复通过写时复制和根指针切换保留旧页,不以逐更新日志为主要恢复依据。两者都要证明稳定写入顺序,不能把“无 WAL”误写成“无需持久化协议”。
运维验证应在 page flush 前、commit log flush 前后和回复客户端前后注入崩溃。只在空闲时优雅重启不会覆盖关键窗口;在本页的 undo/redo 例子中,正确结果应分别表现为撤销 loser、重做 winner,且绝不能遗忘已经确认持久化的 commit。采用多版本恢复或异步提交的系统,应按其明确承诺调整验收条件。
参考资料
- C. Mohan et al., “ARIES: A Transaction Recovery Method Supporting Fine-Granularity Locking and Partial Rollbacks Using Write-Ahead Logging,” ACM Transactions on Database Systems 17(1), 1992, pp. 94–162。
- Theo Härder and Andreas Reuter, “Principles of Transaction-Oriented Database Recovery,” ACM Computing Surveys 15(4), 1983, pp. 287–317。
- Jim Gray and Andreas Reuter, Transaction Processing: Concepts and Techniques, Morgan Kaufmann, 1992, Chs. 9–11。
- PostgreSQL Global Development Group, PostgreSQL 16 Documentation, §30.3 Write-Ahead Logging 与 §30.4 Asynchronous Commit:日志先于数据页落盘、redo、group commit 与减弱持久承诺。