mirror of
https://git.postgresql.org/git/postgresql.git
synced 2024-09-30 13:51:23 +02:00
Fix yet another bug in ON CONFLICT rule deparsing.
Expand testing of rule deparsing a good bit, it's evidently needed. Author: Peter Geoghegan, Andres Freund Discussion: CAM3SWZQmXxZhQC32QVEOTYfNXJBJ_Q2SDENL7BV14Cq-zL0FLg@mail.gmail.com
This commit is contained in:
parent
631d749007
commit
284bef2977
@ -5500,7 +5500,7 @@ get_insert_query_def(Query *query, deparse_context *context)
|
|||||||
get_rule_expr(confl->arbiterWhere, context, false);
|
get_rule_expr(confl->arbiterWhere, context, false);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else if (confl->constraint != InvalidOid)
|
||||||
{
|
{
|
||||||
char *constraint = get_constraint_name(confl->constraint);
|
char *constraint = get_constraint_name(confl->constraint);
|
||||||
|
|
||||||
|
@ -2811,14 +2811,26 @@ CREATE TABLE hat_data (
|
|||||||
);
|
);
|
||||||
create unique index hat_data_unique_idx
|
create unique index hat_data_unique_idx
|
||||||
on hat_data (hat_name COLLATE "C" bpchar_pattern_ops);
|
on hat_data (hat_name COLLATE "C" bpchar_pattern_ops);
|
||||||
-- okay
|
-- DO NOTHING with ON CONFLICT
|
||||||
CREATE RULE hat_nosert AS ON INSERT TO hats
|
CREATE RULE hat_nosert AS ON INSERT TO hats
|
||||||
DO INSTEAD
|
DO INSTEAD
|
||||||
INSERT INTO hat_data VALUES (
|
INSERT INTO hat_data VALUES (
|
||||||
NEW.hat_name,
|
NEW.hat_name,
|
||||||
NEW.hat_color)
|
NEW.hat_color)
|
||||||
ON CONFLICT (hat_name COLLATE "C" bpchar_pattern_ops) WHERE hat_color = 'green'
|
ON CONFLICT (hat_name COLLATE "C" bpchar_pattern_ops) WHERE hat_color = 'green'
|
||||||
DO NOTHING RETURNING *;
|
DO NOTHING
|
||||||
|
RETURNING *;
|
||||||
|
SELECT definition FROM pg_rules WHERE tablename = 'hats' ORDER BY rulename;
|
||||||
|
definition
|
||||||
|
---------------------------------------------------------------------------------------------
|
||||||
|
CREATE RULE hat_nosert AS +
|
||||||
|
ON INSERT TO hats DO INSTEAD INSERT INTO hat_data (hat_name, hat_color) +
|
||||||
|
VALUES (new.hat_name, new.hat_color) ON CONFLICT(hat_name COLLATE "C" bpchar_pattern_ops)+
|
||||||
|
WHERE (hat_data.hat_color = 'green'::bpchar) DO NOTHING +
|
||||||
|
RETURNING hat_data.hat_name, +
|
||||||
|
hat_data.hat_color;
|
||||||
|
(1 row)
|
||||||
|
|
||||||
-- Works (projects row)
|
-- Works (projects row)
|
||||||
INSERT INTO hats VALUES ('h7', 'black') RETURNING *;
|
INSERT INTO hats VALUES ('h7', 'black') RETURNING *;
|
||||||
hat_name | hat_color
|
hat_name | hat_color
|
||||||
@ -2845,6 +2857,34 @@ SELECT tablename, rulename, definition FROM pg_rules
|
|||||||
(1 row)
|
(1 row)
|
||||||
|
|
||||||
DROP RULE hat_nosert ON hats;
|
DROP RULE hat_nosert ON hats;
|
||||||
|
-- DO NOTHING without ON CONFLICT
|
||||||
|
CREATE RULE hat_nosert_all AS ON INSERT TO hats
|
||||||
|
DO INSTEAD
|
||||||
|
INSERT INTO hat_data VALUES (
|
||||||
|
NEW.hat_name,
|
||||||
|
NEW.hat_color)
|
||||||
|
ON CONFLICT
|
||||||
|
DO NOTHING
|
||||||
|
RETURNING *;
|
||||||
|
SELECT definition FROM pg_rules WHERE tablename = 'hats' ORDER BY rulename;
|
||||||
|
definition
|
||||||
|
------------------------------------------------------------------------------
|
||||||
|
CREATE RULE hat_nosert_all AS +
|
||||||
|
ON INSERT TO hats DO INSTEAD INSERT INTO hat_data (hat_name, hat_color)+
|
||||||
|
VALUES (new.hat_name, new.hat_color) ON CONFLICT DO NOTHING +
|
||||||
|
RETURNING hat_data.hat_name, +
|
||||||
|
hat_data.hat_color;
|
||||||
|
(1 row)
|
||||||
|
|
||||||
|
DROP RULE hat_nosert_all ON hats;
|
||||||
|
-- Works (does nothing)
|
||||||
|
INSERT INTO hats VALUES ('h7', 'black') RETURNING *;
|
||||||
|
hat_name | hat_color
|
||||||
|
------------+------------
|
||||||
|
h7 | black
|
||||||
|
(1 row)
|
||||||
|
|
||||||
|
-- DO UPDATE with a WHERE clause
|
||||||
CREATE RULE hat_upsert AS ON INSERT TO hats
|
CREATE RULE hat_upsert AS ON INSERT TO hats
|
||||||
DO INSTEAD
|
DO INSTEAD
|
||||||
INSERT INTO hat_data VALUES (
|
INSERT INTO hat_data VALUES (
|
||||||
@ -2855,6 +2895,17 @@ CREATE RULE hat_upsert AS ON INSERT TO hats
|
|||||||
SET hat_name = hat_data.hat_name, hat_color = excluded.hat_color
|
SET hat_name = hat_data.hat_name, hat_color = excluded.hat_color
|
||||||
WHERE excluded.hat_color <> 'forbidden'
|
WHERE excluded.hat_color <> 'forbidden'
|
||||||
RETURNING *;
|
RETURNING *;
|
||||||
|
SELECT definition FROM pg_rules WHERE tablename = 'hats' ORDER BY rulename;
|
||||||
|
definition
|
||||||
|
-----------------------------------------------------------------------------------------------------------------------------------------
|
||||||
|
CREATE RULE hat_upsert AS +
|
||||||
|
ON INSERT TO hats DO INSTEAD INSERT INTO hat_data (hat_name, hat_color) +
|
||||||
|
VALUES (new.hat_name, new.hat_color) ON CONFLICT(hat_name) DO UPDATE SET hat_name = hat_data.hat_name, hat_color = excluded.hat_color+
|
||||||
|
WHERE (excluded.hat_color <> 'forbidden'::bpchar) +
|
||||||
|
RETURNING hat_data.hat_name, +
|
||||||
|
hat_data.hat_color;
|
||||||
|
(1 row)
|
||||||
|
|
||||||
-- Works (does upsert)
|
-- Works (does upsert)
|
||||||
INSERT INTO hats VALUES ('h8', 'black') RETURNING *;
|
INSERT INTO hats VALUES ('h8', 'black') RETURNING *;
|
||||||
hat_name | hat_color
|
hat_name | hat_color
|
||||||
|
@ -1062,14 +1062,16 @@ CREATE TABLE hat_data (
|
|||||||
create unique index hat_data_unique_idx
|
create unique index hat_data_unique_idx
|
||||||
on hat_data (hat_name COLLATE "C" bpchar_pattern_ops);
|
on hat_data (hat_name COLLATE "C" bpchar_pattern_ops);
|
||||||
|
|
||||||
-- okay
|
-- DO NOTHING with ON CONFLICT
|
||||||
CREATE RULE hat_nosert AS ON INSERT TO hats
|
CREATE RULE hat_nosert AS ON INSERT TO hats
|
||||||
DO INSTEAD
|
DO INSTEAD
|
||||||
INSERT INTO hat_data VALUES (
|
INSERT INTO hat_data VALUES (
|
||||||
NEW.hat_name,
|
NEW.hat_name,
|
||||||
NEW.hat_color)
|
NEW.hat_color)
|
||||||
ON CONFLICT (hat_name COLLATE "C" bpchar_pattern_ops) WHERE hat_color = 'green'
|
ON CONFLICT (hat_name COLLATE "C" bpchar_pattern_ops) WHERE hat_color = 'green'
|
||||||
DO NOTHING RETURNING *;
|
DO NOTHING
|
||||||
|
RETURNING *;
|
||||||
|
SELECT definition FROM pg_rules WHERE tablename = 'hats' ORDER BY rulename;
|
||||||
|
|
||||||
-- Works (projects row)
|
-- Works (projects row)
|
||||||
INSERT INTO hats VALUES ('h7', 'black') RETURNING *;
|
INSERT INTO hats VALUES ('h7', 'black') RETURNING *;
|
||||||
@ -1079,6 +1081,22 @@ SELECT tablename, rulename, definition FROM pg_rules
|
|||||||
WHERE tablename = 'hats';
|
WHERE tablename = 'hats';
|
||||||
DROP RULE hat_nosert ON hats;
|
DROP RULE hat_nosert ON hats;
|
||||||
|
|
||||||
|
-- DO NOTHING without ON CONFLICT
|
||||||
|
CREATE RULE hat_nosert_all AS ON INSERT TO hats
|
||||||
|
DO INSTEAD
|
||||||
|
INSERT INTO hat_data VALUES (
|
||||||
|
NEW.hat_name,
|
||||||
|
NEW.hat_color)
|
||||||
|
ON CONFLICT
|
||||||
|
DO NOTHING
|
||||||
|
RETURNING *;
|
||||||
|
SELECT definition FROM pg_rules WHERE tablename = 'hats' ORDER BY rulename;
|
||||||
|
DROP RULE hat_nosert_all ON hats;
|
||||||
|
|
||||||
|
-- Works (does nothing)
|
||||||
|
INSERT INTO hats VALUES ('h7', 'black') RETURNING *;
|
||||||
|
|
||||||
|
-- DO UPDATE with a WHERE clause
|
||||||
CREATE RULE hat_upsert AS ON INSERT TO hats
|
CREATE RULE hat_upsert AS ON INSERT TO hats
|
||||||
DO INSTEAD
|
DO INSTEAD
|
||||||
INSERT INTO hat_data VALUES (
|
INSERT INTO hat_data VALUES (
|
||||||
@ -1089,6 +1107,7 @@ CREATE RULE hat_upsert AS ON INSERT TO hats
|
|||||||
SET hat_name = hat_data.hat_name, hat_color = excluded.hat_color
|
SET hat_name = hat_data.hat_name, hat_color = excluded.hat_color
|
||||||
WHERE excluded.hat_color <> 'forbidden'
|
WHERE excluded.hat_color <> 'forbidden'
|
||||||
RETURNING *;
|
RETURNING *;
|
||||||
|
SELECT definition FROM pg_rules WHERE tablename = 'hats' ORDER BY rulename;
|
||||||
|
|
||||||
-- Works (does upsert)
|
-- Works (does upsert)
|
||||||
INSERT INTO hats VALUES ('h8', 'black') RETURNING *;
|
INSERT INTO hats VALUES ('h8', 'black') RETURNING *;
|
||||||
|
Loading…
Reference in New Issue
Block a user