CREATE RULE

CREATE RULE — 새 룰 정의

요약

CREATE [ OR REPLACE ] RULE 이름 AS ON 이벤트
    TO 테이블이름 [ WHERE 조건 ]
    DO [ ALSO | INSTEAD ] { NOTHING | 명령 | ( 명령 ; 명령 ... ) }

이벤트 자리에는:

    SELECT | INSERT | UPDATE | DELETE

설명

CREATE RULE 명령은 해당 테이블이나 뷰에 새 룰을 추가한다. CREATE OR REPLACE RULE 명령은 같은 이름의 해당 룰이 있으면 바꾸고 그렇지 않으면 새로 추가한다.

PostgreSQL 룰 시스템은 데이터베이스 내 테이블 대상으로 수행되는 자료 추가, 변경, 삭제 작업에 대해서 대체 작업을 수행할 수 있게 한다. 간단히 이야기하면, 이런 자료 조작 작업이 있을 때, 추가로 다른 작업을 함께 할 수 있게 한다. 또한 다른 한편으로 INSTEAD 옵션을 사용한다면, 아에 그 원래 작업을 진행하지 않고 지정한 작업을 진행하거나, 아무런 작업도 안하게 할 수도 있다. 룰은 SQL 뷰를 구현하는 도구로 사용된다. 룰은 일종의 명령 변환 메카니즘이거나, 명령 메크로로 이해해야 한다. 이 변환은 해당 명령이 실행 되기 이전에 일어남을 기억해야 한다. 작업 대상 각 개별 로우를 대상으로 추가 작업이 필요한 경우는 룰 대신에 트리거를 쓰는 것이 더 좋다. 룰에 대한 더 많은 정보는 40장에 있다.

현재, ON SELECT 룰은 INSTEAD 룰이어야 하며, 대신 실행될 명령은 단일 SELECT 명령이어야 한다. 즉, ON SELECT 룰은 테이블을 뷰로 바꾸는 역할을 한다. 이 뷰는 테이블에 저장된 자료를 보여주는 것이 아니라, 이 룰에서 지정한 명령의 결과를 보여주는 것이 된다. 하지만, ON SELECT 룰을 만들기보다 이미 CREATE VIEW 명령을 제공하고 있기 때문에, 이 명령을 이용하는 것이 더 낫다.

이 룰은 특정 뷰를 마치 테이블인 마냥 쓸 수 있도록 ON INSERT, ON UPDATE, ON DELETE 룰을 그 뷰에 추가해서 자료를 조작할 수도 있다. 또한 INSERT RETURNING 작업도 룰로 구현할 수 있는데, 이 때는 RETURNING 부분의 결과를 직접 지정해야 한다.

복잡한 뷰 갱신 작업으로 조건절 있는 룰을 사용하려면, 먼저, 그 뷰에 각 작업에 대한 조건절 없는 INSTEAD 룰을 각각 만들어야 한다는 것을 알고 있어야 한다. 조건절 있는 룰이거나, INSTEAD 룰이 아니면, update 작업을 정상적으로 진행하지 않는다. 왜냐하면, 서버는 몇몇 경우에 이런 작업은 그 뷰의 dummy 테이블에 대한 작업이 마지막으로 수행될 것이라고 판단해서 실행 금지하기 때문이다. (원문: it thinks it might end up trying to perform the action on the dummy table of the view in some cases.) 조건절 있는 룰을 사용하는 경우라면, 먼저 조건절 없는 DO INSTEAD NOTHING 룰을 만들어서, 서버가 더미 테이블 관련 작업을 아에 할 수 없도록 하는 것이 중요하다. 이렇게 하면, 조건절에 적용 되지 않는 자료들에 대해서는 INSTEAD NOTHING 작업을 하게 된다. (현재, 이 방법은 RETURNING 쿼리를 지원하지 않는다.)

참고

단순한 뷰인 경우는 이미 기본적으로 자료 갱신 작업을 허용하고 있다. (CREATE VIEW 명령 설명서 참조) 그래서, 굳이 사용자가 이 작업을 위해 룰을 만들 필요는 없다. 당연히 성능도 내장 자동 갱신 기능이 더 우수하다.

