I’ve created an ON DELETE rule on a view that SELECTs OLD into a temporary table and then calls a function that performs actions using the values of OLD. The rule deletes the temporary table before running the SELECT INTO TEMPORARY TABLE in case the rule is called more than once during a session by performing a SELECT dropTempTable(). This all works fine except when there is nothing to delete e.g. running the following query when there are no records with a name of ‘John Doe’:
DELETE FROM myview WHERE name = 'John Doe';
In this case the temporary table is created by the planner in preparation for it being used even though it won’t be, but my dropTempTable() statement is never called so the second time I perform a DELETE on my view, it fails because the temporary table already exists. Any suggestions on how to resolve this problem will be greatly appreciated. I realise that this example could be better solved using a Trigger but I’ve simplified it for the purposes of this post and a Trigger won’t work for my particular problem.
My View:
CREATE VIEW myview
AS SELECT * FROM mytable
My Rule:
CREATE RULE myview_delete
AS ON DELETE TO myview
DO INSTEAD (
SELECT dropTempTable();
SELECT OLD INTO TEMPORARY TABLE myTempTable;
SELECT myDeleteFunction();
);
My Drop Table Function:
CREATE FUNCTION dropTempTable()
RETURNS void AS $$
BEGIN
DROP TABLE IF EXISTS myTempTable;
END;
$$ LANGUAGE plpgsql;
I ended up moving my call to the dropTempTable function out of the DELETE rule and into the SELECT rule with the addition of an EXCEPTION statement so it looks like:
My Drop Table Function:
It’s a bit of a hack, but it works.