8

我刚刚离开 MySQL 支持 PostgreSQL,我有一个关于触发器的问题。如果删除了“流程”表中的行,则此触发器旨在更新“工作流”表中的字段。

CREATE OR REPLACE FUNCTION fn_process_delete() RETURNS TRIGGER AS $$
BEGIN
    UPDATE workflow SET deleted_process_name = OLD.process_name
    WHERE process_id = OLD.process_id;
    RETURN NULL;
END;
$$ LANGUAGE plpgsql;

DROP TRIGGER IF EXISTS process_delete ON processes;
CREATE TRIGGER process_delete
AFTER DELETE ON processes
FOR EACH ROW 
EXECUTE PROCEDURE fn_process_delete();

我的问题有两个:

  1. 如果我如上所述使用 AFTER DELETE,该行将被删除,但更新语句不会更新“工作流”表中的字段。

  2. 如果我使用 BEFORE DELETE,则进程表将根本不执行删除,并提供一条错误消息“该行没有唯一标识符”。

任何人都可以建议吗?

4

1 回答 1

17

问题2:

您的触发功能以:

RETURN NULL;

这样您就可以跳过触发事件的执行。根据有关触发程序的文档

触发的行级触发器BEFORE可以返回 null 以指示触发器管理器跳过该行的其余操作(即,不触发后续触发器,并且//INSERT不会针对该行发生)。UPDATEDELETE

您需要将其替换为:

RETURN OLD;

以便系统继续删除该行。原因如下:

在前触发on的情况下DELETE,返回值没有直接影响,但它必须为非空才能允许触发操作继续进行。请注意,触发器中NEW为 null DELETE,因此返回它通常是不明智的。触发器中的常用习语DELETE是 returnOLD

大胆强调我的。

问题 1

我看不出为什么您的触发器和触发器功能不应该作为AFTER DELETE. 不用说,process_id表中必须存在匹配的行workflow

于 2012-05-21T15:16:15.197 回答