또 하나, 룰을 쓰는 자리에, INSTEAD OF 트리거를 대신 쓰는 것도 고려해볼만 하다(CREATE TRIGGER 명령 설명서 참조).

매개 변수

이름

새로 만들 룰 이름. 이 이름은 해당 테이블 대상으로 유일해야 한다. 동일 테이블 동일 이벤트에 여러 룰이 있다면, 그 룰은 알파벳 순으로 사용된다.

이벤트

SELECT, INSERT, UPDATE, 또는 DELETE. INSERT 또는 UPDATE 룰을 사용하고 있는 테이블 대상으로는 INSERT ... ON CONFLICT 쿼리는 사용할 수 없다. 대신에 업데이트 가능한 뷰 사용을 고려해 볼 수 있다.

테이블이름

대상 테이블 또는 뷰 이름(스키마 이름 포함).

조건

SQL 구문으로 작성된 표현식( 결과는 boolean 형). 이 식에서는 NEW, OLD 변수를 사용할 수 없으며, 집계 함수도 사용할 수 없다.

INSTEAD

INSTEAD 명령을 사용할 때. 원래 쿼리 대신에 여기서 지정한 명령을 대신 실행함.

ALSO

ALSO 원래 쿼리 다음에 추가로 지정한 명령을 실행함.

ALSO, INSTEAD 둘 다 지정하지 않았다면, ALSO 로 간주한다.

명령

룰 실 작업 명령. 이 명령으로 SELECT, INSERT, UPDATE, DELETE, 또는 NOTIFY 명령을 사용할 수 있다.

조건명령 안에서는 NEW, OLD 이름의 미리 예약된 테이블을 이름을 사용할 수 있다. NEWON INSERT 또는 ON UPDATE 룰에 사용하는 신규 자료의 로우를 뜻하며, OLDON UPDATE 또는 ON DELETE 룰에 사용하는 옛날 자료의 로우를 뜻한다.

참고

테이블 소유주가 그 테이블에 새 룰을 추가하거나 변경 할 수 있다.

뷰에 INSERT, UPDATE, 또는 DELETE 룰이 있는 경우, 뷰 칼럼을 보기 위해 RETURNING 구문을 사용할 수 있다. 이런 경우는 각각 INSERT RETURNING, UPDATE RETURNING, 또는 DELETE RETURNING 명령이 그 출력을 위해 사용된다. 뷰 변경 작업에서 RETURNING을 사용하지 않았다면, 그런데, 룰 명령으로 이 RETURNING 절은 무시된다. 현재 INSTEAD 룰에서만 RETURNING 절을 사용할 수 있다. 게다가, 이 RETURNING 절은 동일 이벤트에 대한 여러개의 룰이 있는 경우, 최종 하나에만 지정해야한다. 이 RETURNING 절이 하나도 없다면, 뷰 조작 쿼리에서 RETURNING을 사용하면 그 쿼리는 실행되지 않는다.

룰을 사용할 때는 순환하는 룰 사용을 하고 있지는 않는지 꼭 확인이 필요하다. 예를 들어, 두 개의 룰이 각각 서로 사용하도록 지정한 경우다. 다음과 같은 경우, SELECT 명령을 실행할 때 오류가 발생한다:

CREATE RULE "_RETURN" AS
    ON SELECT TO t1
    DO INSTEAD
        SELECT * FROM t2;

CREATE RULE "_RETURN" AS
    ON SELECT TO t2
    DO INSTEAD
        SELECT * FROM t1;

SELECT * FROM t1;

현재, 룰에서 실행할 명령으로 NOTIFY 명령을 사용할 있다. 이 경우 NOTIFY 명령은 조건에 상관 없이 실행된다. 예를 들어:

CREATE RULE notify_me AS ON UPDATE TO mytable DO ALSO NOTIFY mytable;

UPDATE mytable SET name = 'foo' WHERE id = 42;

이 경우 id = 42 조건에 맞는 자료가 없어도 NOTIFY 명령은 실행된다. 이 특성은 다음 버전에서는 그 대상 자료가 있는 경우만 실행되도록 변경되어야 할 것이다.

호환성

CREATE RULE 구문은 PostgreSQL 확장 기능이다.

관련 항목

ALTER RULE, DROP RULE