暂无图片
暂无图片
暂无图片
暂无图片
暂无图片

[译文] PostgreSQL :通过 pg_buffercache 检查内存

原创 Luca Ferrari 2021-08-20
1447

pg_buffercache是一个非常有用的扩展,允许检查实时 PostgreSQL 实例使用的内存。该扩展可通过 contrib 模块使用,对于查看内存使用情况非常有用,即shared_buffers.
由于这个模块,可以清楚地了解内存消耗,从而正确调整shared_buffers参数。

几年前,我编写了一组示例查询来与模块交互并查看内存使用情况。虽然这些查询是一个起点,但它们有一些问题,尤其是当表不消耗内存时(disibion​​ 为零,等等)。

我终于找到时间为这些查询生成更清晰的方法,因此我通过函数重新实现了所有查询。该脚本是一个psql脚本,使用了一些特殊的反斜杠命令,但是您可以提取SQL纯部分并通过另一个客户端执行它。

该脚本创建一个memory模式并将所有功能放入该模式中;函数的名称以 开头f_memory,因此它们不应与现有函数发生冲突。

下面我将描述每个功能。

请注意,这里的想法是提供有关内存检查的背景知识,仍有改进和修复的空间!

安装功能

执行memory.sqlpsql 脚本就足以创建模式memory并将所有功能放入该模式中。该脚本提供了有关创建的对象的一些信息:

通过 pg_buffercache 检查内存 pg_buffercache是一个非常有用的扩展,允许检查实时 PostgreSQL 实例使用的内存。该扩展可通过 contrib 模块使用,对于查看内存使用情况非常有用,即shared_buffers. 由于这个模块,可以清楚地了解内存消耗,从而正确调整shared_buffers参数。 几年前,我编写了一组示例查询来与模块交互并查看内存使用情况。虽然这些查询是一个起点,但它们有一些问题,尤其是当表不消耗内存时(disibion​​ 为零,等等)。 我终于找到时间为这些查询生成更清晰的方法,因此我通过函数重新实现了所有查询。该脚本是一个psql脚本,使用了一些特殊的反斜杠命令,但是您可以提取SQL纯部分并通过另一个客户端执行它。 该脚本创建一个memory模式并将所有功能放入该模式中;函数的名称以 开头f_memory,因此它们不应与现有函数发生冲突。 下面我将描述每个功能。 请注意,这里的想法是提供有关内存检查的背景知识,仍有改进和修复的空间! 安装功能 执行memory.sqlpsql 脚本就足以创建模式memory并将所有功能放入该模式中。该脚本提供了有关创建的对象的一些信息: tfdb=# \i memory.sql Creating a schema named memory... All objects created! Try one of the following functions: - memory.f_memory() to get very basic information - memory.f_memory_usage() to get information about the whole memory - memory.f_memory_usage_by_database() to get information about single databases - memory.f_memory_usage_by_table() to get information about tables in the current database - memory.f_memory_usage_by_table_cumulative() to get cumulative information for tables You can add the memory schema to the search path. Try running the following query while testing the database (e.g., via pgbench): select memory.f_memory_usage(); \watch 5

函数的输出

所有函数都接受一个布尔human标志,默认情况下设置为true. 如果设置了该标志,则内存维度的输出将使用 格式化pg_size_pretty(),因此将采用人类可读的格式。否则,输出将被格式化为纯字节数。

tfdb=# \i memory.sql Creating a schema named memory... All objects created! Try one of the following functions: - memory.f_memory() to get very basic information - memory.f_memory_usage() to get information about the whole memory - memory.f_memory_usage_by_database() to get information about single databases - memory.f_memory_usage_by_table() to get information about tables in the current database - memory.f_memory_usage_by_table_cumulative() to get cumulative information for tables You can add the memory schema to the search path. Try running the following query while testing the database (e.g., via pgbench): select memory.f_memory_usage(); \watch 5

函数的输出

所有函数都接受一个布尔human标志,默认情况下设置为true. 如果设置了该标志,则内存维度的输出将使用 格式化pg_size_pretty(),因此将采用人类可读的格式。否则,输出将被格式化为纯字节数。

tfdb=# select * from memory.f_memory(); total | used | free --------|--------|-------- 800 MB | 101 MB | 699 MB (1 row) tfdb=# select * from memory.f_memory( false ); total | used | free -----------|-----------|----------- 838860800 | 106168320 | 732692480 (1 row)

