觸發器是在特定事件發生時自動執行的 PL/SQL 區塊,類似預存程序但無法由使用者直接呼叫。
biufer_表名_欄位名(b=before, i=insert, u=update, f=for each row, er=error handling)。WHEN 條件,非必要。CREATE TRIGGER biufer_employees_department_id
BEFORE INSERT OR UPDATE OF department_id ON employees
REFERENCING OLD AS old_value NEW AS new_value
FOR EACH ROW
WHEN (new_value.department_id <> 80)
BEGIN
:new_value.commission_pct := 0;
END;
/
department_id 時。REFERENCING 別名簡化新舊值引用。FOR EACH ROW 表列級觸發器(每列觸發一次)。WHEN 限制:僅當新部門代碼不等於 80 時執行。commission_pct 強制歸零。| 類型 | 說明 |
|---|---|
| Statement Trigger | 針對特定 DML 陳述式觸發一次,無論影響多少列。 |
| Row Trigger | 每受影響列觸發一次(FOR EACH ROW)。 |
| INSTEAD OF Trigger | 僅用於視圖,取代 DML 操作。 |
| System Event Trigger | 資料庫啟動/關閉、登入/登出等系統事件。 |
| User Event Trigger | 使用者登入/登出、DDL 操作等。 |
CREATE TABLE scott.employees_copy AS SELECT * FROM scott.emp;
CREATE TABLE scott.employees_log (who VARCHAR2(30), when DATE);
CREATE OR REPLACE TRIGGER biud_employee_copy
BEFORE INSERT OR UPDATE OR DELETE ON scott.employees_copy
BEGIN
INSERT INTO scott.employees_log (who, when) VALUES (USER, SYSDATE);
END;
/
UPDATE scott.employees_copy SET sal = sal * 1.1;
SELECT * FROM scott.employees_log;
CREATE OR REPLACE TRIGGER biud_employee_copy
BEFORE INSERT OR UPDATE OR DELETE ON employees_copy
DECLARE
l_action employees_log.action%TYPE;
BEGIN
IF INSERTING THEN
l_action := 'Insert';
ELSIF UPDATING THEN
l_action := 'Update';
ELSIF DELETING THEN
l_action := 'Delete';
ELSE
RAISE_APPLICATION_ERROR(-20001, 'Unexpected trigger state');
END IF;
INSERT INTO employees_log (who, action, when) VALUES (USER, l_action, SYSDATE);
END;
/
IF UPDATING('COL1') OR UPDATING('COL2') THEN
-- 特定欄位被更新時的處理
END IF;
DBMS_OUTPUT 除錯時,需在用戶端開啟 SET SERVEROUTPUT ON。