20.5.3 업데이트 가능 및 삽입 가능한 View
일부 뷰는 갱신 가능합니다. 즉, 이러한 뷰를 UPDATE
, DELETE
, INSERT
등의 문 사용하여 기본이되는 테이블의 내용을 업데이트 할 수 있습니다. 뷰가 업데이트 가능하므로 해당 뷰의 행과 기반이되는 테이블의 행 사이에 일대일 관계가 존재해야합니다. 또한 뷰를 갱신 불가능하게하는 기타 특정 구조 구문도 존재합니다. 보다 구체적으로는 다음 중 하나를 포함하면 뷰는 업데이트 할 수 없습니다.
집계 함수 (
SUM()
,MIN()
,MAX()
,COUNT()
등)DISTINCT
GROUP BY
HAVING
UNION
또는UNION ALL
선택 목록의 서브 쿼리
특정 결합 (이 섹션 뒷부분의 결합에 대한 추가 설명을 참조하십시오)
FROM
절에서 갱신 불가능한 뷰FROM
절의 테이블을 참조하는WHERE
절의 서브 쿼리리터럴 값만을 참조 (이 경우 업데이트하는 기반이되는 테이블이 없습니다)
ALGORITHM = TEMPTABLE
사용 (임시 테이블을 사용하면 항상 뷰는 갱신 불가능합니다)기본 테이블 중 하나의 컬럼에 대한 여러 참조.
삽입 가능성 ( INSERT
문에서 업데이트 할 수 있음)는 업데이트 가능한 뷰가 뷰 컬럼에 대한 다음의 추가 요구 사항을 충족하는 경우에 삽입 할 수 있습니다.
중복 된 뷰 컬럼 이름이 존재하지 않도록해야합니다.
보기에는 기본값이없는 기본 테이블의 모든 컬럼이 포함되어 있어야합니다.
뷰 컬럼는 파생 컬럼이 아닌 단순한 열 참조 여야합니다. 파생 열은 간단한 컬럼 참조가 아닌 수식에서 파생 된 열입니다. 파생 된 컬럼의 예는 다음과 같습니다.
3.14159 col1 + 3 UPPER(col2) col3 / col4 (
subquery
)
간단한 컬럼 참조 및 파생 열이 혼재하고있는 뷰를 삽입 할 수 없지만 파생 컬럼 이외의 컬럼 만 업데이트하려면 업데이트 할 수 있습니다. 다음 뷰를 생각해보십시오.
CREATE VIEW v AS SELECT col1, 1 AS col2 FROM t;
이 뷰는 col2
가 수식에서 파생 있기 때문에 삽입 할 수 없습니다. 그러나 업데이트 col2
를 업데이트하려고하지 않은 경우 업데이트 할 수 있습니다. 다음 업데이트는 허용됩니다.
UPDATE v SET col1 = 0;
다음 업데이트는 파생 컬럼을 갱신하려고하고 있기 때문에 허용되지 않습니다.
UPDATE v SET col2 = 0;
MERGE
알고리즘으로 처리 할 수 있다면 여러 테이블 뷰를 업데이트 할 수 있습니다. 이것을 실현하려면보기에서 (외부 조인 또는 UNION
대신) 내부 조인을 사용해야합니다. 또한 뷰 정의에서 하나의 테이블 만 업데이트 할 수 있기 때문에 SET
절은 뷰의 테이블 중 하나의 컬럼만을 지명해야합니다. UNION ALL
을 사용하는 뷰는 구현이 임시 테이블을 사용하여 처리하기 때문에 이론적으로 업데이트 할 수도 허용되지 않습니다.
업데이트 가능한 여러 테이블 뷰에서는 INSERT
는 단일 테이블에 삽입 할 때 작동합니다. DELETE
는 지원되지 않습니다.
INSERT DELAYED
는 뷰에서 지원되지 않습니다.
테이블에 AUTO_INCREMENT
컬럼이 포함되어있는 경우, AUTO_INCREMENT
컬럼이 포함되지 않은 테이블에 삽입 할 수있는 뷰에 삽입하면 LAST_INSERT_ID()
의 값을 변경하지 않습니다. 이것은 뷰의 일부가 아닌 컬럼에 기본값을 삽입 한 부작용이 나타나지 않게하기 위해서입니다.
갱신 가능한 뷰에 WITH CHECK OPTION
절을 지정하면 select_statement
의 WHERE
절이 true 인 행을 제외한 행의 삽입 또는 갱신을 피할 수 있습니다.
갱신 가능한 뷰에 대한 WITH CHECK OPTION
절은 뷰가 다른 뷰와 관련하여 정의되어있는 경우 LOCAL
및 CASCADED
키워드에 의해 확인 테스트의 범위가 결정됩니다. LOCAL
키워드는 CHECK OPTION
을 정의되는 뷰에만 제한합니다. CASCADED
을 지정하면 기본이되는 뷰에 대한 체크도 평가됩니다. 두 키워드가 지정되지 않은 경우, 디폴트는 CASCADED
됩니다. 다음 테이블과 일련의 뷰의 정의를 생각 해보세요.
mysql>CREATE TABLE t1 (a INT);
mysql>CREATE VIEW v1 AS SELECT * FROM t1 WHERE a < 2
->WITH CHECK OPTION;
mysql>CREATE VIEW v2 AS SELECT * FROM v1 WHERE a > 0
->WITH LOCAL CHECK OPTION;
mysql>CREATE VIEW v3 AS SELECT * FROM v1 WHERE a > 0
->WITH CASCADED CHECK OPTION;
여기서 v2
와 v3
뷰는 v1
라는 다른 뷰의 관점에서 정의되어 있습니다. v2
는 LOCAL
검사 옵션이 있기 때문에 삽입은 v2
검사에 대해서만 테스트됩니다. v3
는 CASCADED
검사 옵션이 있기 때문에 삽입은 자신의 검사에 대해서만 아니라 기반이되는 뷰의 체크 대해 테스트됩니다. 다음 문에서 이러한 차이를 보여줍니다.
mysql>INSERT INTO v2 VALUES (2);
Query OK, 1 row affected (0.00 sec) mysql>INSERT INTO v3 VALUES (2);
ERROR 1369 (HY000) : CHECK OPTION failed 'test.v3'
MySQL은 CREATE VIEW
시 뷰의 갱신 가능성 플래그 플래그를 설정합니다. UPDATE
및 DELETE
(및 이와 유사한 작업)이 뷰에 사용하는 경우 플래그는 YES
(true)로 설정됩니다. 그렇지 않으면 플래그는 NO
(false)로 설정됩니다. INFORMATION_SCHEMA.VIEWS
테이블 IS_UPDATABLE
열이 플래그의 상태를 표시합니다. 이것은 뷰가 갱신 가능한지 여부를 서버가 항상 파악하고있는 것을 의미합니다. 뷰가 업데이트 가능하지 않은 경우, UPDATE
, DELETE
, INSERT
등의 문은 무효이며, 거부됩니다. (이 섹션의 다른 부분에서 설명하고있는 바와 같이, 뷰가 업데이트 가능한 경우에도 뷰에 삽입 할 수없는 경우도 있습니다.)
뷰를 업데이트 할 수 있는지 여부는 updatable_views_with_limit
시스템 변수의 값에 영향됩니다. 섹션 5.1 "서버 시스템 변수" 를 참조하십시오.