I have two tables in Postgres, t_product
and t_product_modifications
having the following respective structures:
t_product
product_code product_category owner
============ ================ =====
A home Jack
B office Daniel
C outdoor Jack
D home Susan
(the 'product_code' and 'product_category' are unique together and is a composite primary key.
There is also a NOT NULL constraint on the 'owner' column)
t_product_modifications
product_code last_modified_time
============ ==================
A 2020-04-07 16:10:30
B 2020-04-07 16:10:30
C 2020-04-07 16:10:30
D 2020-04-07 16:10:30
I basically need to do a bulk insert/update into the t_product
table. And only if there has been a modification to a record, i should update the last_modified_time
column in the t_product_modifications
table. In addition to this, it is important that the entire bulk upsert should not fail if some other constraints have failed for certain records but rather it should just return a list of product_codes or an error log for which the upserts were not possible. (Also, for certain reasons I can't have both tables as one)
For example, let us say i am trying to do a bulk upsert for the following values into the t_product
table:
1. ('A','home', 'Susan')
2. ('B','office', 'Daniel')
3. ('E','office', NULL)
4. ('F','home', NULL)
When trying to insert the above four values, this is what needs to happen
('A','home')
primary key and the value Susan
should be updated in the owner
column. Since this record was an update to the t_product
table, the last_modified_time
for the respective product should be updated in the t_product_modifications
table.t_product_modifications
table since there are no modifications being made to the t_product
tableNULL
NULL
I will be executing this Postgres query from a Python script and wish to save all errors that happened during upsert without the entire query failing. I was unable to find a solution on StackOverflow that was efficient enough.
Trigger procedures are perfect for solving your problem. You need to create a procedure that will be executed when a record of the t_product
table is updated and check if the values of the columns have changed, if true, then update the last_modified_time
column from the t_product_modifications
table.
Your Trigger:
CREATE FUNCTION update_product() RETURNS TRIGGER AS $$
BEGIN
IF (TG_OP = 'UPDATE') AND OLD!=NEW THEN
UPDATE t_product_modifications SET last_modified_time = NOW() WHERE product_code = New.product_code;
END IF;
RETURN NEW;
END; $$ LANGUAGE plpgsql;
CREATE TRIGGER update_product_modified_time BEFORE UPDATE ON t_product FOR EACH ROW EXECUTE PROCEDURE update_product();
Demo in DBfiddle
-- This will update the last_modified_time in the t_product_modifications table
UPDATE t_product SET product_category = 'home', owner = 'Susan' WHERE product_code = 'A';
-- Nothing will happen
UPDATE t_product SET product_category = 'office', owner = 'Daniel' WHERE product_code = 'B';
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.