WAL会自动启用;除了确保满足 WAL 文件所需的磁盘空间,并进行任何必要的调整(参见 第 28.5 节)之外,管理员无需采取任何操作。WAL文件,并在写入每个新记录时追加到
WAL记录被追加到WAL文件。插入位置由一个日志序列号(LSN)描述,该号码是 WAL 中的一个字节偏移量,随着每个新记录的写入而单调递增。LSN值作为数据类型 pg_lsn
返回。值可以进行比较,以计算它们之间的数据量,因此它们用于测量复制和恢复的进度。WAL数据量,所以它们用于衡量复制和恢复的进度。
WAL文件存储在数据目录下的 pg_wal
目录中,作为一系列段文件,通常每个文件大小为 16MB(但可以通过修改 initdb 的 --wal-segsize
选项来更改大小)。每个段又被划分为页面,通常每页 8kB(此大小可以通过 --with-wal-blocksize
configure 选项更改)。WAL 记录头在 access/xlogrecord.h
中描述;记录内容取决于正在记录的事件类型。段文件的命名为递增的数字,从 000000010000000000000001
开始。这些数字不会回绕,但用完所有数字需要非常非常长的时间。
如果 WAL 位于与主数据库文件不同的磁盘上,将会带来好处。这可以通过(当然是在服务器关闭的情况下)将 pg_wal
目录移动到另一个位置,并在主数据目录的原始位置创建一个指向新位置的符号链接来实现。
目标是WAL的目的是确保日志在数据库记录被修改之前写入,但这可能会被磁盘驱动器所破坏,这些驱动器会虚假地向内核报告写入成功,而实际上它们只缓存了数据但尚未将其存储在磁盘上。在这种情况下,断电可能会导致无法恢复的数据损坏。管理员应尽量确保存储 PostgreSQL 的 WAL 文件的磁盘不会做出此类虚假报告(参见 第 28.1 节)。WAL文件不产生此类虚假报告。
在制作完检查点并刷新 WAL 后,检查点的位置保存在 pg_control
文件中。因此,在恢复开始时,服务器首先读取 pg_control
,然后读取检查点记录;然后,它通过从检查点记录中指示的 WAL 位置向前扫描来执行 REDO 操作。由于在检查点后的第一次页面修改时,所有更改过的页面的完整内容都会保存在 WAL 中(假设 full_page_writes 没有被禁用),因此自上次检查点以来更改的所有页面都将被恢复到一致的状态。
为了处理 pg_control
损坏的情况,我们应该支持反向扫描现有 WAL 段(从最新到最旧)以查找最新检查点的可能性。这尚未实现。pg_control
的大小足够小(小于一个磁盘页),因此它不会受到部分写入问题的影响,并且在编写本文时,还没有关于仅因无法读取 pg_control
本身而导致数据库失败的报告。所以,虽然它理论上是一个薄弱环节,但在实践中 pg_control
似乎并不是一个问题。
如果您在文档中发现任何不正确之处、与您在使用特定功能时的体验不符之处,或者需要进一步澄清的地方,请使用 此表格 报告文档问题。