F.37. pg_walinspect — просмотр журнала предзаписи на низком уровне #

Модуль pg_walinspect предоставляет SQL-функции для просмотра журнала предзаписи на низком уровне. Он работает с запущенным кластером баз данных PostgreSQL и может быть полезен для целей отладки, анализа, отчётности или обучения. Модуль похож на pg_waldump, но работает через SQL, а не как отдельная утилита.

Все функции этого модуля выдают информацию из WAL, относящуюся к текущей линии времени сервера.

Примечание

Функции pg_walinspect зачастую вызываются с аргументом LSN, который задаёт начало интересующей записи WAL. Тем не менее некоторые функции, например pg_logical_emit_message, возвращают LSN после только что добавленной записи.

Подсказка

Все функции pg_walinspect, которые показывают информацию о записях, попадающих в определённый диапазон значений LSN, могут принимать конечные_lsn после текущего LSN сервера. При использовании конечного_lsn «из будущего» ошибки не возникнет.

Может быть удобным указать значение FFFFFFFF/FFFFFFFF (максимально допустимое значение pg_lsn) в качестве аргумента конечного_lsn. Это аналогично варианту указать конечный_lsn, совпадающий с текущим LSN сервера.

По умолчанию использовать эти функции разрешено только суперпользователям и ролям, включённым в роль pg_read_server_files. Суперпользователь может дать доступ другим, воспользовавшись командой GRANT.

F.37.1. Функции общего назначения #

pg_get_wal_record_info(in_lsn pg_lsn) returns record #

Получает информацию о записи WAL, которая расположена по заданному_lsn или после него. Например:

postgres=# SELECT * FROM pg_get_wal_record_info('0/E419E28');
-[ RECORD 1 ]----+-------------------------------------------------
start_lsn        | 0/E419E28
end_lsn          | 0/E419E68
prev_lsn         | 0/E419D78
xid              | 0
resource_manager | Heap2
record_type      | VACUUM
record_length    | 58
main_data_length | 2
fpi_length       | 0
description      | nunused: 5, unused: [1, 2, 3, 4, 5]
block_ref        | blkref #0: rel 1663/16385/1249 fork main blk 364

Если заданный_lsn не находится в начале записи WAL, будет показана информация о следующей корректной записи WAL. Если такой записи WAL нет, функция выдаст ошибку.

pg_get_wal_records_info(start_lsn pg_lsn, end_lsn pg_lsn) returns setof record #

Получает информацию обо всех корректных записях WAL между начальным_lsn и конечным_lsn. Возвращает одну строку для каждой записи WAL. Пример использования функции:

postgres=# SELECT * FROM pg_get_wal_records_info('0/1E913618', '0/1E913740') LIMIT 1;
-[ RECORD 1 ]----+--------------------------------------------------------------
start_lsn        | 0/1E913618
end_lsn          | 0/1E913650
prev_lsn         | 0/1E9135A0
xid              | 0
resource_manager | Standby
record_type      | RUNNING_XACTS
record_length    | 50
main_data_length | 24
fpi_length       | 0
description      | nextXid 33775 latestCompletedXid 33774 oldestRunningXid 33775
block_ref        |

Функция выдаёт ошибку, если начальный_lsn недоступен.

pg_get_wal_block_info(start_lsn pg_lsn, end_lsn pg_lsn, show_data boolean DEFAULT true) returns setof record #

Получает информацию о каждой ссылке на блок из всех корректных записей WAL между начальным_lsn и конечным_lsn с одной или более ссылок на блок. Возвращает одну строку для ссылки на блок для каждой записи WAL. Например:

postgres=# SELECT * FROM pg_get_wal_block_info('0/1230278', '0/12302B8');
-[ RECORD 1 ]-----+-----------------------------------
start_lsn         | 0/1230278
end_lsn           | 0/12302B8
prev_lsn          | 0/122FD40
block_id          | 0
reltablespace     | 1663
reldatabase       | 1
relfilenode       | 2658
relforknumber     | 0
relblocknumber    | 11
xid               | 341
resource_manager  | Btree
record_type       | INSERT_LEAF
record_length     | 64
main_data_length  | 2
block_data_length | 16
block_fpi_length  | 0
block_fpi_info    |
description       | off: 46
block_data        | \x00002a00070010402630000070696400
block_fpi_data    |

В этом примере рассмотрена запись WAL, содержащая только одну ссылку на блок, однако во многих записях WAL таких ссылок несколько. Строки, возвращаемые функцией pg_get_wal_block_info, будут гарантированно иметь уникальную комбинацию начального_lsn и id_блока.

Большая часть показанной здесь информации совпадает с выводом функции pg_get_wal_records_info, при условии передачи одинаковых аргументов. Однако pg_get_wal_block_info выводит информацию из каждой записи WAL в расширенном виде, добавляя в вывод по одной строке для каждой ссылки на блок, поэтому некоторые детали отслеживаются на уровне ссылки на блок, а не на уровне целой записи. Такая структура полезна при работе с запросами, которые отслеживают изменение отдельных блоков с течением времени. Обратите внимание, что для записей без ссылок на блоки (например, записи WAL для COMMIT), строки возвращаться не будут, поэтому функция pg_get_wal_block_info действительно может возвращать меньше строк, чем функция pg_get_wal_records_info.

Параметры reltablespace, reldatabase и relfilenode ссылаются на pg_tablespace.oid, pg_database.oid и pg_class.relfilenode соответственно. Поле relforknumber обозначает номер слоя в отношении для ссылки на блок (за подробностями обратитесь к common/relpath.h).

Подсказка

Функция pg_filenode_relation (см. Таблицу 9.97) позволяет определить, какое отношение было изменено первоначально.

Клиенты могут избежать издержек материализации данных блока, что может существенно ускорить выполнение функции. Когда для show_data задано значение false, значения block_data и block_fpi_data опускаются (то есть выходные аргументы block_data и block_fpi_data принимают значение NULL для всех возвращаемых строк). Очевидно, что подобная оптимизация осуществима только для запросов, которым на самом деле не требуются данные блоков.

Функция выдаёт ошибку, если начальный_lsn недоступен.

pg_get_wal_stats(start_lsn pg_lsn, end_lsn pg_lsn, per_record boolean DEFAULT false) returns setof record #

Выдаёт статистику по всем корректным записям WAL между начальным_lsn и конечным_lsn. По умолчанию возвращает одну строку для каждого типа менеджера_ресурсов (resource_manager). Когда по_типу_записи имеет значение true, то возвращает отдельные строки для разных типов_записей (record_type). Пример использования функции:

postgres=# SELECT * FROM pg_get_wal_stats('0/1E847D00', '0/1E84F500')
             WHERE count > 0 AND
                   "resource_manager/record_type" = 'Transaction';
             LIMIT 1;
-[ RECORD 1 ]----------------+-------------------
resource_manager/record_type | Transaction
count                        | 2
count_percentage             | 8
record_size                  | 875
record_size_percentage       | 41.23468426013195
fpi_size                     | 0
fpi_size_percentage          | 0
combined_size                | 875
combined_size_percentage     | 2.8634072910530795

Функция выдаёт ошибку, если начальный_lsn недоступен.

F.37.2. Автор #

Бхарат Рупиредди (Bharath Rupireddy)