Дана таблица KK_16 и таблица KK_16_LOG, являющаяся логом изменений в KK_16. KK_16_LOG содержит два набора полей, имеющихся в KK_16, (для старых и новых значений), дополнительное поле OPERATION_CODE, принимающее одно из значений ('I','U','D'), и дополнительное поле OPERATION_DATE – дата операции.
Написать AFTER INSERT OR UPDATE OR DELETE триггер на таблицу KK_16, который добавляет в KK_16_LOG записи о том, что было в KK_16 вставлено, изменено (указать старые и новые значения полей) или удалено. В логе следует указывать тип операции ('I'-insert, 'U'-update, 'D'-delete) и дату SYSDATE, когда проведена логируемая операция.
Создадим таблицы:
create table KK_16
(
nickname VARCHAR2(50),
rating INTEGER,
reg_date DATE
);
create table KK_16_LOG
(
old_nickname VARCHAR2(50),
old_rating INTEGER,
old_reg_date DATE,
new_nickname VARCHAR2(50),
new_rating INTEGER,
new_reg_date DATE,
operation_code VARCHAR2(1),
operation_date DATE
);
Создадим решающий задачу триггер. Заметим, что commit в триггере не делаем, commit делается во внешней транзакции:
CREATE OR REPLACE TRIGGER KK_TRIG_AIUD_KK_16
AFTER INSERT OR UPDATE OR DELETE ON KK_16
FOR EACH ROW
BEGIN
IF INSERTING THEN
INSERT INTO KK_16_LOG
(OLD_NICKNAME,
OLD_RATING,
OLD_REG_DATE,
NEW_NICKNAME,
NEW_RATING,
NEW_REG_DATE,
OPERATION_CODE,
OPERATION_DATE)
VALUES
(NULL,
NULL,
NULL,
:NEW.NICKNAME,
:NEW.RATING,
:NEW.REG_DATE,
'I',
SYSDATE);
ELSIF UPDATING THEN
INSERT INTO KK_16_LOG
(OLD_NICKNAME,
OLD_RATING,
OLD_REG_DATE,
NEW_NICKNAME,
NEW_RATING,
NEW_REG_DATE,
OPERATION_CODE,
OPERATION_DATE)
VALUES
(:OLD.NICKNAME,
:OLD.RATING,
:OLD.REG_DATE,
:NEW.NICKNAME,
:NEW.RATING,
:NEW.REG_DATE,
'U',
SYSDATE);
ELSIF DELETING THEN
INSERT INTO KK_16_LOG
(OLD_NICKNAME,
OLD_RATING,
OLD_REG_DATE,
NEW_NICKNAME,
NEW_RATING,
NEW_REG_DATE,
OPERATION_CODE,
OPERATION_DATE)
VALUES
(:OLD.NICKNAME,
:OLD.RATING,
:OLD.REG_DATE,
NULL,
NULL,
NULL,
'D',
SYSDATE);
END IF;
END KK_TRIG_AIUD_KK_16;
Проверим работу триггера с помощью следующих операций:
INSERT INTO KK_16(NICKNAME, RATING, REG_DATE) VALUES('moloko', 31337, to_date('28.08.2004', 'DD.MM.YYYY'));
INSERT INTO KK_16(NICKNAME, RATING, REG_DATE) VALUES('razdvakr', 98798, to_date('09.06.2005', 'DD.MM.YYYY'));
INSERT INTO KK_16(NICKNAME, RATING, REG_DATE) VALUES('kokos', 7687, to_date('11.09.2011', 'DD.MM.YYYY'));
UPDATE KK_16 SET RATING = 346 WHERE NICKNAME = 'razdvakr';
UPDATE KK_16 SET NICKNAME = 'KOKOC', REG_DATE = to_date('12.10.2010', 'DD.MM.YYYY') WHERE RATING = 7687;