Skip to content

20.4 资源消耗#

20.4.1 内存
20.4.2 磁盘
20.4.3 内核资源使用
20.4.4 基于成本的 Vacuum 延迟
20.4.5 后台写入器
20.4.6 异步行为

20.4.1 内存#

shared_buffers (integer) #

设置数据库服务器用于共享内存缓冲区的内存量。默认值通常为 128 兆字节 (128MB),但如果内核设置不支持(在 initdb 期间确定),则可能更低。此设置必须至少为 128 千字节。但是,通常需要远高于最低值的设置才能获得良好的性能。如果未指定此值单位,则将其视为块,即 BLCKSZ 字节,通常为 8kB。(BLCKSZ 的非默认值会更改最小值。)此参数只能在服务器启动时设置。

如果您有一个具有 1GB 或更多 RAM 的专用数据库服务器,则 shared_buffers 的合理起始值为系统中内存的 25%。有些工作负载即使将 shared_buffers 设置为更大值也是有效的,但由于 PostgreSQL 还依赖于操作系统缓存,因此将超过 40% 的 RAM 分配给 shared_buffers 不太可能比较小数量的效果更好。将 shared_buffers 设置为较大值通常需要相应增加 max_wal_size,以便在较长时间内分摊写入大量新数据或更改数据的过程。

在 RAM 少于 1GB 的系统上,应使用较小百分比的 RAM,以便为操作系统留出足够的空间。

huge_pages (enum) #

控制是否为主要共享内存区域请求大页面。有效值为 try(默认值)、onoff。当 huge_pages 设置为 try 时,服务器将尝试请求大页面,但如果失败,则回退到默认值。当 on 时,请求大页面失败将阻止服务器启动。当 off 时,将不会请求大页面。

目前,此设置仅在 Linux 和 Windows 上受支持。当设置为 try 时,该设置在其他系统上将被忽略。在 Linux 上,仅当 shared_memory_type 设置为 mmap(默认值)时才受支持。

使用大页面可减少页表大小并减少 CPU 在内存管理上花费的时间,从而提高性能。有关在 Linux 上使用大页面的更多详细信息,请参阅 第 19.4.5 节

在 Windows 上,大页面称为大页面。要使用它们,您需要将用户权限 锁定内存中的页面 分配给运行 PostgreSQL 的 Windows 用户帐户。您可以使用 Windows 组策略工具 (gpedit.msc) 来分配用户权限 锁定内存中的页面。要以独立进程(而非 Windows 服务)在命令提示符上启动数据库服务器,必须以管理员身份运行命令提示符或禁用用户访问控制 (UAC)。当启用 UAC 时,启动时普通命令提示符会撤销用户权限 锁定内存中的页面

请注意,此设置仅影响主共享内存区域。诸如 Linux、FreeBSD 和 Illumos 等操作系统还可以自动为普通内存分配使用大页面(也称为 超级 页面或 页面),而无需 PostgreSQL 的明确请求。在 Linux 上,这称为 透明大页面 (THP)。已知该功能会导致 PostgreSQL 在某些 Linux 版本上对某些用户造成性能下降,因此目前不建议使用(与明确使用 huge_pages 不同)。

huge_page_size (integer) #

当使用 huge_pages 启用大页面时,控制大页面的大小。默认值为零 (0)。当设置为 0 时,将使用系统上的默认大页面大小。此参数只能在服务器启动时设置。

现代 64 位服务器架构上通常可用的页面大小包括:2MB1GB(英特尔和 AMD)、16MB16GB(IBM POWER)以及 64kB2MB32MB1GB(ARM)。有关用法和支持的更多信息,请参阅第 19.4.5 节

目前仅在 Linux 上支持非默认设置。

temp_buffers (integer) #

