aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorDean Rasheed <dean.a.rasheed@gmail.com>2023-02-22 09:41:28 +0000
committerDean Rasheed <dean.a.rasheed@gmail.com>2023-02-22 09:41:28 +0000
commit018af1cc1c8075346e6a5fe3bb77b7e31399be70 (patch)
tree1585eadced83b2d84d4a8f3cf7dc0b7ab2c2ce70 /src
parentfa5dd460c1805a00a6fcc909b7e1f826663bcce3 (diff)
downloadpostgresql-018af1cc1c8075346e6a5fe3bb77b7e31399be70.tar.gz
postgresql-018af1cc1c8075346e6a5fe3bb77b7e31399be70.zip
Fix MERGE command tag for cross-partition updates.
This ensures that the row count in the command tag for a MERGE is correctly computed. Previously, if MERGE updated a partitioned table, the row count would be incorrect if any row was moved to a different partition, since such updates were counted twice. Back-patch to v15, where MERGE was introduced. Discussion: https://postgr.es/m/CAEZATCWRMG7XX2QEsVL1LswmNo2d_YG8tKTLkpD3=Lp644S7rg@mail.gmail.com
Diffstat (limited to 'src')
-rw-r--r--src/backend/executor/nodeModifyTable.c2
-rw-r--r--src/test/regress/expected/merge.out16
-rw-r--r--src/test/regress/sql/merge.sql11
3 files changed, 28 insertions, 1 deletions
diff --git a/src/backend/executor/nodeModifyTable.c b/src/backend/executor/nodeModifyTable.c
index 508dcc4cbea..ad0aa8dd9d7 100644
--- a/src/backend/executor/nodeModifyTable.c
+++ b/src/backend/executor/nodeModifyTable.c
@@ -2889,7 +2889,7 @@ lmerge_matched:;
}
ExecUpdatePrepareSlot(resultRelInfo, newslot, context->estate);
result = ExecUpdateAct(context, resultRelInfo, tupleid, NULL,
- newslot, mtstate->canSetTag, &updateCxt);
+ newslot, false, &updateCxt);
if (result == TM_Ok && updateCxt.updated)
{
ExecUpdateEpilogue(context, &updateCxt, resultRelInfo,
diff --git a/src/test/regress/expected/merge.out b/src/test/regress/expected/merge.out
index 564ff686943..cc324bd3137 100644
--- a/src/test/regress/expected/merge.out
+++ b/src/test/regress/expected/merge.out
@@ -1582,6 +1582,10 @@ SELECT * FROM pa_target ORDER BY tid;
ROLLBACK;
-- try updating the partition key column
BEGIN;
+CREATE FUNCTION merge_func() RETURNS integer LANGUAGE plpgsql AS $$
+DECLARE
+ result integer;
+BEGIN
MERGE INTO pa_target t
USING pa_source s
ON t.tid = s.sid
@@ -1589,6 +1593,18 @@ MERGE INTO pa_target t
UPDATE SET tid = tid + 1, balance = balance + delta, val = val || ' updated by merge'
WHEN NOT MATCHED THEN
INSERT VALUES (sid, delta, 'inserted by merge');
+IF FOUND THEN
+ GET DIAGNOSTICS result := ROW_COUNT;
+END IF;
+RETURN result;
+END;
+$$;
+SELECT merge_func();
+ merge_func
+------------
+ 14
+(1 row)
+
SELECT * FROM pa_target ORDER BY tid;
tid | balance | val
-----+---------+--------------------------
diff --git a/src/test/regress/sql/merge.sql b/src/test/regress/sql/merge.sql
index cef37e57d92..9ed648ad1f6 100644
--- a/src/test/regress/sql/merge.sql
+++ b/src/test/regress/sql/merge.sql
@@ -999,6 +999,10 @@ ROLLBACK;
-- try updating the partition key column
BEGIN;
+CREATE FUNCTION merge_func() RETURNS integer LANGUAGE plpgsql AS $$
+DECLARE
+ result integer;
+BEGIN
MERGE INTO pa_target t
USING pa_source s
ON t.tid = s.sid
@@ -1006,6 +1010,13 @@ MERGE INTO pa_target t
UPDATE SET tid = tid + 1, balance = balance + delta, val = val || ' updated by merge'
WHEN NOT MATCHED THEN
INSERT VALUES (sid, delta, 'inserted by merge');
+IF FOUND THEN
+ GET DIAGNOSTICS result := ROW_COUNT;
+END IF;
+RETURN result;
+END;
+$$;
+SELECT merge_func();
SELECT * FROM pa_target ORDER BY tid;
ROLLBACK;