首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >我可以在触发器中使用或条件吗?

我可以在触发器中使用或条件吗?
EN

Stack Overflow用户
提问于 2013-02-28 02:27:39
回答 2查看 93关注 0票数 0

我正在尝试在oracle数据库上创建触发器,但我遇到了when条件的问题。当我尝试使用它时,我得到“无效的关系运算符”。

代码语言:javascript
复制
   create or replace TRIGGER SQLTEST.TRIGGER_TESTE
AFTER INSERT OR UPDATE ON SQLDBA.VT_TABLE
FOR EACH ROW
WHEN (INSERTING OR NEW.FIELD_1 is null and OLD.FIELD_1 is not null or NEW.FIELD_1 <> OLD.FIELD_1) 

DECLARE
VAR_FIELD_1 VT_LOG_TABLE.FIELD_1%TYPE;

BEGIN

SELECT SQLDBA.SEQ_LOG_TABLE.NEXtval into VAR_FIELD_1
FROM dual;


INSERT INTO VT_LOG_TABLE
(FIELD_0,VAR_FIELD_1,FIELD_2,FIELD_3,FIELD_1, FIELD_4 )
VALUES( :NEW.FIELD_0,VAR_FIELD_1, :NEW.FIELD_2, :NEW.FIELD_3, :NEW.FIELD_1,SYSDATE);

END TRIGGER_TESTE;

什么才是实现这个条件的正确方法呢?

EN

回答 2

Stack Overflow用户

发布于 2013-02-28 05:17:41

正如graceemile所说,WHEN子句不理解INSERTING。我不确定是否可以依赖old.field_1 is null来指示插入,因为它看起来像一个可以为空的字段(因为new.field_1显然可以为空)。如果你不能,那么你可以将逻辑移到块中:

代码语言:javascript
复制
create or replace trigger vt_trigger
after insert or update on vt_table
for each row
declare
    do_logging boolean := false;
begin
    if inserting then
        do_logging := true;
    elsif (:new.field_1 is null and :old.field_1 is not null)
        or (:new.field_1 is not null and :old.field_1 is null)
        or (:new.field_1 <> :old.field_1)
    then
        do_logging := true;
    end if;

    if do_logging then
        insert into vt_log_table (field_0, var_field_1, field_2, field_3,
            field_1, field_4)
        values (:new.field_0, seq_log_table.nextval, :new.field_2, :new.field_3,
            :new.field_1, sysdate);
    end if;
end vt_trigger;
/

我把支票改成了这个样子:

代码语言:javascript
复制
    elsif (:new.field_1 is null and :old.field_1 is not null)
        or (:new.field_1 is not null and :old.field_1 is null)
        or (:new.field_1 <> :old.field_1)

..。为了检测field_1是否已经从null更改为null,或者从一个非NULL值更改为另一个非NULL值;也许您不希望这样,部分检查在我看来有点奇怪。我假设你只想在field_1以任何方式改变了,或者如果你插入了一个新的行的情况下记录。

票数 3
EN

Stack Overflow用户

发布于 2013-02-28 03:31:14

我刚刚尝试了类似的方法,Oracle不喜欢WHEN条件中的插入值。新的和旧的似乎都可以,即使是插入。

从实验中看,如果将以下内容添加到WHEN条件中,触发器将在插入时触发:

代码语言:javascript
复制
OR OLD.FIELD_1 IS NULL

所以试着这样做:

代码语言:javascript
复制
create or replace TRIGGER SQLTEST.TRIGGER_TESTE
AFTER INSERT OR UPDATE ON SQLDBA.VT_TABLE
FOR EACH ROW
WHEN (NEW.FIELD_1 is null and OLD.FIELD_1 is not null
   or NEW.FIELD_1 <> OLD.FIELD_1
   or OLD.FIELD_1 IS NULL)

DECLARE

... and so on

如果太复杂,可以创建两个触发器:一个用于UPDATE,带有WHEN条件,另一个用于INSERT,没有条件。

您还可以尝试将触发器定义为VT_TABLE上的Field_1的插入或更新之后:

代码语言:javascript
复制
create or replace trigger vt_trigger
after insert or update of field_1 on vt_table
for each row
begin
    insert into vt_log_table (field_0, var_field_1, field_2, field_3,
        field_1, field_4)
    values (:new.field_0, seq_log_table.nextval, :new.field_2, :new.field_3,
        :new.field_1, sysdate);
end vt_trigger;
/
票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/15119508

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档