Add test for connection limits

Reviewed-by: Andres Freund <andres@anarazel.de>
Discussion: https://www.postgresql.org/message-id/a102f15f-eac4-4ff2-af02-f9ff209ec66f@iki.fi
This commit is contained in:
Heikki Linnakangas 2024-10-08 15:06:26 +03:00
parent 5b7da5c261
commit 6a1d0d470e
6 changed files with 143 additions and 1 deletions

View File

@ -12,7 +12,7 @@ subdir = src/test
top_builddir = ../..
include $(top_builddir)/src/Makefile.global
SUBDIRS = perl regress isolation modules authentication recovery subscription
SUBDIRS = perl postmaster regress isolation modules authentication recovery subscription
ifeq ($(with_icu),yes)
SUBDIRS += icu

View File

@ -4,6 +4,7 @@ subdir('regress')
subdir('isolation')
subdir('authentication')
subdir('postmaster')
subdir('recovery')
subdir('subscription')
subdir('modules')

View File

@ -0,0 +1,23 @@
#-------------------------------------------------------------------------
#
# Makefile for src/test/postmaster
#
# Portions Copyright (c) 1996-2024, PostgreSQL Global Development Group
# Portions Copyright (c) 1994, Regents of the University of California
#
# src/test/postmaster/Makefile
#
#-------------------------------------------------------------------------
subdir = src/test/postmaster
top_builddir = ../../..
include $(top_builddir)/src/Makefile.global
check:
$(prove_check)
installcheck:
$(prove_installcheck)
clean distclean:
rm -rf tmp_check

View File

@ -0,0 +1,27 @@
src/test/postmaster/README
Regression tests for postmaster
===============================
This directory contains a test suite for postmaster's handling of
connections, connection limits, and startup/shutdown sequence.
Running the tests
=================
NOTE: You must have given the --enable-tap-tests argument to configure.
Run
make check
or
make installcheck
You can use "make installcheck" if you previously did "make install".
In that case, the code in the installation tree is tested. With
"make check", a temporary installation tree is built from the current
sources and then tested.
Either way, this test initializes, starts, and stops a test Postgres
cluster.
See src/test/perl/README for more info about running these tests.

View File

@ -0,0 +1,12 @@
# Copyright (c) 2022-2024, PostgreSQL Global Development Group
tests += {
'name': 'postmaster',
'sd': meson.current_source_dir(),
'bd': meson.current_build_dir(),
'tap': {
'tests': [
't/001_connection_limits.pl',
],
},
}

View File

@ -0,0 +1,79 @@
# Copyright (c) 2021-2024, PostgreSQL Global Development Group
# Test connection limits, i.e. max_connections, reserved_connections
# and superuser_reserved_connections.
use strict;
use warnings FATAL => 'all';
use PostgreSQL::Test::Cluster;
use PostgreSQL::Test::Utils;
use Test::More;
# Initialize the server with specific low connection limits
my $node = PostgreSQL::Test::Cluster->new('primary');
$node->init;
$node->append_conf('postgresql.conf', "max_connections = 6");
$node->append_conf('postgresql.conf', "reserved_connections = 2");
$node->append_conf('postgresql.conf', "superuser_reserved_connections = 1");
$node->append_conf('postgresql.conf', "log_connections = on");
$node->start;
$node->safe_psql(
'postgres', qq{
CREATE USER regress_regular LOGIN;
CREATE USER regress_reserved LOGIN;
GRANT pg_use_reserved_connections TO regress_reserved;
CREATE USER regress_superuser LOGIN SUPERUSER;
});
# With the limits we set in postgresql.conf, we can establish:
# - 3 connections for any user with no special privileges
# - 2 more connections for users belonging to "pg_use_reserved_connections"
# - 1 more connection for superuser
sub background_psql_as_user
{
my $user = shift;
return $node->background_psql(
'postgres',
on_error_die => 1,
extra_params => [ '-U', $user ]);
}
my @sessions = ();
push(@sessions, background_psql_as_user('regress_regular'));
push(@sessions, background_psql_as_user('regress_regular'));
push(@sessions, background_psql_as_user('regress_regular'));
$node->connect_fails(
"dbname=postgres user=regress_regular",
"reserved_connections limit",
expected_stderr =>
qr/FATAL: remaining connection slots are reserved for roles with privileges of the "pg_use_reserved_connections" role/
);
push(@sessions, background_psql_as_user('regress_reserved'));
push(@sessions, background_psql_as_user('regress_reserved'));
$node->connect_fails(
"dbname=postgres user=regress_regular",
"reserved_connections limit",
expected_stderr =>
qr/FATAL: remaining connection slots are reserved for roles with the SUPERUSER attribute/
);
push(@sessions, background_psql_as_user('regress_superuser'));
$node->connect_fails(
"dbname=postgres user=regress_superuser",
"superuser_reserved_connections limit",
expected_stderr => qr/FATAL: sorry, too many clients already/);
# TODO: test that query cancellation is still possible
foreach my $session (@sessions)
{
$session->quit;
}
done_testing();