Механизм получения bind-переменных завершенных запросов из представления БД
Функциональность доступна только для редакций Enterprise и Enterprise для ERP-систем.
При переходе от редакции Standard к Enterprise параметры становятся доступными для изменения. При обратном переходе параметры блокируются, значения парамеров конфигурации сбрасываются в состояние по умолчанию.
При завершении действия лицензии c типом Trial механизм автоматически прекращает дублирование логов. Все новые параметры возвращаются к значениям по умолчанию, файлы закрываются. При попытке изменения параметров без лицензии будет выведено предупреждение, параметры будут сброшены.
В случае деградации производительности SQL-запросов, которая может быть связана с аномальным значением переменной запроса, происходит логирование информации о запросах в лог СУБД при превышении времени выполнения запросов, установленного параметром log_min_duration_statement.
Описание
Оригинальный PostgreSQL не предоставляет возможности онлайн-мониторинга bind-переменных активных запросов через системные представления в связи с архитектурными ограничениями. Для анализа используются механизмы логирования, однако основной лог СУБД перегружен событиями аудита, аутентификации и активностью бэкенд-процессов, что затрудняет навигацию и поиск запросов с длительным временем выполнения.
В рамках данной функциональности в Pangolin реализовано дублирование записей из основного лога в отдельный лог-файл. В новый файл выводятся только SQL-запросы, превысившие значение параметра log_min_duration_statement, а также протоколы модуля auto_explain. Это позволяет упростить анализ деградирующих запросов и их параметров.
Новый механизм логирования работает через процесс sys_logger совместно с обычным логированием, требует включенную настройку logging_collector = on. Формат записей в новом логе полностью соответствует формату стандартного лога Pangolin, при этом каждая запись обязательно содержит текст запроса.
Виды сообщений, попадающих в лог:
- выполнение запросов в режиме
Simple query; - выполнение каждого шага отдельно в режиме
Extended:parse,bind,execute; - выполнение функций для работы с большим объемом данных по протоколу
fastpath(функции с приставкойlo_); - вывод
auto_explain.
При сбое записи (например, удаление файла, запрет доступа) механизм автоматически пытается пересоздать файл и продолжить запись, при этом теряется не более одной записи. Сообщения о сбое фиксируются в stderr.
Настройка
Добавлена настройка, позволяющая продублировать сообщения, вызываемые длительностью каждого завершенного оператора в журнал, если оператор выполнялся не менее указанного времени.
Конфигурационные параметры
Реализованы следующие новые конфигурационные параметры:
| Название параметра | Тип | Значение по умолчанию | Допустимые значения | Описание |
|---|---|---|---|---|
log_sql_dedicated_enable | boolean | off | on/off | Включение или отключение механизма дублирования логов |
log_sql_directory | string | /pgerrorlogs | - | Каталог для сохранения файлов лога. Если задана пустая строка, то файлы логов будут создаваться в каталоге по умолчанию – /pgerrorlogs |
log_sql_filename | string | log_duration_statement-%Y-%m-%d_%H%M%S.log | - | Шаблон имен файлов лога. Поддерживает спецпоследовательности как в log_filename |
log_sql_rotation_size | integer | 0 | 0 - 2097151 (КБ) | Максимальный размер файла лога, при достижении которого создается новый файл. Значение 0 отключает ротацию по размеру |
log_sql_rotation_age | integer | 1440 (1 день) | 0 - 35791394 (минуты) | Максимальное время жизни файла лога в минутах, по истечении создается новый файл. Если параметр равен 0, создание новых файлов журналов по времени отключается |
log_sql_truncate_on_rotation | boolean | off | on/off | Управление перезаписью файлов журналов при переключении записи на уже существующий файл журнала. Если значение параметра off, запись продолжается в конец файла. Параметр учитывается только при ротации по времени |
log_sql_file_mode | integer | 0600 | 0 - 511 | Определение прав на создаваемый файл лога |
log_sql_method | string | stderr | stderr, csvlog, jsonlog, syslog | Метод протоколирования сообщений. Указывается один или несколько методов протоколирования, разделенных запятыми |
Также существуют неизмененные конфигурационные параметры, от которых зависит работа новых функций:
logging_collector;log_transaction_sample_rate;log_timezone;log_statement_sample_rate;log_min_duration_statement;log_min_duration_sample.
Подробнее о данных параметрах в интегрированной переведенной документации PostgreSQL, в разделе «Отчетность и ведение журнала сообщений» документа «Программирование и администрирование сервера PostgreSQL».
Управление
Включение функциональности
Для включения необходимо активировать следующие параметры в конфигурационном файле (postgresql.conf/postgres.yml):
log_sql_dedicated_enable = on;logging_collector = on.
После изменения требуется перечитать конфигурацию (pg_reload_conf()) или перезапустить сервер.
Область применения переменных – на весь кластер.
При включении механизма, часть сообщений обычного лога будет продублирована в новый настроенный файл, но только в части сообщений, которые превысили время выполнения (log_min_duration_statement/log_min_duration_sample + log_statement_sample_rate) или выводятся с помощью настройки log_transaction_sample_rate.
Ограничения функциональности
Формирование записей логов выполняется только после завершения оператора, так как именно в этот момент доступна информация о его длительности для оценивания. В отличие от стандартного лога, где наличие текста запроса (statement:) зависит от параметра log_min_error_statement, в новом логе текст SQL-запроса всегда включается в запись. Сообщения, сформированные только по log_min_error_statement, в отдельный лог не попадают.
Правила маскирования и формат сообщений полностью соответствуют стандартному журналированию, дополнительных различий нет.
Логирование
В рамках данной доработки реализован механизм защиты файлов журналов (как нового, так и основного). Ранее, если файл журнала был недоступен для записи (например, удален, поврежден, запрещена запись в файл), журналирование могло полностью остановиться до следующей ротации, а в некоторых случаях — прекратиться окончательно. Теперь при сбое записи процесс логирования автоматически пытается пересоздать файл (в режиме append), назначить ему права доступа и продолжить работу. В результате потеряется только одна запись — та, что вызвала ошибку. Информация о попытках пересоздания файлов фиксируется в stderr.
Права управления
По умолчанию файлы логов доступны только для пользователя ОС, от имени которого запущен сервер СУБД. Права доступа к файлам логов настраиваются параметром log_sql_file_mode. По умолчанию значение параметра 0600.
Отключение функциональности
Для отключения достаточно установить параметр log_sql_dedicated_enable в значение off.
Диагностика
Логируются операции (SQL-запросы или вызовы функций) которые выполнялись дольше, чем установленный лимит времени log_min_duration_statement.
Сообщения, которые могут фиксироваться в логах:
| Формат записи | Описание |
|---|---|
duration: <duration> ms statement: <query> | Выполнение простого SQL-запроса, который не использует механизм подготовленных операторов |
duration: <duration> ms parse <prepared statement>: <query> | Клиентское приложение или команда PREPARE впервые отправляет запрос, который будет использоваться как «подготовленный оператор» |
duration: <duration> ms bind <prepared statement>: <query> | Фаза связывания конкретных значений с ранее подготовленным шаблоном запроса, если используется специфический способ обработки результатов (например, курсоры) |
duration: <duration> ms bind <prepared statement>/<portal name>: <query> | Фаза связывания конкретных значений с ранее подготовленным шаблоном запроса |
duration: <duration> ms execute <prepared statement>: <query> | Операция получения очередной порции результатов (строк данных) из уже запущенного запроса (курсора) |
duration: <duration> ms execute <prepared statement>/<portal name>: <query> | Операция получения очередной порции результатов (строк данных) из уже запущенного запроса (курсора) |
duration: <duration> ms execute fetch from <prepared statement>: <query> | Непосредственное выполнение ранее подготовленного запроса |
duration: <duration> ms execute fetch from <prepared statement>/<portal name>: <query> | Непосредственное выполнение ранее подготовленного запроса |
duration: <duration> ms planning <planning duration> ms plan: <plan> | Процесс выбора оптимального способа выполнения запроса |
duration: <duration> ms fastpath function call: <query> (OID <function OID>) | Прямой вызов встроенной или пользовательской функции (не через SQL-запрос), например, lo_* |
Пример логов:
2025-07-09 10:06:36 MSK [3808975]: [16-1] app=PostgreSQL JDBC Driver,user=postgres,db=postgres,client=<IP-Address>,type=client backend LOG: duration: 0.536 ms parse <unnamed>: prepare sel(int) as select * from tb2 where id = $1
2025-07-09 10:06:36 MSK [3808975]: [17-1] app=PostgreSQL JDBC Driver,user=postgres,db=postgres,client=<IP-Address>,type=client backend LOG: duration: 0.028 ms bind <unnamed>: prepare sel(int) as select * from tb2 where id = $1
2025-07-09 10:06:36 MSK [3808975]: [18-1] app=PostgreSQL JDBC Driver,user=postgres,db=postgres,client=<IP-Address>,type=client backend DETAIL: parameters: $1 = '1'
2025-07-09 10:06:36 MSK [3808975]: [19-1] app=PostgreSQL JDBC Driver,user=postgres,db=postgres,client=<IP-Address>,type=client backend LOG: execute <unnamed>: prepare sel(int) as select * from tb2 where id = $1
2025-07-09 10:06:36 MSK [3808975]: [20-1] app=PostgreSQL JDBC Driver,user=postgres,db=postgres,client=<IP-Address>,type=client backend DETAIL: parameters: $1 = '1'
2025-07-09 10:06:36 MSK [3808975]: [21-1] app=PostgreSQL JDBC Driver,user=postgres,db=postgres,client=<IP-Address>,type=client backend LOG: duration: 0.116 ms
Сценарии использования
Создание лог-файла и регистрация запроса в лог
-
Активируйте функциональность:
ALTER SYSTEM SET log_sql_dedicated_enable = 'on';
ALTER SYSTEM SET log_min_duration_statement = 0;
SELECT pg_reload_conf();Функциональность включена:
ALTER SYSTEM
ALTER SYSTEM -
Выполните запрос:
\o /dev/null
SELECT generate_series(1, 100);
\oЗапрос выполнен.
-
Убедитесь, что лог-файл создан, запись была добавлена в лог:
ls -la /pgerrorlogs
ls -lat /pgerrorlogs | grep 'log_duration_statement' | head -n 1 | awk '{print$9}'
cat /pgerrorlogs/"$(ls -lat /pgerrorlogs | grep 'log_duration_statement' | head -n 1 | awk '{print$9}')"В каталоге
/pgerrorlogsсоздан новый лог-файл, запись с выполненным запросом присутствует:drwxrwx--- 3 postgres pangolin_users 20480 Aug 31 22:12 .
dr-xr-xr-x. 27 root root 4096 Aug 28 19:42 ..
drwxrwx--- 5 postgres pangolin_users 4096 Aug 31 03:31 06
-rw------- 1 postgres postgres 186 Aug 31 22:12 log_duration_statement-2025-08-31_220459.log2025-08-31 22:12:50 MSK [1637036]: [113-1] app=psql,user=postgres,db=postgres,client=<IP-Address>,type=client backend LOG: duration: 0.604 ms statement: SELECT generate_series(1, 100);
Логирование запросов, превышающих log_min_duration_statement
-
Установите значение параметра:
ALTER SYSTEM SET log_min_duration_statement = '3s';
SELECT pg_reload_conf();Значение установлено:
ALTER SYSTEM -
Выполните запрос:
\o /dev/null
SELECT generate_series(1, 50000000);
\oЗапрос выполнен.
-
Убедитесь, что запись была добавлена в лог:
cat /pgerrorlogs/"$(ls -lat /pgerrorlogs | grep 'log_duration_statement' | head -n 1 | awk '{print$9}')"Запись добавлена:
2025-08-31 23:13:17 MSK [1637036]: [125-1] app=psql,user=postgres,db=postgres,client=<IP-Address>,type=client backend LOG: duration: 8385.841 ms statement: SELECT generate_series(1, 50000000);
Выдача прав на файл и протоколирование сообщений
-
Установите значения следующих параметров:
ALTER SYSTEM SET log_sql_file_mode = '0777';
ALTER SYSTEM SET log_sql_method = 'stderr, csvlog, jsonlog';
SELECT pg_reload_conf();Значения установлены:
ALTER SYSTEM
ALTER SYSTEM -
Выполните запрос:
\o /dev/null
SELECT generate_series(1, 200);
\oЗапрос выполнен.
-
Убедитесь, что появились логи форматов
.log,.csv,.jsonи права на файлы изменены:ls -la /pgerrorlogs
ls -lat /pgerrorlogs | grep 'log_duration_statement' | head -n 1 | awk '{print$9}'
cat /pgerrorlogs/"$(ls -lat /pgerrorlogs | grep 'log_duration_statement' | head -n 1 | awk '{print$9}')"Появились новые файлы, права на файл 777, запись добавлена:
drwxrwx--- 3 postgres pangolin_users 20480 Aug 31 23:33 .
dr-xr-xr-x. 27 root root 4096 Aug 28 19:42 ..
drwxrwx--- 5 postgres pangolin_users 4096 Aug 31 03:31 06
-rw------- 1 postgres postgres 43538 Aug 31 23:13 log_duration_statement-2025-08-31_220459.log
-rw------- 1 postgres postgres 943 Aug 31 23:23 log_duration_statement-2025-08-31_231620.log
-rw------- 1 postgres postgres 187 Aug 31 23:24 log_duration_statement-2025-08-31_232400.log
-rw-rw-rw- 1 postgres postgres 263 Aug 31 23:33 log_duration_statement-2025-08-31_233301.csv
-rw-rw-rw- 1 postgres postgres 453 Aug 31 23:33 log_duration_statement-2025-08-31_233301.json
-rw-rw-rw- 1 postgres postgres 186 Aug 31 23:33 log_duration_statement-2025-08-31_233301.logФормат
.csv:2025-08-31 23:33:07.996 MSK,"postgres","postgres",1637036,"<IP-Address>:60560",68b49785.18faac,15,"SELECT",2025-08-31 21:42:13 MSK,7/0,0,LOG,00000,"duration: 0.529 ms statement: SELECT generate_series(1, 200);",,,,,,,,,"psql","client backend",,-85780237804673294Формат
.json:{"timestamp":"2025-08-31 23:33:07.996 MSK","user":"postgres","dbname":"postgres","pid":1637036,"remote_host":"<IP-Address>","remote_port":60560,"session_id":"68b49785.18faac","line_num":11,"ps":"SELECT","session_start":"2025-08-31 21:42:13 MSK","vxid":"7/0","txid":0,"error_severity":"LOG","message":"duration: 0.529 ms statement: SELECT generate_series(1, 200);","application_name":"psql","backend_type":"client backend","query_id":-85780237804673294}Формат
.log:2025-08-31 23:33:07 MSK [1637036]: [206-1] app=psql,user=postgres,db=postgres,client=<IP-Address>,type=client backend LOG: duration: 0.529 ms statement: SELECT generate_series(1, 200); -
Сбросьте значения параметров:
ALTER SYSTEM RESET log_sql_file_mode;
ALTER SYSTEM RESET log_sql_method;
SELECT pg_reload_conf();Значения сброшены:
ALTER SYSTEM
ALTER SYSTEM