实用功能

  • 有一些实用函数用作构建其他函数的主干。特别是:
  • memory.f_check_pg_buffercache()它检查扩展pg_buffercache是否安装到数据库中;
  • memory.f_check_user()检查用户是管理员还是具有运行pg_buffercache功能的权限;
  • memory.f_check()调用前两个函数并在检查失败时引发异常。此函数由所有其他与内存相关的函数调用,因此在运行该函数之前,用户可以获得有关丢失碎片的警报;
  • memory.f_usagecounter_to_string()提供pg_buffercache.usagecount值的文本描述;
  • memory.f_tablename() 提供将出现在其他函数输出中的任何表、索引或视图的名称;
  • memory.f_print_bytes()使用pg_size_pretty()文本或纯文本转换将字节数打印为文本。这用于每个函数以支持上述human标志。

可用功能

下面描述了用于检查内存使用情况的可用函数。

f_memory()

该函数memory.f_memory()提供集群中空闲和已用内存的概览。

通过 pg_buffercache 检查内存 pg_buffercache是一个非常有用的扩展,允许检查实时 PostgreSQL 实例使用的内存。该扩展可通过 contrib 模块使用,对于查看内存使用情况非常有用,即shared_buffers. 由于这个模块,可以清楚地了解内存消耗,从而正确调整shared_buffers参数。 几年前,我编写了一组示例查询来与模块交互并查看内存使用情况。虽然这些查询是一个起点,但它们有一些问题,尤其是当表不消耗内存时(disibion​​ 为零,等等)。 我终于找到时间为这些查询生成更清晰的方法,因此我通过函数重新实现了所有查询。该脚本是一个psql脚本,使用了一些特殊的反斜杠命令,但是您可以提取SQL纯部分并通过另一个客户端执行它。 该脚本创建一个memory模式并将所有功能放入该模式中;函数的名称以 开头f_memory,因此它们不应与现有函数发生冲突。 下面我将描述每个功能。 请注意,这里的想法是提供有关内存检查的背景知识,仍有改进和修复的空间! 安装功能 执行memory.sqlpsql 脚本就足以创建模式memory并将所有功能放入该模式中。该脚本提供了有关创建的对象的一些信息: tfdb=# \i memory.sql Creating a schema named memory... All objects created! Try one of the following functions: - memory.f_memory() to get very basic information - memory.f_memory_usage() to get information about the whole memory - memory.f_memory_usage_by_database() to get information about single databases - memory.f_memory_usage_by_table() to get information about tables in the current database - memory.f_memory_usage_by_table_cumulative() to get cumulative information for tables You can add the memory schema to the search path. Try running the following query while testing the database (e.g., via pgbench): select memory.f_memory_usage(); \watch 5 函数的输出 所有函数都接受一个布尔human标志,默认情况下设置为true. 如果设置了该标志,则内存维度的输出将使用 格式化pg_size_pretty(),因此将采用人类可读的格式。否则,输出将被格式化为纯字节数。 tfdb=# select * from memory.f_memory(); total | used | free --------|--------|-------- 800 MB | 101 MB | 699 MB (1 row) tfdb=# select * from memory.f_memory( false ); total | used | free -----------|-----------|----------- 838860800 | 106168320 | 732692480 (1 row) 实用功能 有一些实用函数用作构建其他函数的主干。特别是: memory.f_check_pg_buffercache()它检查扩展pg_buffercache是否安装到数据库中; memory.f_check_user()检查用户是管理员还是具有运行pg_buffercache功能的权限; memory.f_check()调用前两个函数并在检查失败时引发异常。此函数由所有其他与内存相关的函数调用,因此在运行该函数之前,用户可以获得有关丢失碎片的警报; memory.f_usagecounter_to_string()提供pg_buffercache.usagecount值的文本描述; memory.f_tablename() 提供将出现在其他函数输出中的任何表、索引或视图的名称; memory.f_print_bytes()使用pg_size_pretty()文本或纯文本转换将字节数打印为文本。这用于每个函数以支持上述human标志。 可用功能 下面描述了用于检查内存使用情况的可用函数。 f_memory() 该函数memory.f_memory()提供集群中空闲和已用内存的概览。 tfdb=# select * from memory.f_memory(); total | used | free --------|--------|-------- 800 MB | 163 MB | 637 MB (1 row)

f_memory_usage()

该函数memory.f_memory_usage()提供了有关内存使用情况的更详细视图。特别是它提供了级别使用的内存量usagecount。

tfdb=# select * from memory.f_memory_usage(); total_memory | memory | percent | cumulative | description --------------|---------|---------|------------|---------------- 800 MB | 22 MB | 2.71 % | 2.71% | VERY HIGH (5) 800 MB | 2536 kB | 0.31 % | 3.02% | HIGH (4) 800 MB | 1936 kB | 0.24 % | 3.26% | MID (3) 800 MB | 1888 kB | 0.23 % | 3.49% | LOW (2) 800 MB | 135 MB | 16.85 % | 20.34% | VERY LOW (1) 800 MB | 637 MB | 79.66 % | 100.00% | == FREE == (0) (6 rows)

