我的任务是制作一个触发器,它会在我们的程序员在数据库中创建、更改、替换或删除触发器时触发。它必须将他们的更改记录到我所做的类似于SYS.trigger$
表的 2 个数据表中,并添加一些关于对它们进行更改的用户的额外信息。我从名为Galaktika或Galaxy的 ERP 系统中现有的审计功能中复制了日志记录的原则,以使其变得简单。但是,我遇到了一个众所周知的问题ORA-04089: no one can create triggers on system tables
并坚持了下来。
现在我正在寻找一种根据数据库规则轻轻修改触发器的方法。这是原始代码:
CREATE OR REPLACE TRIGGER MRK_AlTrigger$
BEFORE DELETE OR INSERT OR UPDATE
ON SYS.TRIGGER$
REFERENCING NEW AS New OLD AS Old
FOR EACH ROW
DECLARE
Log_Rec MRK_TRIGGERS_LOG_HEADER.NREC%TYPE;
BEGIN
INSERT INTO MRK_TRIGGERS_LOG_HEADER (DATEOFCHANGE,
USERCODE,
OPERATION,
OBJ#)
VALUES (
SYSDATE,
UID,
CASE
WHEN INSERTING THEN 0
WHEN UPDATING THEN 1
WHEN DELETING THEN 2
END,
CASE
WHEN INSERTING OR UPDATING THEN :new.OBJ#
ELSE :old.OBJ#
END)
RETURNING NRec
INTO Log_Rec;
IF INSERTING OR UPDATING
THEN
INSERT INTO MRK_TRIGGERS_LOG_SPECIF (LOGLINK,
OBJ#,
TYPE#,
UPDATE$,
INSERT$,
DELETE$,
BASEOBJECT,
REFOLDNAME,
REFNEWNAME,
DEFINITION,
WHENCLAUSE,
ACTION#,
ACTIONSIZE,
ENABLED,
PROPERTY,
SYS_EVTS,
NTTRIGCOL,
NTTRIGATT,
REFPRTNAME,
ACTIONLINENO)
VALUES (Log_Rec,
:new.OBJ#,
:new.TYPE#,
:new.UPDATE$,
:new.INSERT$,
:new.DELETE$,
:new.BASEOBJECT,
:new.REFOLDNAME,
:new.REFNEWNAME,
:new.DEFINITION,
:new.WHENCLAUSE,
:new.ACTION#,
:new.ACTIONSIZE,
:new.ENABLED,
:new.PROPERTY,
:new.SYS_EVTS,
:new.NTTRIGCOL,
:new.NTTRIGATT,
:new.REFPRTNAME,
:new.ACTIONLINENO);
END IF;
EXCEPTION
WHEN OTHERS
THEN
-- Consider logging the error and then re-raise
RAISE;
END MRK_AlTrigger$;
/
我也可以提供MRK_TRIGGERS_LOG_HEADER
和MRK_TRIGGERS_LOG_SPECIF
DDL,但认为没有必要。所以总结一下,这里是我的问题:
- 如何将上述源代码修改为语法
CREATE OR REPLACE TRIGGER ON DATABASE
? - 我是在发明一个轮子吗?有没有常见的方法来做这些事情?(我注意到有些表有日志记录选项,但认为它是出于调试目的)
任何帮助将不胜感激!
UPD:我决定(感谢 APC)最好在源代码管理中保存不同版本的代码并在 DB 中仅记录修订号,但梦想自动执行此操作。