Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commit0161074

Browse files
committed
Fix pg_dump's failure to honor dependencies of SQL functions.
A new-style SQL function can contain a parse-time dependencyon a unique index, much as views and matviews can (such casesarise from GROUP BY and ON CONFLICT clauses, for example).To dump and restore such a function successfully, pg_dump mustpostpone the function until after the unique index is created,which will happen in the post-data part of the dump. Thereforewe have to remove the normal constraint that functions aredumped in pre-data. Add code similar to the existing logicthat handles this for matviews. I added test cases for bothas well, since code coverage tests showed that we weren'ttesting the matview logic.Per report from Sami Imseih. Back-patch to v14 wherenew-style SQL functions came in.Discussion:https://postgr.es/m/2C1933AB-C2F8-499B-9D18-4AC1882256A0@amazon.com
1 parentb3f32a6 commit0161074

File tree

4 files changed

+89
-1
lines changed

4 files changed

+89
-1
lines changed

‎src/bin/pg_dump/pg_dump.c

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6085,6 +6085,7 @@ getAggregates(Archive *fout, int *numAggs)
60856085
agginfo[i].aggfn.argtypes,
60866086
agginfo[i].aggfn.nargs);
60876087
}
6088+
agginfo[i].aggfn.postponed_def = false; /* might get set during sort */
60886089

60896090
/* Decide whether we want to dump it */
60906091
selectDumpableObject(&(agginfo[i].aggfn.dobj), fout);
@@ -6283,6 +6284,7 @@ getFuncs(Archive *fout, int *numFuncs)
62836284
parseOidArray(PQgetvalue(res, i, i_proargtypes),
62846285
finfo[i].argtypes, finfo[i].nargs);
62856286
}
6287+
finfo[i].postponed_def = false; /* might get set during sort */
62866288

62876289
/* Decide whether we want to dump it */
62886290
selectDumpableObject(&(finfo[i].dobj), fout);
@@ -12168,7 +12170,8 @@ dumpFunc(Archive *fout, const FuncInfo *finfo)
1216812170
.namespace = finfo->dobj.namespace->dobj.name,
1216912171
.owner = finfo->rolname,
1217012172
.description = keyword,
12171-
.section = SECTION_PRE_DATA,
12173+
.section = finfo->postponed_def ?
12174+
SECTION_POST_DATA : SECTION_PRE_DATA,
1217212175
.createStmt = q->data,
1217312176
.dropStmt = delqry->data));
1217412177

‎src/bin/pg_dump/pg_dump.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -227,6 +227,7 @@ typedef struct _funcInfo
227227
intnargs;
228228
Oid*argtypes;
229229
Oidprorettype;
230+
boolpostponed_def;/* function must be postponed into post-data */
230231
}FuncInfo;
231232

232233
/* AggInfo is a superset of FuncInfo */

‎src/bin/pg_dump/pg_dump_sort.c

Lines changed: 44 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -868,6 +868,28 @@ repairMatViewBoundaryMultiLoop(DumpableObject *boundaryobj,
868868
}
869869
}
870870