设置每个数据库会话中临时缓冲区使用的最大内存量。这些是仅用于访问临时表的会话本地缓冲区。如果未指定该值单位,则将其视为块,即 BLCKSZ 字节,通常为 8kB。默认值为八兆字节 (8MB)。(如果 BLCKSZ 不为 8kB,则默认值将按比例缩放。)此设置可以在各个会话中更改,但只能在会话中首次使用临时表之前更改;随后更改该值的尝试将不会影响该会话。

会话将根据 temp_buffers 给出的限制按需分配临时缓冲区。在实际上不需要许多临时缓冲区的会话中设置一个大值,其成本只是一个缓冲区描述符,或每个 temp_buffers 增量约 64 字节。但是,如果实际使用了缓冲区,则将为其消耗额外的 8192 字节(或通常为 BLCKSZ 字节)。

max_prepared_transactions (integer) #

设置可以同时处于已准备状态的事务的最大数量(请参阅PREPARE TRANSACTION)。将此参数设置为零(这是默认值)将禁用已准备事务功能。此参数只能在服务器启动时设置。

如果您不打算使用已准备事务,则应将此参数设置为零,以防止意外创建已准备事务。如果您正在使用已准备事务,您可能希望 max_prepared_transactions 至少与 max_connections 一样大,以便每个会话都可以挂起已准备事务。

在运行备用服务器时,您必须将此参数设置为与主服务器上相同或更高的值。否则,将不允许在备用服务器中进行查询。

work_mem (整数) #

设置查询操作(例如排序或哈希表)在写入临时磁盘文件之前使用的基本最大内存量。如果未指定单位,则以千字节为单位。默认值为四兆字节 (4MB)。请注意,复杂查询可能同时执行多个排序和哈希操作,每个操作通常允许使用此值指定的最大内存量,然后才开始将数据写入临时文件。此外,多个正在运行的会话可以同时执行此类操作。因此,使用的总内存可能是 work_mem 值的数倍;在选择值时有必要牢记这一事实。排序操作用于 ORDER BYDISTINCT 和合并连接。哈希表用于哈希连接、基于哈希的聚合、记忆节点和基于哈希的 IN 子查询处理。

基于哈希的操作通常比基于排序的同等操作对内存可用性更敏感。哈希表的内存限制通过将 work_mem 乘以 hash_mem_multiplier 来计算。这使得基于哈希的操作可以使用超出通常 work_mem 基本量的内存量。

hash_mem_multiplier (浮点) #

用于计算基于哈希的操作可以使用的最大内存量。最终限制通过将 work_mem 乘以 hash_mem_multiplier 来确定。默认值为 2.0,这使得基于哈希的操作使用通常 work_mem 基本量的两倍。

在查询操作经常溢出的环境中,考虑增加 hash_mem_multiplier,尤其是在仅仅增加 work_mem 会导致内存压力(内存压力通常表现为间歇性的内存不足错误)时。默认设置 2.0 通常对混合工作负载有效。在 work_mem 已增加到 40MB 或更多的情况中,2.0 - 8.0 或更高的设置可能有效。

maintenance_work_mem (integer) #

指定维护操作(例如 VACUUMCREATE INDEXALTER TABLE ADD FOREIGN KEY)可使用的最大内存量。如果未指定单位,则此值将以千字节为单位。其默认值为 64 兆字节 (64MB)。由于数据库会话一次只能执行其中一项操作,并且一个安装通常不会同时运行很多此类操作,因此可以将此值设置为显著大于 work_mem 的值。较大的设置可能会提高清理和恢复数据库转储的性能。

请注意,当自动清理运行时,可能会分配高达 autovacuum_max_workers 倍的内存,因此请小心不要将默认值设置得太高。通过单独设置 autovacuum_work_mem 来控制此设置可能很有用。

请注意,对于已死元组标识符的收集,VACUUM 只能利用最多 1GB 的内存。

autovacuum_work_mem (integer) #

指定每个自动清理工作程序进程可使用的最大内存量。如果未指定单位,则此值将以千字节为单位。其默认值为 -1,表示应使用 maintenance_work_mem 的值。此设置对在其他上下文中运行的 VACUUM 的行为没有影响。此参数只能在 postgresql.conf 文件或服务器命令行中设置。

对于已死元组标识符的收集,自动清理只能利用最多 1GB 的内存,因此将 autovacuum_work_mem 设置为高于该值不会影响自动清理在扫描表时可以收集的已死元组数量。

vacuum_buffer_usage_limit (integer) #

指定 缓冲区访问策略 的大小,由 VACUUMANALYZE 命令使用。设置 0 将允许操作使用任意数量的 shared_buffers。否则,有效大小范围为 128 kB16 GB。如果指定的大小超过 shared_buffers 大小的 1/8,则该大小将自动限制为该值。默认值为 256 kB。如果未指定单位,则此值将以千字节为单位。此参数可随时设置。当传递 BUFFER_USAGE_LIMIT 选项时,可为 VACUUMANALYZE 覆盖此参数。较高的设置可以让 VACUUMANALYZE 运行得更快,但设置过高可能会导致太多其他有用的页面从共享缓冲区中驱逐出去。

logical_decoding_work_mem (integer) #

指定逻辑解码使用的最大内存量,在将部分已解码的更改写入本地磁盘之前。这限制了逻辑流复制连接使用的内存量。其默认值为 64 兆字节 (64MB)。由于每个复制连接仅使用此大小的单个缓冲区,并且一个安装通常不会同时有许多此类连接(受 max_wal_senders 限制),因此可以将此值设置为明显高于 work_mem,从而减少写入磁盘的已解码更改量。

max_stack_depth (integer) #

指定服务器执行堆栈的最大安全深度。此参数的理想设置是内核强制执行的实际堆栈大小限制(由 ulimit -s 或本地等效项设置),减去大约一兆字节的安全裕度。需要安全裕度,因为服务器中并非每个例程都会检查堆栈深度,而只在关键的潜在递归例程中检查。如果未指定此值的单位,则将其视为千字节。默认设置是两兆字节 (2MB),该设置保守而小,不太可能导致崩溃。但是,它可能太小,无法执行复杂函数。只有超级用户和具有适当 SET 权限的用户才能更改此设置。

max_stack_depth 设置得高于实际内核限制意味着失控的递归函数可能会使单个后端进程崩溃。在 PostgreSQL 可以确定内核限制的平台上,服务器不允许将此变量设置为不安全的值。但是,并非所有平台都提供此信息,因此建议在选择值时谨慎行事。

shared_memory_type (enum) #

指定服务器应为包含 PostgreSQL 共享缓冲区和其他共享数据的 PostgreSQL 主共享内存区域使用的共享内存实现。可能的值包括 mmap(用于使用 mmap 分配的匿名共享内存)、sysv(用于通过 shmget 分配的 System V 共享内存)和 windows(用于 Windows 共享内存)。并非所有值在所有平台上都受支持;第一个受支持的选项是该平台的默认值。一般不建议使用 sysv 选项(并非任何平台上的默认值),因为它通常需要非默认内核设置才能允许大分配(请参阅 第 19.4.1 节)。

dynamic_shared_memory_type (enum) #

指定服务器应使用的动态共享内存实现。可能的值为 posix(用于使用 shm_open 分配的 POSIX 共享内存)、sysv(用于通过 shmget 分配的 System V 共享内存)、windows(用于 Windows 共享内存)和 mmap(用于使用存储在数据目录中的内存映射文件模拟共享内存)。并非所有值都受所有平台支持;第一个受支持的选项通常是该平台的默认选项。通常不建议使用 mmap 选项(它并非任何平台的默认选项),因为操作系统可能会将修改后的页面反复写入磁盘,从而增加系统 I/O 负载;但是,它可能对调试有用,例如当 pg_dynshmem 目录存储在 RAM 磁盘上时,或者当其他共享内存功能不可用时。

