1
0
mirror of https://github.com/postgres/postgres.git synced 2025-07-28 23:42:10 +03:00

Refactor background psql TAP functions

This breaks out the background and interactive psql functionality into a
new class, PostgreSQL::Test::BackgroundPsql.  Sessions are still initiated
via PostgreSQL::Test::Cluster, but once started they can be manipulated by
the new helper functions which intend to make querying easier.  A sample
session for a command which can be expected to finish at a later time can
be seen below.

  my $session = $node->background_psql('postgres');
  $bsession->query_until(qr/start/, q(
    \echo start
	CREATE INDEX CONCURRENTLY idx ON t(a);
  ));
  $bsession->quit;

Patch by Andres Freund with some additional hacking by me.

Author: Andres Freund <andres@anarazel.de>
Reviewed-by: Andrew Dunstan <andrew@dunslane.net>
Discussion: https://postgr.es/m/20230130194350.zj5v467x4jgqt3d6@awork3.anarazel.de
This commit is contained in:
Daniel Gustafsson
2023-04-07 22:14:20 +02:00
parent 32bc0d022d
commit 664d757531
7 changed files with 386 additions and 240 deletions

View File

@ -36,63 +36,46 @@ $node->safe_psql('postgres', q(CREATE TABLE tbl(i int)));
# statements.
#
my $main_in = '';
my $main_out = '';
my $main_timer = IPC::Run::timeout($PostgreSQL::Test::Utils::timeout_default);
my $main_h = $node->background_psql('postgres');
my $main_h =
$node->background_psql('postgres', \$main_in, \$main_out,
$main_timer, on_error_stop => 1);
$main_in .= q(
$main_h->query_safe(q(
BEGIN;
INSERT INTO tbl VALUES(0);
\echo syncpoint1
);
pump $main_h until $main_out =~ /syncpoint1/ || $main_timer->is_expired;
));
my $cic_in = '';
my $cic_out = '';
my $cic_timer = IPC::Run::timeout($PostgreSQL::Test::Utils::timeout_default);
my $cic_h =
$node->background_psql('postgres', \$cic_in, \$cic_out,
$cic_timer, on_error_stop => 1);
$cic_in .= q(
my $cic_h = $node->background_psql('postgres');
$cic_h->query_until(qr/start/, q(
\echo start
CREATE INDEX CONCURRENTLY idx ON tbl(i);
);
pump $cic_h until $cic_out =~ /start/ || $cic_timer->is_expired;
));
$main_in .= q(
$main_h->query_safe(q(
PREPARE TRANSACTION 'a';
);
));
$main_in .= q(
$main_h->query_safe(q(
BEGIN;
INSERT INTO tbl VALUES(0);
\echo syncpoint2
);
pump $main_h until $main_out =~ /syncpoint2/ || $main_timer->is_expired;
));
$node->safe_psql('postgres', q(COMMIT PREPARED 'a';));
$main_in .= q(
$main_h->query_safe(q(
PREPARE TRANSACTION 'b';
BEGIN;
INSERT INTO tbl VALUES(0);
\echo syncpoint3
);
pump $main_h until $main_out =~ /syncpoint3/ || $main_timer->is_expired;
));
$node->safe_psql('postgres', q(COMMIT PREPARED 'b';));
$main_in .= q(
$main_h->query_safe(q(
PREPARE TRANSACTION 'c';
COMMIT PREPARED 'c';
);
$main_h->pump_nb;
));
$main_h->finish;
$cic_h->finish;
$main_h->quit;
$cic_h->quit;
$result = $node->psql('postgres', q(SELECT bt_index_check('idx',true)));
is($result, '0', 'bt_index_check after overlapping 2PC');
@ -113,22 +96,15 @@ PREPARE TRANSACTION 'persists_forever';
));
$node->restart;
my $reindex_in = '';
my $reindex_out = '';
my $reindex_timer =
IPC::Run::timeout($PostgreSQL::Test::Utils::timeout_default);
my $reindex_h =
$node->background_psql('postgres', \$reindex_in, \$reindex_out,
$reindex_timer, on_error_stop => 1);
$reindex_in .= q(
my $reindex_h = $node->background_psql('postgres');
$reindex_h->query_until(qr/start/, q(
\echo start
DROP INDEX CONCURRENTLY idx;
CREATE INDEX CONCURRENTLY idx ON tbl(i);
);
pump $reindex_h until $reindex_out =~ /start/ || $reindex_timer->is_expired;
));
$node->safe_psql('postgres', "COMMIT PREPARED 'spans_restart'");
$reindex_h->finish;
$reindex_h->quit;
$result = $node->psql('postgres', q(SELECT bt_index_check('idx',true)));
is($result, '0', 'bt_index_check after 2PC and restart');