3.2 WAL:澄清 WAL write failure 与 MemTable pending entry 的时序 #1

Closed
opened 2026-06-09 10:31:52 +08:00 by dailz · 0 comments
Owner

背景

docs/design.md 第 3.2 节的 WAL 写入流程是:commit queue -> WAL writer 组 batch -> 分配 sequence -> 编码并写 WAL -> 写入 MemTable pending -> fsync -> publish。

但后续失败处理描述中说:如果 WAL write 失败或 WAL bytes 未完整写入,pending entries 保留在 MemTable 中并保持 unpublished / aborted。

问题

这和当前流程存在时序矛盾:如果 WAL write 在写入 MemTable 之前失败,理论上 pending entry 还没有进入 MemTable。

风险

实现时可能出现两种互相冲突的解释:

  • 先写 WAL,失败时没有 MemTable entry,需要按纯 WAL failure 处理
  • 先写 MemTable,再写 WAL,失败时需要 aborted entry 和 flush 过滤

如果不明确,WAL、MemTable flush、recovery 的失败路径会分叉。

建议

在 3.2 中明确区分:

  1. WAL encode/write 失败且尚未插入 MemTable:无需 aborted entry
  2. 已插入 MemTable 后 fsync 失败:保留 unpublished / unknown entry
  3. 如果设计有意先写 MemTable 再写 WAL,应调整写入流程并重新说明 crash consistency

参考

  • docs/design.md:101 写入流程
  • docs/design.md:117 WAL write failure 处理
  • docs/design.md:119 fsync unknown 处理
## 背景 `docs/design.md` 第 3.2 节的 WAL 写入流程是:commit queue -> WAL writer 组 batch -> 分配 sequence -> 编码并写 WAL -> 写入 MemTable pending -> fsync -> publish。 但后续失败处理描述中说:如果 WAL write 失败或 WAL bytes 未完整写入,pending entries 保留在 MemTable 中并保持 unpublished / aborted。 ## 问题 这和当前流程存在时序矛盾:如果 WAL write 在写入 MemTable 之前失败,理论上 pending entry 还没有进入 MemTable。 ## 风险 实现时可能出现两种互相冲突的解释: - 先写 WAL,失败时没有 MemTable entry,需要按纯 WAL failure 处理 - 先写 MemTable,再写 WAL,失败时需要 aborted entry 和 flush 过滤 如果不明确,WAL、MemTable flush、recovery 的失败路径会分叉。 ## 建议 在 3.2 中明确区分: 1. WAL encode/write 失败且尚未插入 MemTable:无需 aborted entry 2. 已插入 MemTable 后 fsync 失败:保留 unpublished / unknown entry 3. 如果设计有意先写 MemTable 再写 WAL,应调整写入流程并重新说明 crash consistency ## 参考 - `docs/design.md:101` 写入流程 - `docs/design.md:117` WAL write failure 处理 - `docs/design.md:119` fsync unknown 处理
dailz closed this issue 2026-06-09 11:39:14 +08:00
Sign in to join this conversation.
No Label
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: dailz/go-kv#1