871+
/*
872+
* If a function is involved in a multi-object loop, we can't currently fix
873+
* that by splitting it into two DumpableObjects. As a stopgap, we try to fix
874+
* it by dropping the constraint that the function be dumped in the pre-data
875+
* section. This is sufficient to handle cases where a function depends on
876+
* some unique index, as can happen if it has a GROUP BY for example.
877+
*/
878+
staticvoid
879+
repairFunctionBoundaryMultiLoop(DumpableObject*boundaryobj,
880+
DumpableObject*nextobj)
881+
{
882+
/* remove boundary's dependency on object after it in loop */
883+
removeObjectDependency(boundaryobj,nextobj->dumpId);
884+
/* if that object is a function, mark it as postponed into post-data */
885+
if (nextobj->objType==DO_FUNC)
886+
{
887+
FuncInfo*nextinfo= (FuncInfo*)nextobj;
888+
889+
nextinfo->postponed_def= true;
890+
}
891+
}
892+
871893
/*
872894
* Because we make tables depend on their CHECK constraints, while there
873895
* will be an automatic dependency in the other direction, we need to break
@@ -1062,6 +1084,28 @@ repairDependencyLoop(DumpableObject **loop,
10621084
}
10631085
}
10641086

1087+
/* Indirect loop involving function and data boundary */
1088+
if (nLoop>2)
1089+
{
1090+
for (i=0;i<nLoop;i++)
1091+
{
1092+
if (loop[i]->objType==DO_FUNC)
1093+
{
1094+
for (j=0;j<nLoop;j++)
1095+
{
1096+
if (loop[j]->objType==DO_PRE_DATA_BOUNDARY)
1097+
{
1098+
DumpableObject*nextobj;
1099+
1100+
nextobj= (j<nLoop-1) ?loop[j+1] :loop[0];
1101+
repairFunctionBoundaryMultiLoop(loop[j],nextobj);
1102+
return;
1103+
}
1104+
}
1105+
}
1106+
}
1107+
}
1108+
10651109
/* Table and CHECK constraint */
10661110
if (nLoop==2&&
10671111
loop[0]->objType==DO_TABLE&&

‎src/bin/pg_dump/t/002_pg_dump.pl

Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2490,6 +2490,27 @@
24902490
},
24912491
},
24922492
2493+
'Check ordering of a function that depends on a primary key' => {
2494+
create_order => 41,
2495+
create_sql => '
2496+
CREATE TABLE dump_test.ordering_table (id int primary key, data int);
2497+
CREATE FUNCTION dump_test.ordering_func ()
2498+
RETURNS SETOF dump_test.ordering_table
2499+
LANGUAGE sql BEGIN ATOMIC
2500+
SELECT * FROM dump_test.ordering_table GROUP BY id; END;',
2501+
regexp => qr/^
2502+
\QALTER TABLE ONLY dump_test.ordering_table\E
2503+
\n\s+\QADD CONSTRAINT ordering_table_pkey PRIMARY KEY (id);\E
2504+
.*^
2505+
\QCREATE FUNCTION dump_test.ordering_func\E/xms,
2506+
like =>
2507+
{%full_runs,%dump_test_schema_runs, section_post_data => 1, },
2508+
unlike => {
2509+
exclude_dump_test_schema => 1,
2510+
only_dump_measurement => 1,
2511+
},
2512+
},
2513+
24932514
'CREATE PROCEDURE dump_test.ptest1' => {
24942515
create_order => 41,
24952516
create_sql => 'CREATE PROCEDURE dump_test.ptest1(a int)
@@ -2732,6 +2753,25 @@
27322753
},
27332754
},
27342755
2756+
'Check ordering of a matview that depends on a primary key' => {
2757+
create_order => 42,
2758+
create_sql => '
2759+
CREATE MATERIALIZED VIEW dump_test.ordering_view AS
2760+
SELECT * FROM dump_test.ordering_table GROUP BY id;',
2761+
regexp => qr/^
2762+
\QALTER TABLE ONLY dump_test.ordering_table\E
2763+
\n\s+\QADD CONSTRAINT ordering_table_pkey PRIMARY KEY (id);\E
2764+
.*^
2765+
\QCREATE MATERIALIZED VIEW dump_test.ordering_view AS\E
2766+
\n\s+\QSELECT id,\E/xms,
2767+
like =>
2768+
{%full_runs,%dump_test_schema_runs, section_post_data => 1, },
2769+
unlike => {
2770+
exclude_dump_test_schema => 1,
2771+
only_dump_measurement => 1,
2772+
},
2773+
},
2774+
27352775
'CREATE POLICY p1 ON test_table' => {
27362776
create_order => 22,
27372777
create_sql => 'CREATE POLICY p1 ON dump_test.test_table

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp