diff --git a/src/backend/executor/execMain.c b/src/backend/executor/execMain.c index 602a08e585..6a459af9a2 100644 --- a/src/backend/executor/execMain.c +++ b/src/backend/executor/execMain.c @@ -2799,15 +2799,24 @@ EvalPlanQualStart(EPQState *epqstate, EState *parentestate, Plan *planTree) estate->es_output_cid = parentestate->es_output_cid; if (parentestate->es_num_result_relations > 0) { - int numResultRelations = parentestate->es_num_result_relations; + int numResultRels = parentestate->es_num_result_relations; + int numRootResultRels = parentestate->es_num_root_result_relations; ResultRelInfo *resultRelInfos; resultRelInfos = (ResultRelInfo *) - palloc(numResultRelations * sizeof(ResultRelInfo)); + palloc(numResultRels * sizeof(ResultRelInfo)); memcpy(resultRelInfos, parentestate->es_result_relations, - numResultRelations * sizeof(ResultRelInfo)); + numResultRels * sizeof(ResultRelInfo)); estate->es_result_relations = resultRelInfos; - estate->es_num_result_relations = numResultRelations; + estate->es_num_result_relations = numResultRels; + + /* Also transfer partitioned root result relations. */ + resultRelInfos = (ResultRelInfo *) + palloc(numRootResultRels * sizeof(ResultRelInfo)); + memcpy(resultRelInfos, parentestate->es_root_result_relations, + numRootResultRels * sizeof(ResultRelInfo)); + estate->es_root_result_relations = resultRelInfos; + estate->es_num_root_result_relations = numRootResultRels; } /* es_result_relation_info must NOT be copied */ /* es_trig_target_relations must NOT be copied */ diff --git a/src/test/isolation/expected/eval-plan-qual.out b/src/test/isolation/expected/eval-plan-qual.out index 0308f2d729..703f410068 100644 --- a/src/test/isolation/expected/eval-plan-qual.out +++ b/src/test/isolation/expected/eval-plan-qual.out @@ -629,3 +629,15 @@ step multireadwcte: <... completed> subid id 1 1 + +starting permutation: simplepartupdate complexpartupdate c1 c2 +step simplepartupdate: + update parttbl set a = a; + +step complexpartupdate: + with u as (update parttbl set a = a returning parttbl.*) + update parttbl set a = u.a from u; + +step c1: COMMIT; +step complexpartupdate: <... completed> +step c2: COMMIT; diff --git a/src/test/isolation/specs/eval-plan-qual.spec b/src/test/isolation/specs/eval-plan-qual.spec index 5a4d1c1705..4744f558b0 100644 --- a/src/test/isolation/specs/eval-plan-qual.spec +++ b/src/test/isolation/specs/eval-plan-qual.spec @@ -32,6 +32,10 @@ setup CREATE TABLE jointest AS SELECT generate_series(1,10) AS id, 0 AS data; CREATE INDEX ON jointest(id); + + CREATE TABLE parttbl (a int) PARTITION BY LIST (a); + CREATE TABLE parttbl1 PARTITION OF parttbl FOR VALUES IN (1); + INSERT INTO parttbl VALUES (1); } teardown @@ -41,6 +45,7 @@ teardown DROP TABLE accounts_ext; DROP TABLE p CASCADE; DROP TABLE table_a, table_b, jointest; + DROP TABLE parttbl; } session "s1" @@ -137,6 +142,12 @@ step "selectresultforupdate" { where jt.id = y for update of jt, ss1, ss2; } +# test for EPQ on a partitioned result table + +step "simplepartupdate" { + update parttbl set a = a; +} + session "s2" setup { BEGIN ISOLATION LEVEL READ COMMITTED; } @@ -174,6 +185,10 @@ step "updateforcip3" { } step "wrtwcte" { UPDATE table_a SET value = 'tableAValue2' WHERE id = 1; } step "wrjt" { UPDATE jointest SET data = 42 WHERE id = 7; } +step "complexpartupdate" { + with u as (update parttbl set a = a returning parttbl.*) + update parttbl set a = u.a from u; +} # Use writable CTEs to create self-updated rows, that then are # (updated|deleted). The *fail versions of the tests additionally @@ -261,3 +276,5 @@ permutation "wrtwcte" "readwcte" "c1" "c2" permutation "wrjt" "selectjoinforupdate" "c2" "c1" permutation "wrjt" "selectresultforupdate" "c2" "c1" permutation "wrtwcte" "multireadwcte" "c1" "c2" + +permutation "simplepartupdate" "complexpartupdate" "c1" "c2"