的memory列提供的存储器用于特定量区域,并且percent列提供的内存使用情况的比例相对于总存储器。该cumulative列提供了使用级别大于当前级别的金额比例。

举个例子,上面有135 MB不经常使用的,因此20.34 %内存的使用从很高到很低。

f_memory_usage_by_database()

该函数memory.f_memory_usage_by_database()提供有关集群中每个数据库的内存使用情况的信息,还提供每个数据库的缓存量。

pgbench=# select * from memory.f_memory_usage_by_database(); total_memory | database | size_in_memory | size_on_disk | percent_cached | percent_of_memory --------------|-------------|----------------|--------------|----------------|------------------- 256 MB | pgbench | 182 MB | 1505 MB | 12.11% | 71.15% 256 MB | ltdb | 608 kB | 171 MB | 0.35% | 0.23% 256 MB | postgres | 544 kB | 104 MB | 0.51% | 0.21% 256 MB | restore | 544 kB | 104 MB | 0.51% | 0.21% 256 MB | restore2 | 544 kB | 104 MB | 0.51% | 0.21% 256 MB | restore3 | 544 kB | 104 MB | 0.51% | 0.21% 256 MB | restore4 | 544 kB | 8269 kB | 6.58% | 0.21% 256 MB | template1 | 544 kB | 8245 kB | 6.60% | 0.21% (8 rows)

f_memory_usage_by_table()

该函数memory.f_memory_usage_by_table()提供有关所有类似表格的东西的用法的信息,换句话说就是关于关系。

tfdb=# select * from memory.f_memory_usage_by_table(); ... 800 MB | tfdb | (table) respi.y2019m12 | 8192 bytes | 0.00 % | VERY HIGH (5) 800 MB | tfdb | (table) respi.y2019m12 | 22 MB | 2.70 % | VERY VERY LOW (0) 800 MB | tfdb | (index) respi.y2019m12_ts_idx | 32 kB | 0.00 % | VERY HIGH (5) 800 MB | tfdb | (index) respi.y2019m12_ts_idx1 | 8192 bytes | 0.00 % | VERY HIGH (5)

f_memory_usage_by_table_cumulative()

该函数f_memory_usage_by_table_cumulative()提供了单个表“消耗”了多少内存的概览,而不考虑使用级别计数器。

tfdb=# select * from memory.f_memory_usage_by_table_cumulative(); -[ RECORD 1 ]-----|----------------------------------------------- total_memory | 800 MB database | tfdb relation | (table) respi.y2019m07 memory | 10 MB on_disk | 1159 MB percent_of_memory | 1.27 % percent_of_disk | 0.88% usagedescription | any -[ RECORD 2 ]-----|----------------------------------------------- total_memory | 800 MB database | tfdb relation | (table) respi.y2019m06 memory | 10 MB on_disk | 1156 MB percent_of_memory | 1.26 % percent_of_disk | 0.87% usagedescription | any ...

该函数接受通常的human参数,但也接受一个整数可选参数,表示您感兴趣的使用计数器。指定时,该函数将仅显示使用的内存量与更大或相等的使用计数器。

tfdb=# select * from memory.f_memory_usage_by_table_cumulative( 5 ); -[ RECORD 1 ]-----|----------------------------------------------- total_memory | 800 MB database | tfdb relation | (table) respi.y2019m07 memory | 8192 bytes on_disk | 1159 MB percent_of_memory | 0.00 % percent_of_disk | 0.00% usagedescription | >= VERY HIGH (5) -[ RECORD 2 ]-----|----------------------------------------------- total_memory | 800 MB database | tfdb relation | (table) respi.y2019m06 memory | 8192 bytes on_disk | 1156 MB percent_of_memory | 0.00 % percent_of_disk | 0.00% usagedescription | >= VERY HIGH (5) ...

结论

上述函数集可用作构建您自己的查询集以检查实时 PostgreSQL 集群的内存使用情况的起点。仍有改进和减少代码重复的空间,敬请期待其他版本!

「喜欢这篇文章,您的关注和赞赏是给作者最好的鼓励」
关注作者
【版权声明】本文为墨天轮用户原创内容,转载时必须标注文章的来源(墨天轮),文章链接,文章作者等基本信息,否则作者和墨天轮有权追究责任。如果您发现墨天轮中有涉嫌抄袭或者侵权的内容,欢迎发送邮件至:contact@modb.pro进行举报,并提供相关证据,一经查实,墨天轮将立刻删除相关内容。

评论