min_dynamic_shared_memory (integer) #

指定在服务器启动时应分配的内存量,以便并行查询使用。当此内存区域不足或被并发查询耗尽时,新的并行查询会尝试使用 dynamic_shared_memory_type 配置的方法从操作系统临时分配额外的共享内存,这可能会由于内存管理开销而变慢。在启动时使用 min_dynamic_shared_memory 分配的内存受 huge_pages 设置的影响(在支持该设置的操作系统上),并且在自动管理该设置的操作系统上更有可能受益于更大的页面。默认值为 0(无)。此参数只能在服务器启动时设置。

20.4.2. 磁盘#

temp_file_limit (integer) #

指定进程可用于临时文件(例如排序和哈希临时文件或保持游标的存储文件)的最大磁盘空间量。尝试超过此限制的事务将被取消。如果未指定此值单位,则将其视为千字节。 -1(默认值)表示无限制。只有超级用户和具有适当 SET 权限的用户才能更改此设置。

此设置限制给定的 PostgreSQL 进程使用的所有临时文件在任何时刻使用的总空间。需要注意的是,用于显式临时表(与查询执行中后台使用的临时文件相对)的磁盘空间 计入此限制。

20.4.3. 内核资源使用#

max_files_per_process (integer) #

设置允许每个服务器子进程同时打开的最大文件数。默认是一千个文件。如果内核正在强制执行一个安全的每个进程限制,则无需担心此设置。但在某些平台(特别是大多数 BSD 系统)上,如果许多进程都尝试打开许多文件,内核将允许各个进程打开比系统实际支持的更多文件。如果您发现看到 打开的文件过多 失败,请尝试减少此设置。此参数只能在服务器启动时设置。

20.4.4. 基于成本的 Vacuum 延迟#

在执行VACUUMANALYZE命令期间,系统维护一个内部计数器,用于跟踪所执行的各种 I/O 操作的估计成本。当累积成本达到限制(由vacuum_cost_limit指定)时,执行操作的进程将休眠一段时间,如vacuum_cost_delay指定的那样。然后它将重置计数器并继续执行。

此功能的目的是允许管理员减少这些命令对并发数据库活动的 I/O 影响。在许多情况下,维护命令(如VACUUMANALYZE)快速完成并不重要;但是,这些命令通常不会严重干扰系统执行其他数据库操作的能力非常重要。基于成本的 vacuum 延迟为管理员提供了一种实现此目的的方法。

此功能在手动发出的VACUUM命令中默认禁用。要启用它,请将vacuum_cost_delay变量设置为非零值。

vacuum_cost_delay (浮点数) #

当成本限制被超过时,进程将休眠的时间量。如果未指定此值单位,则将其视为毫秒。默认值为零,这将禁用基于成本的 vacuum 延迟功能。正值启用基于成本的 vacuum。

在使用基于成本的 vacuum 时,vacuum_cost_delay 的适当值通常非常小,可能小于 1 毫秒。虽然 vacuum_cost_delay 可以设置为毫秒级以下的值,但此类延迟在较旧的平台上可能无法准确测量。在这样的平台上,要增加 VACUUM 的节流资源消耗(高于在 1 毫秒时获得的消耗),需要更改其他 vacuum 成本参数。尽管如此,您应该将 vacuum_cost_delay 保持在您的平台可以持续测量的大小;大的延迟没有帮助。

vacuum_cost_page_hit (整数) #

在共享缓冲区高速缓存中找到缓冲区时,对真空吸尘的估计成本。它表示锁定缓冲池、查找共享哈希表和扫描页面内容的成本。默认值为 1。

vacuum_cost_page_miss (整数) #

对必须从磁盘读取的缓冲区进行真空吸尘的估计成本。它表示锁定缓冲池、查找共享哈希表、从磁盘读取所需块并扫描其内容所做的工作。默认值为 2。

