-1

我正在尝试使用触发器将记录插入到与另一个表中更改的记录相同的表中。

我还需要插入操作是插入、更新还是删除

CREATE OR REPLACE TRIGGER triggername
AFTER INSERT OR UPDATE OR DELETE
ON tablename

DECLARE
operation_type VARCHAR2;
changed_id VARCHAR2;
BEGIN

IF UPDATING
THEN operation_type := 'Update';

ELSE IF INSERTING
THEN operation_type := 'Insert';

ELSE IF DELETING
THEN operation_type := 'Delete';

END IF;


SELECT id
FROM tablename
WHERE :OLD.record1 != :NEW.record1
OR :OLD.record2 != :NEW.record2
OR :OLD.record3 != :NEW.record3
OR :OLD.record4 != :NEW.record4
OR :OLD.record5 != :NEW.record5
OR :OLD.record6 != :NEW.record6;

INTO changed_id;

  INSERT INTO trigger_table.id VALUES(changed_id);
  INSERT INTO trigger_table.type VALUES(operation_type);
END;
/

我收到一个错误

每个 :NEW 或 :OLD 的“BAD BIND NAME :NEW”或“BAD BIND NAME :OLD”

如上所示

4

2 回答 2

1

您的触发代码存在多个问题:

  1. operation_type VARCHAR2;

您必须声明变量大小。否则你会得到一个错误

PLS-00215:字符串长度约束必须在范围内(1 .. 32767)

例如,将其修改为:

operation_type VARCHAR2(20);
changed_id VARCHAR2(20);
  1. SELECT .. INTO 语句
SELECT id
FROM tablename
WHERE :OLD.record1 != :NEW.record1
OR :OLD.record2 != :NEW.record2
OR :OLD.record3 != :NEW.record3
OR :OLD.record4 != :NEW.record4
OR :OLD.record5 != :NEW.record5
OR :OLD.record6 != :NEW.record6;

INTO changed_id;

它在语法上是不正确的。INTO子句应该在SELECTFROM子句之间:

SELECT id 
  INTO changed_id 
FROM tablename 
 WHERE ...
  1. 哪里 :OLD.record1 != :NEW.record1

这是您关于bad bind variable error的原始问题。

要引用:OLD:NEW值,您需要创建必须包含以下条件的ROW LEVEL 触发器:

FOR EACH ROW
  1. 插入语句
INSERT INTO trigger_table.id VALUES(changed_id);
INSERT INTO trigger_table.type VALUES(operation_type);

您必须使用两个插入语句插入单行而不是两行。另外,trigger_table.id语法不正确。您需要在括号内提及列名。

例如,

INSERT INTO trigger_table(column1, column2) VALUES
          (changed_id, operation_type);
于 2015-05-13T05:05:54.037 回答
0

当您尝试将 :NEW 用于删除和 :OLD 用于在触发器中创建时,您会看到这些错误。

最好将 select & insert 语句移到里面

IF INSERTING THEN ... END IF;
IF UPDATING THEN ... END IF;
IF DELETING THEN ... END IF;

使用 :NEW 和 :OLD 变量

于 2015-05-13T04:01:34.733 回答