From 4b55965fc145d978287c8bd8b79681cf58d4ff24 Mon Sep 17 00:00:00 2001 From: Ubuntu Date: Thu, 18 Sep 2025 15:36:33 +0000 Subject: [PATCH v14] Add tests for temp file logging MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Temporary file usage is sometimes attributed to the wrong query in the logs output. One identified reason is that unnamed portal cleanup (and consequently temp file logging) happens during the next BIND message, after debug_query_string has already been updated to the new query. This commit is a first step towards fixing this, adding tests to track which query is displayed next to the temp file when the portal is dropped. Author: Sami Imseih Author: Frédéric Yhuel Reviewed-by: Mircea Cadariu Discussion: https://www.postgresql.org/message-id/flat/3d07ee43-8855-42db-97e0-bad5db82d972@dalibo.com --- src/test/modules/test_misc/meson.build | 1 + .../modules/test_misc/t/009_log_temp_files.pl | 115 ++++++++++++++++++ 2 files changed, 116 insertions(+) create mode 100644 src/test/modules/test_misc/t/009_log_temp_files.pl diff --git a/src/test/modules/test_misc/meson.build b/src/test/modules/test_misc/meson.build index 6b1e730bf4..f258bf1ccd 100644 --- a/src/test/modules/test_misc/meson.build +++ b/src/test/modules/test_misc/meson.build @@ -17,6 +17,7 @@ tests += { 't/006_signal_autovacuum.pl', 't/007_catcache_inval.pl', 't/008_replslot_single_user.pl', + 't/009_log_temp_files.pl', ], }, } diff --git a/src/test/modules/test_misc/t/009_log_temp_files.pl b/src/test/modules/test_misc/t/009_log_temp_files.pl new file mode 100644 index 0000000000..f5071ebf89 --- /dev/null +++ b/src/test/modules/test_misc/t/009_log_temp_files.pl @@ -0,0 +1,115 @@ +# +# Verify that temporary file usage is logged with the expected statement text +# for various query execution paths (portals, pipelines, cursors, prepared +# statements, etc.). +# +# Copyright (c) 2021-2025, PostgreSQL Global Development Group +# + +use strict; +use warnings FATAL => 'all'; +use PostgreSQL::Test::Cluster; +use PostgreSQL::Test::Utils; +use Test::More; + +# Initialize a new PostgreSQL test cluster +my $node = PostgreSQL::Test::Cluster->new('primary'); +$node->init(); +$node->append_conf( + 'postgresql.conf', qq( +work_mem = 64kB +log_temp_files = 0 +)); +$node->start; + +my $log_offset = -s $node->logfile; + +# Setup table and populate with data +$node->safe_psql("postgres", qq{ +CREATE UNLOGGED TABLE foo(a int); +INSERT INTO foo(a) SELECT * FROM generate_series(1, 5000); +}); + +# unnamed portal test +$node->safe_psql("postgres", qq{ +BEGIN; +SELECT a FROM foo ORDER BY a OFFSET \$1 \\bind 4999 \\g +SELECT 1; +END; +}); +$log_offset = $node->wait_for_log(qr/LOG:\s+temporary file: path.*\n.*\ STATEMENT:\s+SELECT 1/s, $log_offset); +ok("log temp with unnamed portal"); + +# bind with implicit transaction test +$node->safe_psql("postgres", qq{ +SELECT a FROM foo ORDER BY a OFFSET \$1 \\bind 4999 \\g +}); +$log_offset = $node->wait_for_log(qr/LOG:\s+temporary file:/s, $log_offset); +ok("log temp with bind and implicit transaction"); + +# named portal test +$node->safe_psql("postgres", qq{ +BEGIN; +SELECT a FROM foo ORDER BY a OFFSET \$1 \\parse stmt +\\bind_named stmt 4999 \\g +SELECT 1; +END; +}); +$log_offset = $node->wait_for_log(qr/LOG:\s+temporary file: path.*\n.*\ STATEMENT:\s+SELECT 1/s, $log_offset); +ok("log temp with named portal"); + +# pipelined query test +$log_offset = -s $node->logfile; +$node->safe_psql("postgres", qq{ +\\startpipeline +SELECT a FROM foo ORDER BY a OFFSET \$1 \\bind 4999 \\sendpipeline +SELECT 1; +\\endpipeline +}); +$log_offset = $node->wait_for_log(qr/LOG:\s+temporary file: path.*\n.*\ STATEMENT:\s+SELECT 1/s, $log_offset); +ok("log temp with pipelined query"); + +# parse and bind tests +$log_offset = -s $node->logfile; +$node->safe_psql("postgres", qq{ +SELECT a, a, a FROM foo ORDER BY a OFFSET \$1 \\parse p1 +\\bind_named p1 4999 \\g +}); +$log_offset = $node->wait_for_log(qr/LOG:\s+temporary file:/s, $log_offset); +ok("log temp with parse and bind"); + +# simple query test +$node->safe_psql("postgres", qq{ +BEGIN; +SELECT a FROM foo ORDER BY a OFFSET 4999; +END; +}); +$log_offset = $node->wait_for_log(qr/SELECT a FROM foo ORDER BY a OFFSET 4999;\n.*\ LOG:\s+temporary file: path/s, $log_offset); +ok("log temp with simple query"); + +# cursor test +$node->safe_psql("postgres", qq{ +BEGIN; +DECLARE mycur CURSOR FOR SELECT a FROM foo ORDER BY a OFFSET 4999; +FETCH 10 FROM mycur; +SELECT 1; +CLOSE mycur; +END; +}); +$log_offset = $node->wait_for_log(qr/CLOSE mycur;\n.*\ LOG:\s+temporary file:/s, $log_offset); +ok("log temp with cursor"); + +# prepare/execute test +$node->safe_psql("postgres", qq{ +BEGIN; +PREPARE p1 AS SELECT a FROM foo ORDER BY a OFFSET 4999; +EXECUTE p1; +DEALLOCATE p1; +END; +}); +$log_offset = $node->wait_for_log(qr/EXECUTE p1;\n.*\ LOG:\s+temporary file:/s, $log_offset); +ok("prepare and execute cursor"); + +# Stop the node +$node->stop('fast'); +done_testing(); -- 2.39.5 (Apple Git-154)