vacuum_cost_page_dirty (整数) #

真空吸尘修改先前干净的块时收取的估计成本。它表示将脏块再次刷新到磁盘所需的额外 I/O。默认值为 20。

vacuum_cost_limit (整数) #

将导致真空吸尘进程休眠的累积成本。默认值为 200。

注意

某些操作持有关键锁,因此应尽快完成。成本为基础的真空吸尘延迟不会在这些操作期间发生。因此,成本可能会累积得远高于指定的限制。为了避免在这种情况下出现无用的长时间延迟,实际延迟将计算为vacuum_cost_delayaccumulated_balance/vacuum_cost_limit,最大值为vacuum_cost_delay 4。

20.4.5. 后台写入器#

有一个单独的服务器进程称为后台写入器,其功能是发出“脏”(新或已修改)共享缓冲区的写入。当干净共享缓冲区的数量似乎不足时,后台写入器会将一些脏缓冲区写入文件系统并将其标记为干净。这降低了处理用户查询的服务器进程无法找到干净缓冲区并且必须自己写入脏缓冲区的可能性。但是,后台写入器确实导致 I/O 负载的总体净增加,因为虽然重复弄脏的页面可能在每个检查点间隔内只写入一次,但后台写入器可能会在同一间隔内弄脏它时多次写入它。本小节中讨论的参数可用于根据本地需求调整行为。

bgwriter_delay (integer) #

指定后台写入器活动轮次之间的延迟。在每个轮次中,写入器会为一些脏缓冲区发出写入(可通过以下参数控制)。然后,它将休眠bgwriter_delay的时间长度,然后重复。但是,当缓冲池中没有脏缓冲区时,它会进入更长时间的休眠,而不管bgwriter_delay如何。如果未指定此值,则将其视为毫秒。默认值为 200 毫秒 (200ms)。请注意,在许多系统上,休眠延迟的有效分辨率为 10 毫秒;将bgwriter_delay设置为不是 10 的倍数的值可能会产生与将其设置为下一个更高的 10 的倍数相同的结果。此参数只能在postgresql.conf文件中或在服务器命令行上设置。

bgwriter_lru_maxpages (integer) #

在每个轮次中,后台写入器最多将写入此数量的缓冲区。将其设置为零将禁用后台写入。(请注意,由单独的专用辅助进程管理的检查点不受影响。)默认值为 100 个缓冲区。此参数只能在postgresql.conf文件中或在服务器命令行上设置。

bgwriter_lru_multiplier (floating point) #

每个轮次中写入的脏缓冲区数量基于服务器进程在最近轮次中所需的新缓冲区数量。将平均近期需求乘以bgwriter_lru_multiplier以得出下一轮次中所需缓冲区数量的估计值。脏缓冲区将被写入,直到有那么多干净的可重用缓冲区可用为止。(但是,每个轮次最多将写入bgwriter_lru_maxpages个缓冲区。)因此,1.0 的设置表示准时策略,即写入预测需要的确切缓冲区数量。较大的值可为需求激增提供一些缓冲,而较小的值则故意将写入留给服务器进程。默认值为 2.0。此参数只能在postgresql.conf文件中或在服务器命令行上设置。

bgwriter_flush_after (整数) #

每当后台写入程序写入的数据量超过此值时,尝试强制操作系统将这些写入操作发送到底层存储。这样做将限制内核页面高速缓存中的脏数据量,从而降低在检查点结束时发出 fsync 或当操作系统在后台以更大的批次回写数据时发生停滞的可能性。通常,这将大大减少事务延迟,但也有一些情况,特别是对于比 shared_buffers 大但比操作系统的页面高速缓存小的工作负载,性能可能会下降。此设置在某些平台上可能无效。如果未指定此值单位,则将其视为块,即 BLCKSZ 字节,通常为 8kB。有效范围介于 0(禁用强制回写)和 2MB 之间。在 Linux 上的默认值为 512kB,在其他地方的默认值为 0。(如果 BLCKSZ 不是 8kB,则默认值和最大值将按比例缩放。)此参数只能在 postgresql.conf 文件或服务器命令行中设置。

