From 92608d497d779000077d13dae6c2064549c3785f Mon Sep 17 00:00:00 2001 From: "Chao Li (Evan)" Date: Sat, 11 Oct 2025 13:13:32 +0800 Subject: [PATCH v1] Fixed a bug in pg_dump about determining NotNull In determineNotNullFlags(), a check should be done against tbinfo->notnull_islocal[j], but "[j]" was missing. However, this bug cannot be actually fired, see the discussion. This commit fixes the bug and adds a TAP test of determining NotNull for pg_dump. Author: Chao Li Discussion: https://www.postgresql.org/message-id/CAEudQAo7ah%3D4TDheuEjtb0dsv6bHoK7uBNqv53Tsub2h-xBSJw%40mail.gmail.com --- src/bin/pg_dump/meson.build | 1 + src/bin/pg_dump/pg_dump.c | 2 +- src/bin/pg_dump/t/011_dump_determine_null.pl | 59 ++++++++++++++++++++ 3 files changed, 61 insertions(+), 1 deletion(-) create mode 100644 src/bin/pg_dump/t/011_dump_determine_null.pl diff --git a/src/bin/pg_dump/meson.build b/src/bin/pg_dump/meson.build index a2233b0a1b4..47225b818da 100644 --- a/src/bin/pg_dump/meson.build +++ b/src/bin/pg_dump/meson.build @@ -103,6 +103,7 @@ tests += { 't/004_pg_dump_parallel.pl', 't/005_pg_dump_filterfile.pl', 't/010_dump_connstr.pl', + 't/011_dump_determine_null.pl', ], }, } diff --git a/src/bin/pg_dump/pg_dump.c b/src/bin/pg_dump/pg_dump.c index 641bece12c7..9dc9396a34d 100644 --- a/src/bin/pg_dump/pg_dump.c +++ b/src/bin/pg_dump/pg_dump.c @@ -10074,7 +10074,7 @@ determineNotNullFlags(Archive *fout, PGresult *res, int r, */ if ((dopt->binary_upgrade && !tbinfo->ispartition && - !tbinfo->notnull_islocal) || + !tbinfo->notnull_islocal[j]) || !PQgetisnull(res, r, i_notnull_comment)) { tbinfo->notnull_constrs[j] = diff --git a/src/bin/pg_dump/t/011_dump_determine_null.pl b/src/bin/pg_dump/t/011_dump_determine_null.pl new file mode 100644 index 00000000000..11d93135dd8 --- /dev/null +++ b/src/bin/pg_dump/t/011_dump_determine_null.pl @@ -0,0 +1,59 @@ +# 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; + +my $tempdir = PostgreSQL::Test::Utils::tempdir; +my $node = PostgreSQL::Test::Cluster->new('main'); +my $port = $node->port; +my $backupdir = $node->backup_dir; +my $plainfile = "$backupdir/plain.sql"; + +# Init & start the node (no extra args; follow conventions used by other tests) +$node->init; +$node->start; + +# Setup parent/child table for binary upgrade NOT NULL check +$node->safe_psql('postgres', "CREATE TABLE parent_nn(a int NOT NULL, b int)"); +$node->safe_psql('postgres', "CREATE TABLE child_nn() INHERITS (parent_nn)"); + +# Add a local NOT NULL to child column 'b' +$node->safe_psql('postgres', "ALTER TABLE child_nn ALTER COLUMN b SET NOT NULL"); + +# Do a schema-only pg_dump through the tap helper +command_ok( + [ + 'pg_dump', + '--file' => $plainfile, + '--schema-only', + '--binary-upgrade', + '--port' => $port, + 'postgres' + ], + 'pg_dump schema-only succeeds' +); + +# Read dump and assert expected NOT NULL markings +my $dump = slurp_file($plainfile); + +# Check parent table that NOT NULL is there +ok($dump =~ qr/CREATE TABLE public\.parent_nn\s*\(\s*a integer NOT NULL/m, + "parent NOT NULL column 'a' is there"); + +# Check parent table that NULL-able is there +ok($dump =~ qr/CREATE TABLE public\.parent_nn\s*\(\s*a.*,\s*b integer/m, + "parent NULL-able column 'b' is there"); + +# Check child table that inherited NOT NULL is preserved +ok($dump =~ qr/CREATE TABLE public\.child_nn\s*\(\s*a integer CONSTRAINT parent_nn_a_not_null NOT NULL/m, + "inherited NOT NULL column 'a' preserved"); + +# Check child table that locally added NOT NULL is preserved +ok($dump =~ qr/CREATE TABLE public\.child_nn\s*\(\s*a.*,\s*b integer NOT NULL/m, + "child local NOT NULL column 'b' preserved"); + +done_testing(); -- 2.39.5 (Apple Git-154)