DML 문
UPDATE / DELETE 실수 방지 습관
- 쿼리를 실행하기 전 트렌젝션으로 묶는다.
- 쿼리를 작성할 때 SELECT 절을 사용하여 삭제할 데이터를 확인한다.
SELECT a.*, (SELECt sum(x.comm) FROM emp x WHERE x.deptno = b.deptno) FROM t1 a WHERE t1 a WHERE EXISTS (SELECT 1 FROM emp x WHERE x.deptno. a.deptno);
- 이후 쿼리를 UPDATE / DELETE 쿼리로 변경한다.
UPDATE t1 a SET a.sal = (SELECt sum(x.comm) FROM emp x WHERE x.deptno = b.deptno) WHERE EXISTS (SELECT 1 FROM emp x WHERE x.deptno. a.deptno);
- 변경된 결과를 확인한 후 COMMIT / ROLLBACK 을 진행한다.
Merge 문
Merge 문을 사용하면 테이블에 신규 행을 추가하거나, 갱신 또는 삭제를 할 수 있다.
다른 DB 에서는 UPSERT 또는 CONFRIT 문이 있는 것 같다. 한번 찾아봐야겠다.
언어의 차이인지, 다른 기능인지.
Merge 문 문법
- INTO TABLE_NAME : 갱신 또는 삽입할 타겟 테이블
- USING TABLE_NAME : 갱신 또는 삽입에 사용할 소스 테이블
- ON : 조건
- MATCHED THEN : 조건이 만족할 경우 업데이트
- NOT MATCHED THEN : 조건이 만족하지 않을 경우 추가
MERGE INTO TABLE_NAME USING TABLE_NAME ON (Condition) WHEN MATCHED THEN UPDATE_QUERY WHEN NOT MATCHED THEN INSERT_QUERY
Merge 절은 10.1 버전 미만의 경우 UPDATE/INSERT 을 동시에 사용해야한다.
하지만 10.1 버전 이상은 독립적인 사용이 가능하다.
INTO / USING 절에는 INLINE VIEW 절을 사용할 수 있다.
WHEN MATCHED THEN 절에는 WHERE 절 사용이 가능하며(Update), WHEN NOT MATCHED THEN 절에는 INSERT 이기 때문에 WHERE 절을 사용할 수 없다.
INSERT 절에는 WHERE 절을 사용할 경우 USING TABLE_NAME
을 인용해야 한다.
솔직히 이 부분이 소리인지 잘 모르겠다. 484Page 참고
옵티마이저 동작 원리에 따라서 MERGE UPDATE/INSERT 절의 WHERE 절보다 인라인 뷰에 일반 조건을 기술하는 편이 성능 측면에서 유리하다.
MERGE
INTO t1 t
USING (SELECT * FROM t2 WHERE job = 'CLERK') s
ON (t.empno = s.empno)
WHEN NOT MATCHED THEN
INSERT (t.empno, t.ename, t.job)
VALUES (s.empno, s.ename, s.job);
또한 10.1 버전 이후부터 MATCHED THEN(UPDATE) 에서는 DELETE 을 사용할 수 있다.
이 경우 갱신된 데이터 중 조건에 충족하는 경우에 데이터를 업데이트 한 후 삭제한다.
't1, t2 테이블에 모두 존재하는 행 중 job이 CLERK 인 행의 sal가 갱신되고, 갱신된 sal가 3000보다 작은 행이 삭제된다. MERGE INSERT 절에 의해 t2 테이블에만 존재하는 행 중 job이 CLERK 인 행이 삽입된다.'
MERGE
INTO t1 t
USING t2 s
ON (t.empno = s.empno)
WHEN MATCHED THEN
UPDATE SET t.sal = s.sal - 500 WHERE t.job = 'CLERK'
DELETE WHERE t.sal < 3000
WHEN NOT MATCHED THEN
INSERT (t.empno, t.ename, t.job)
VALUES (s.empno, s.enama, s.job)
WHERE s.job = 'CLERK';
MERGE 고급 - 차수 조인
MERGE 문도 UPDATE 문처럼 조인 차수에 따라 에러가 발생할 수 있다.
t1 테이블에서 empno 는 1개의 값(PK)만 있지만, t4 테이블에는 empno 가 N개가 있을 수 있다.
이 경우 WHEN MATCH TEHN 에서 WHERE 을 사용할 때 SET t.sal = s.sal - 500;
s.sal 가 N개 이기 때문이다.
이럴 때에는 ROW_NUMBER 등을 사용하여 N개가 아닌 1개가 선택될 수 있도록 해야한다.
MERGE 고급 - 조인 조건
ON 절에 기술된 열은 무한 루프에 걸릴 수 있기 때문에 갱신할 수 없다.
MERGE 고급 - 일반 조건 - PASS
MERGE 고급 - 아우터 조인 - PASS
DML 에러 로깅
DML 문에서 에러가 밸상한다면 해당 DML 문에 의한 변경 사항이 모두 롤백된다. 99행까지 변경한 후 마지막 1행에서 에러가 밸생한다면 99행이 모두 롤백된다는 것이다. 이런 상황을 하기 위해 DML 에러 로깅 기능을 사용할 수 있다. DML 에러 로깅 기능은 10.2 버전부터 사용할 수 있다.
DML 에러 로깅 기능은 DML 수행 시 에러가 밸상하면 에러를 로그 테이블에 기록한 후, 다음 행에 대한 DML을 계속 진행한다.
- INTO : 에러 로깅 테이블을 지정
- simple_expression : 에러 태그로 사용할 값을 지정
- REJECT LIMIT : interger로 에러의 한계 값을 지정(기본값은 0 또는 UNLIMITED)
'도서 > 불친절한 SQL 프로그래밍' 카테고리의 다른 글
불친절한 SQL 프로그래밍 - 1부 기본 개념 - 3장 오라클 데이터베이스 (0) | 2025.01.13 |
---|