较小的bgwriter_lru_maxpagesbgwriter_lru_multiplier值会减少后台写入程序造成的额外 I/O 负载,但会增加服务器进程必须自己发出写入操作的可能性,从而延迟交互式查询。

20.4.6. 异步行为#

backend_flush_after (整数) #

当单个后端写入的数据量超过此值时,尝试强制操作系统将这些写入操作发送到底层存储。这样做将限制内核页面缓存中的脏数据量,从而降低在检查点结束时发出 fsync 或当操作系统在后台以较大批次写入数据时发生停顿的可能性。通常这将大大降低事务延迟,但也有一些情况,尤其是当工作负载大于 shared_buffers 但小于操作系统的页面缓存时,性能可能会下降。此设置在某些平台上可能无效。如果未指定单位,则此值将视为块,即 BLCKSZ 字节,通常为 8kB。有效范围在 0(禁用强制写回)和 2MB 之间。默认值为 0,即不强制写回。(如果 BLCKSZ 不为 8kB,则最大值将按比例缩放。)

effective_io_concurrency (integer) #

设置 PostgreSQL 预计可以同时执行的并发磁盘 I/O 操作数。提高此值将增加任何单个 PostgreSQL 会话尝试并行启动的 I/O 操作数。允许的范围为 1 到 1000,或零以禁用异步 I/O 请求的发出。目前,此设置仅影响位图堆扫描。

对于磁性驱动器,此设置的一个良好起点是用于数据库的 RAID 0 条带或 RAID 1 镜像所包含的独立驱动器数。(对于 RAID 5,不应计算奇偶校验驱动器。)但是,如果数据库经常在并发会话中发出多个查询,则较低的值可能足以使磁盘阵列保持忙碌。高于使磁盘保持忙碌所需的价值只会导致额外的 CPU 开销。SSD 和其他基于内存的存储通常可以处理许多并发请求,因此最佳值可能在数百个范围内。

异步 I/O 依赖于有效的 posix_fadvise 函数,而某些操作系统没有此函数。如果不存在此函数,则将此参数设置为非零值将导致错误。在某些操作系统(例如 Solaris)上,此函数存在但实际上不执行任何操作。

在受支持的系统上,默认值为 1,否则为 0。可以通过设置同名表空间参数来覆盖特定表空间中的表的值(请参阅 ALTER TABLESPACE)。

maintenance_io_concurrency (integer) #

类似于 effective_io_concurrency,但用于代表许多客户端会话执行的维护工作。

在受支持的系统上,默认值为 10,否则为 0。可以通过设置同名表空间参数来覆盖特定表空间中的表的值(请参阅 ALTER TABLESPACE)。

max_worker_processes (integer) #

设置系统可支持的后台进程的最大数量。此参数只能在服务器启动时设置。默认值为 8。

在运行备用服务器时,您必须将此参数设置为与主服务器上相同或更高的值。否则,将不允许在备用服务器中进行查询。

更改此值时,还要考虑调整 max_parallel_workersmax_parallel_maintenance_workersmax_parallel_workers_per_gather

max_parallel_workers_per_gather (integer) #

设置单个 GatherGather Merge 节点可以启动的最大工作程序数量。并行工作程序取自由 max_worker_processes 建立的进程池,受 max_parallel_workers 限制。请注意,请求的工作程序数量在运行时可能实际上不可用。如果发生这种情况,该计划将以少于预期的工作程序运行,这可能是低效的。默认值为 2。将此值设置为 0 将禁用并行查询执行。

