LWLock:pg_stat_statements - Amazon Relational Database Service

LWLock:pg_stat_statements

pg_stat_statements 扩展对跟踪 SQL 语句的哈希表进行独占锁定时,就会发生 LWLock:pg_stat_statements 等待事件。如果存在以下情形,可能会发生这种情况:

  • 当跟踪的语句数量达到配置的 pg_stat_statements.max 参数值,并且需要为更多条目腾出空间时,此扩展会对调用次数执行排序,移除 5% 的执行次数最少的语句,然后用剩余的条目重新填充哈希表。

  • pg_stat_statements 对磁盘上的 pgss_query_texts.stat 文件执行 garbage collection 操作并重新写入该文件时。

支持的引擎版本

RDS for PostgreSQL 的所有版本均支持此等待事件信息。

上下文

了解 pg_stat_statements 扩展:pg_stat_statements 扩展在哈希表中跟踪 SQL 语句执行统计数据。该扩展可跟踪 SQL 语句,直至达到由 pg_stat_statements.max 参数定义的限制。此参数确定可以跟踪的最大语句数,该数量对应于 pg_stat_statements 视图中的最大行数。

语句统计数据持久性:该扩展通过以下方式,在实例重新启动时持久保留语句统计数据:

  • 将数据写入名为 pg_stat_statements.stat 的文件

  • 使用 pg_stat_statements.save 参数来控制持久行为

当 pg_stat_statements.save 设为以下设置时:

  • 开启(默认):关闭时保存统计数据,并在服务器启动时重新加载它们

  • 关闭:既不会在服务器关闭时保存统计数据,也不会在服务器启动时重新加载它们

查询文本存储:该扩展将所跟踪的查询的文本存储在一个名为 pgss_query_texts.stat 的文件中。在进行垃圾回收之前,该文件可以增长到所有跟踪的 SQL 语句平均大小的两倍。该扩展需要在清理操作和重新写入 pgss_query_texts.stat 文件期间对哈希表实施独占锁定。

语句取消分配流程:当所跟踪语句的数量达到 pg_stat_statements.max 限制并且需要跟踪新的语句时,此扩展会:

  • 对哈希表实施独占锁定(LWLock:pg_stat_statements)。

  • 将现有数据加载到本地内存中。

  • 根据调用次数执行快速排序。

  • 移除调用次数最少的语句(底部 5%)。

  • 用剩余的条目重新填充哈希表。

监控语句取消分配:在 PostgreSQL 14 及更高版本中,可以使用 pg_stat_statements_info 视图来监控语句取消分配。此视图包括一个 dealloc 列,该列显示对语句取消分配来为新语句腾出空间的次数

如果频繁地对语句取消分配,则会导致更频繁地对磁盘上的 pgss_query_texts.stat 文件进行垃圾回收。

等待次数增加的可能原因

LWLock:pg_stat_statements 等待次数增加的典型原因包括:

  • 应用程序使用的唯一查询的数量有所增加。

  • 与正在使用的唯一查询的数量相比,pg_stat_statements.max 参数值较小。

操作

根据等待事件的原因,我们建议采取不同的操作。可以通过使用 Amazon RDS 性能详情或查询视图 pg_stat_activity 来识别 LWLock:pg_stat_statements 事件。

调整以下 pg_stat_statements 参数,以控制跟踪行为并减少 LWLock:pg_stat_ statements 等待事件。

禁用 pg_stat_statements.track 参数

如果 LWLock:pg_stat_statements 等待事件对数据库性能产生不利影响,并且在进一步分析 pg_stat_statements 视图以确定根本原因之前需要快速的解决方案,则可以通过将 pg_stat_statements.track 参数设置为 none 来禁用该参数。这将禁用对语句统计数据的回收。

提高 pg_stat_statements.max 参数的值

要减少取消分配并最大限度地减少磁盘上 pgss_query_texts.stat 文件的垃圾回收,请提高 pg_stat_statements.max 参数的值。默认值为 5,000

注意

pg_stat_statements.max 参数为静态参数。必须重新启动数据库实例,才能应用对此参数的任何更改。

禁用 pg_stat_statements.track_utility 参数

您可以分析 pg_stat_statements 视图,以确定哪些实用程序命令正在消耗由 pg_stat_statements 跟踪的大部分资源。

pg_stat_statements.track_utility 参数控制模块是否跟踪实用程序命令,包括除 SELECT、INSERT、UPDATE、DELETE 和 MERGE 之外的所有命令。默认情况下,此参数设置为 on

例如,当应用程序使用许多本质上为唯一的保存点查询时,它可能会增加语句取消分配。要解决此问题,您可以禁用 pg_stat_statements.track_utility 参数以停止 pg_stat_statements 跟踪保存点查询。

注意

pg_stat_statements.track_utility 参数是一个动态参数。无需重新启动数据库实例即可更改其值。

例 pg_stat_statements 中的唯一保存点查询示例
query | queryid -------------------------------------------------+--------------------- SAVEPOINT JDBC_SAVEPOINT_495701 | -7249565344517699703 SAVEPOINT JDBC_SAVEPOINT_1320 | -1572997038849006629 SAVEPOINT JDBC_SAVEPOINT_26739 | 54791337410474486 SAVEPOINT JDBC_SAVEPOINT_1294466 | 8170064357463507593 ROLLBACK TO SAVEPOINT JDBC_SAVEPOINT_65016 | -33608214779996400 SAVEPOINT JDBC_SAVEPOINT_14185 | -2175035613806809562 SAVEPOINT JDBC_SAVEPOINT_45837 | -6201592986750645383 SAVEPOINT JDBC_SAVEPOINT_1324 | 6388797791882029332

PostgreSQL 17 引入了多项增强功能来进行实用程序命令跟踪:

  • 保存点名称现在显示为常量。

  • 现在,两阶段提交命令的全局事务 ID(GID)显示为常量。

  • DEALLOCATE 语句的名称显示为常量。

  • CALL 参数现在显示为常量。