PostgreSQL:检查触发器函数中的NEW和OLD

时间:2018-06-21 07:24:41

标签: postgresql plpgsql database-trigger postgresql-9.5

我想创建一个对行进行计数并更新另一个表中的字段的触发器。我当前的解决方案适用于INSERT语句,但是当我删除一行时失败。

我当前的功能:

 CREATE OR REPLACE FUNCTION update_table_count()
RETURNS trigger AS
$$
DECLARE updatecount INT;
  BEGIN
      Select count(*) into updatecount 
        From source_table 
       Where id = new.id;
      Update dest_table set count=updatecount 
       Where id = new.id;
RETURN NEW;
END;
$$
LANGUAGE 'plpgsql';

触发器是一个非常基本的触发器,看起来像。

CREATE TRIGGER count_trigger
AFTER INSERT OR DELETE
ON source_table
FOR EACH ROW
EXECUTE PROCEDURE update_table_count();

当我执行DELETE语句时,会发生以下错误:

  

错误:记录“ new”尚未分配

     

详细信息:尚未分配的记录的元组结构不确定。

我知道一个解决方案可能是仅为DELETE创建一组触发器和函数,为INSERT语句创建一组触发器和函数。但是我想做得更优雅一些,并且想知道,是否有一种解决方案可以检查当前上下文中是否存在NEW或OLD并仅实现IF ELSE块。但是我不知道如何检查上下文相关项目。

感谢您的帮助

1 个答案:

答案 0 :(得分:4)

根据触发方式如何,使触发函数执行不同操作的常用方法是通过TG_OP

检查触发操作
CREATE OR REPLACE FUNCTION update_table_count()
RETURNS trigger AS
$$
DECLARE 
  updatecount INT;
BEGIN
  if tg_op = 'UPDATE' then 
    select count(*) into updatecount from source_table where id = new.id;
    update dest_table set count=updatecount where id = new.id;
  elsif tg_op = 'DELETE' then 
    ... do something else
  end if;
  RETURN NEW;
END;
$$
LANGUAGE plpgsql;

无关,但是:语言名称是一个标识符。不要用单引号引起来。