🥥 트리거

개념

  • 프로시저와 함수는 그 실행이 외부적인 실행 명령에 의해 이루어지는데 반해, 트리거의 실행은 트리거링 사건(Triggering Event)에 의해 내부적으로 이루어짐
  • 트리거를 일으키는 사건 (event)
    • 데이터베이스 테이블에 DML문이 발생할 때
    • DDL문도 가능
  • INSERT, UPDATE, DELETE 문의 사용에 사건을 정의할 수 있으며, 이들을 실행할 때 정의된 트리거도 자동 실행
  • 테이블과 별도로 데이터베이스에 저장


용도

  • 테이블 생성시 참조 무결성과 데이터 무결성 그 밖의 다른 제약 조건으로 정의할 수 없는 복잡한 요구 사항에 대한 제약조건을 생성할 수 있음
  • 테이블의 데이터에 생기는 작업을 감시, 보안할 수 있음 (변화 감지)
  • 테이블에 생기는 변화에 따라 필요한 다른 프로그램을 실행시킬 수 있음


형식

CREATE [OR REPLACE] TRIGGER trigger_name
BEFORE|AFTER
    trigger_event ON table_name
    [FOR EACH ROW]       -- 행 단위 작동
    [WHEN (condition)]   -- 더 구체적인 조건 명시
    PL/SQL block         -- 행위
  • BEFORE
    • INSERT, UPDATE, DELETE문이 실행되기 트리거 실행
  • AFTER
    • INSERT, UPDATE, DELETE문이 실행된 트리거 실행
  • trigger_event
    • INSERT, UPDATE, DELETE 중 한 개 이상
  • FOR EACH ROW
    • 행 트리거


🥥 문장 트리거와 행 트리거

문장 트리거

  • 트리거링 사건에 의해 단 한 번 실행
  • 컬럼의 각 데이터 행 제어 불가능
  • 컬럼의 데이터 값에 상관없이 그 컬럼에 변화가 일어남을 감지하여 실행되는 트리거


행 트리거

  • 컬럼의 각각의 데이터 행에 변화가 생길 때마다 실행
  • 변화가 생긴 데이터 행의 실제 값 제어 가능
  • 데이터 행의 실제 값을 수정, 변경 또는 저장할 때 사용


행 트리거의 컬럼값 참조

  • :old, :new 연산자 사용
  • INSERT 문
    • 입력할 데이터 값: :new.column_name에 지정
    • column_name은 테이블의 컬럼 이름
  • UPDATE 문
    • 변경하기 전 컬럼 데이터 값: :old.column_name
    • 수정할 새로운 데이터 값: :new.column_name
  • DELETE 문
    • 삭제되는 컬럼: :old.column_name


🥥 트리거 예 (1)

CREATE OR REPLACE TRIGGER trigger_test
BEFORE
    UPDATE ON dept
    FOR EACH ROW
BEGIN
    DBMS_OUTPUT.PUT_LINE('변경 전 컬럼값: ' || :old.dname);
    DBMS_OUTPUT.PUT_LINE('변경 후 컬럼값: ' || :new.dname);
END;
/
SET SERVEROUTPUT ON;
UPDATE dept
SET dname = '총무부'
WHERE deptno = 30

/* UPDATE문 실행 전 트리거링 발생

변경 전 컬럼값: 인사과
변경 후 컬럼값: 총무부

1 행이 갱신되었습니다.
*/


🥥 트리거 예 (2)

CREATE OR REPLACE TRIGGER sum_trigger
BEFORE
    INSERT OR UPDATE ON emp
    FOR EACH ROW
DECLARE
    -- 변수 선언
    avg_sal NUMBER;
BEGIN
    SELECT ROUND(AVG(sal), 3)
    INTO avg_sal
    FROM emp;

    DBMS_OUTPUT.PUT_LINE('급여 평균: ' || avg_sal);
END;
/

/* 트리거가 생성되었습니다. */
SET SERVEROUTPUT ON;

INSERT INTO EMP(empno, ename, job, hiredate, sal) 
VALUES(1000, 'LION', 'SALES', SYSDATE, 5000);

/* INSERT 문이 실행되기 전까지의 급여 평균 출력

급여 평균: 2073.214

1 개의 행이 만들어졌습니다.
*/