请注意,并行查询可能消耗比非并行查询多得多的资源,因为每个工作进程都是一个完全独立的进程,对系统的影响与一个附加用户会话大致相同。在选择此设置的值以及配置控制资源利用率的其他设置(如 work_mem)时,应考虑这一点。诸如 work_mem 之类的资源限制会单独应用于每个工作进程,这意味着所有进程的总利用率可能比任何单个进程的正常利用率高得多。例如,使用 4 个工作进程的并行查询可能比根本不使用工作进程的查询使用多达 5 倍的 CPU 时间、内存、I/O 带宽等。

有关并行查询的更多信息,请参阅 第 15 章

max_parallel_maintenance_workers (integer) #

设置单个实用程序命令可以启动的最大并行工作进程数。目前,支持使用并行工作进程的并行实用程序命令仅为 CREATE INDEX(仅在构建 B 树索引时)和不带 FULL 选项的 VACUUM。并行工作进程取自由 max_worker_processes 建立的进程池,受 max_parallel_workers 限制。请注意,请求的工作进程数在运行时可能实际上不可用。如果发生这种情况,实用程序操作将以少于预期的工作进程运行。默认值为 2。将此值设置为 0 将禁用实用程序命令使用并行工作进程。

请注意,并行实用程序命令消耗的内存不应比等效的非并行操作多。此策略不同于并行查询,其中资源限制通常适用于每个工作进程。并行实用程序命令将资源限制 maintenance_work_mem 视为要应用于整个实用程序命令的限制,而不管并行工作进程的数量如何。但是,并行实用程序命令仍然可能消耗大量 CPU 资源和 I/O 带宽。

max_parallel_workers (integer) #

设置系统可支持的用于并行操作的最大工作进程数。默认值为 8。在增加或减少此值时,还要考虑调整 max_parallel_maintenance_workersmax_parallel_workers_per_gather。此外,请注意,高于 max_worker_processes 的此值设置不会产生任何效果,因为并行工作进程是从该设置建立的工作进程池中获取的。

parallel_leader_participation (boolean) #

允许领导进程在 GatherGather Merge 节点下执行查询计划,而不是等待工作进程。默认值为 on。将此值设置为 off 可降低工作进程因领导进程读取元组不够快而被阻塞的可能性,但要求领导进程等待工作进程启动,然后才能生成第一个元组。领导进程可以帮助或阻碍性能的程度取决于计划类型、工作进程数量和查询持续时间。

old_snapshot_threshold (integer) #

设置查询快照可使用的最短时间,而不会在使用快照时出现 快照过旧 错误的风险。已死亡超过此阈值的数据允许被真空吸走。这有助于防止长期使用快照而产生的膨胀。为了防止由于清理本来对快照可见的数据而导致结果不正确,当快照早于此阈值并且快照用于读取自构建快照以来已修改的页面时,将生成错误。

如果此值未指定单位,则以分钟为单位。值为 -1(默认值)禁用此功能,实际上将快照年龄限制设置为无限。此参数只能在服务器启动时设置。

生产工作中有用值可能从几个小时到几天不等。小值(例如 01min)仅允许使用,因为它们有时可能对测试有用。虽然允许设置高达 60d,但请注意,在许多工作负载中,极端膨胀或事务 ID 环绕可能在更短的时间内发生。

启用此功能后,无法将关系末尾的释放空间释放给操作系统,因为这可能会删除检测 快照太旧 条件所需的信息。分配给关系的所有空间都将与该关系关联,仅在该关系内重复使用,除非显式释放(例如,使用 VACUUM FULL)。

此设置不会尝试保证在任何特定情况下都会生成错误。事实上,如果可以从(例如)已实现结果集的游标生成正确的结果,即使引用的表中的基础行已被清除,也不会生成错误。某些表无法安全地提前清除,因此不会受到此设置的影响,例如系统目录。对于此类表,此设置既不会减少膨胀,也不会在扫描时产生 快照太旧 错误的可能性。