PostgreSQL 内部原理第4部分:初学者指南 - 理解PostgreSQL中的WAL

PostgreSQL 内部原理第4部分:初学者指南 - 理解PostgreSQL中的WAL

💡 原文英文,约1500词,阅读约需6分钟。
📝

内容提要

本文介绍了PostgreSQL中的Write-Ahead Logging(WAL)的概念和内部结构,WAL是确保数据完整性和持久性的关键特性。文章还介绍了WAL在PostgreSQL中的工作原理和系统崩溃后的恢复过程,以及WAL文件的结构和命名规则。

🔎

延伸解读

WAL 的演进与关键特性

文章指出,PostgreSQL 7.1 引入 WAL,显著提升了可靠性和性能。此后,每个主要版本都带来了新特性:8.0 引入时间点恢复(PITR),9.0 引入流复制和热备,9.6 改进复制与恢复机制,10 引入逻辑复制,13 增强 WAL 归档和复制。这些演进表明 WAL 不仅是崩溃恢复的基础,也是高级功能如复制和 PITR 的基石。

同步提交设置对数据丢失风险的影响

文章通过问答形式说明,如果崩溃发生在 WAL 缓冲区,数据丢失风险取决于 synchronous_commit 设置。当设置为 on(默认)时,PostgreSQL 确保在事务提交前将 WAL 记录刷写到磁盘,从而最小化数据丢失风险。当设置为 off 时,事务在写入 WAL 缓冲区后即被视为提交,但尚未刷写到磁盘,这可以提高性能,但增加了崩溃时数据丢失的风险。

崩溃恢复中 LSN 比较机制

在恢复过程中,PostgreSQL 读取 WAL 段文件中的 XLOG 记录,并比较记录中的 LSN 与数据页的 LSN。如果 XLOG 记录的 LSN 大于页面的 LSN,说明该记录尚未应用到页面,PostgreSQL 会重放该记录并更新页面的 LSN。如果 XLOG 记录的 LSN 小于或等于页面的 LSN,则说明更改已应用,无需操作。这一机制确保所有已提交事务被应用,使数据库达到一致状态。

WAL 段文件的命名与滚动规则

WAL 段文件是 16MB 大小的文件,文件名由 24 位十六进制数组成,分为三部分:时间线 ID、日志文件 ID 和段 ID。例如,000000010000000000000001 表示时间线 1、日志文件 0、段 1。当段文件填满后,段 ID 递增;达到 FF 后,日志文件 ID 递增,段 ID 重置为 00。这种命名规则保证了 WAL 记录的顺序性,便于管理。

❓

Q&A

什么是PostgreSQL中的WAL?

WAL(预写日志)是PostgreSQL中的一个关键特性,用于确保数据完整性和持久性,它在数据库更改应用之前记录这些更改,以便在崩溃时恢复数据。

WAL是如何提高PostgreSQL的可靠性的?

WAL通过在事务提交前将更改记录写入日志,确保所有更改在应用到数据文件之前被安全存储,从而提高了数据库的可靠性和性能。

如果WAL缓冲区发生崩溃,会导致数据丢失吗?

数据丢失的风险取决于synchronous_commit设置。如果该设置为开启,WAL记录会在事务提交前写入磁盘,降低数据丢失风险;如果为关闭,可能会导致未写入磁盘的WAL记录丢失。

PostgreSQL是如何从WAL文件中恢复数据的?

PostgreSQL在恢复过程中读取WAL文件中的XLOG记录,从最近的检查点开始重放这些记录,以确保所有已提交的事务被应用,恢复数据库到一致状态。

WAL段文件的命名规则是什么?

WAL段文件的名称由时间线ID、日志文件ID和段ID组成,通常为16MB大小,文件名格式为24位十六进制数字,例如000000010000000000000001。

如何获取当前的WAL文件名称?

可以通过执行SQL查询SELECT pg_walfile_name(pg_current_wal_lsn());来获取当前WAL文件的名称。

🏷️

标签

➡️

继续阅读