CREATE TABLE source_det (
det_id number(10) by default IDENTITY
e_id NUMBER(10),
sys_name VARCHAR2(20),
ref_id NUMBER(10),
sys_other VARCHAR2(30)
);
INSERT INTO source_det VALUES(1,11,'SOURCE',992,null);
INSERT INTO source_det VALUES(2,11,'SOURCE',637,null);
INSERT INTO source_det VALUES(3,11,'SOURCE',null,'Manual');
INSERT INTO source_det VALUES(4,11,'TARGET',637,null);
INSERT INTO source_det VALUES(5,12,'TARGET',637,null);
審核表:
CREATE SEQUENCE audit_tab_sq;
CREATE TABLE audit_tab (
a_id NUMBER(10) default audit_tab_sq.nextval,
l_transaction varchar2(20),--INSERT, UPDATE, DELETE
e_id NUMBER(10),
sys_name VARCHAR2(20),
value_old VARCHAR2(20),
value_new VARCHAR2(20)
);
我需要創建一個觸發器,只要主表上發生新事件,就會觸發該觸發器,即source_det
示例:假設此記錄
INSERT INTO source_det VALUES(11,'SOURCE',null,'Manual');
為 e_id 11,其sys_name為 SOURCE 且ref_id為空且sys_other為手動。
因此,對于此記錄,如果用戶填寫了ref_idto 321 和sys_otherto Document。
然后在我的審計表中,即使我們有多個 e_id,也只會為這一行插入一個新條目。
預期輸出:
------ --------------- ------ ---------- ----------- -----------
| a_id | l_transaction | e_id | sys_name | value_old | value_new |
------ --------------- ------ ---------- ----------- -----------
| 1 | UPDATE | 11 | SOURCE | null | Document |
------ --------------- ------ ---------- ----------- -----------
同樣,如果有任何新記錄插入或洗掉,情況也是如此。
我想知道這是否可以使用觸發器來處理,因為可以有多個e_id
使用的工具:Oracle SQL Developer(18c)
uj5u.com熱心網友回復:
從您提供的資訊來看,您似乎缺少表的唯一值(鍵),這可能會導致您的問題。
根據您給定的代碼,您有
CREATE TABLE source_det (
e_id NUMBER(10),
sys_name VARCHAR2(20),
ref_id NUMBER(10),
sys_other VARCHAR2(30)
);
INSERT INTO source_det VALUES(11,'SOURCE',992,null);
INSERT INTO source_det VALUES(11,'SOURCE',637,null);
INSERT INTO source_det VALUES(11,'SOURCE',null,'Manual');
INSERT INTO source_det VALUES(11,'TARGET',637,null);
INSERT INTO source_det VALUES(12,'TARGET',637,null);
資料庫目前無法區分插入INSERT INTO source_det VALUES(11,'SOURCE',637,null);的行和插入的行INSERT INTO source_det VALUES(11,'SOURCE',637,null);。
我建議為每個表添加一個唯一值(鍵),以便有一個唯一值來標識每個元組。您可以通過多種方式(id、唯一對等)實作此目的,但您的資料集似乎不包含唯一對,因此 id 可能效果最好:
CREATE TABLE source_det (
id NUMBER GENERATED BY DEFAULT AS IDENTITY
e_id NUMBER(10),
sys_name VARCHAR2(20),
ref_id NUMBER(10),
sys_other VARCHAR2(30),
PRIMARY KEY(id)
);
然后您可以創建一個在更新時觸發的觸發器 | 插入 | delete 并將有一個唯一的鍵來參考每一行。
uj5u.com熱心網友回復:
這是如何做; 扳機:
SQL> CREATE OR REPLACE TRIGGER trg_sdet_audit
2 BEFORE INSERT OR UPDATE OR DELETE
3 ON source_det
4 FOR EACH ROW
5 BEGIN
6 IF INSERTING
7 THEN
8 INSERT INTO audit_tab (a_id,
9 l_transaction,
10 e_id,
11 sys_name,
12 value_old,
13 value_new)
14 VALUES (audit_tab_sq.NEXTVAL,
15 'INSERT',
16 :new.e_id,
17 :new.sys_name,
18 NULL,
19 :new.sys_other);
20 ELSIF UPDATING
21 THEN
22 INSERT INTO audit_tab (a_id,
23 l_transaction,
24 e_id,
25 sys_name,
26 value_old,
27 value_new)
28 VALUES (audit_tab_sq.NEXTVAL,
29 'UPDATE',
30 :new.e_id,
31 :new.sys_name,
32 :old.sys_other,
33 :new.sys_other);
34 ELSIF DELETING
35 THEN
36 INSERT INTO audit_tab (a_id,
37 l_transaction,
38 e_id,
39 sys_name,
40 value_old,
41 value_new)
42 VALUES (audit_tab_sq.NEXTVAL,
43 'DELETE',
44 :new.e_id,
45 :new.sys_name,
46 :old.sys_other,
47 NULL);
48 END IF;
49 END;
50 /
Trigger created.
測驗:
SQL> UPDATE source_det
2 SET sys_other = 'Other'
3 WHERE e_id = 11;
4 rows updated.
SQL> DELETE FROM source_det
2 WHERE det_id = 2;
1 row deleted.
結果:
SQL> SELECT * FROM audit_tab;
A_ID L_TRANSACTION E_ID SYS_NAME VALUE_OLD VALUE_NEW
---------- -------------------- ---------- -------------------- -------------------- --------------------
16 UPDATE 11 SOURCE Other
17 UPDATE 11 SOURCE Other
18 UPDATE 11 SOURCE Manual Other
19 UPDATE 11 TARGET Other
20 DELETE Other
SQL>
請注意,在日志表中包含時間戳可能是個好主意。
轉載請註明出處,本文鏈接:https://www.uj5u.com/qiye/449516.html
