[2015-06-26] Oracle 성능 최적화 및 품질 고도화 3
-
Upload
seok-joon-yun -
Category
Software
-
view
96 -
download
14
Transcript of [2015-06-26] Oracle 성능 최적화 및 품질 고도화 3
![Page 1: [2015-06-26] Oracle 성능 최적화 및 품질 고도화 3](https://reader031.fdocuments.net/reader031/viewer/2022013108/55c2b05ebb61ebdd2b8b47c6/html5/thumbnails/1.jpg)
WareValleyhttp://www.WareValley.com
WareValley
Oracle중소기업 DB관리자를 위한 데이터베이스
성능 최적화 및 품질 고도화 전문가 과정 #3
오렌지팀 윤석준 선임연구원
![Page 2: [2015-06-26] Oracle 성능 최적화 및 품질 고도화 3](https://reader031.fdocuments.net/reader031/viewer/2022013108/55c2b05ebb61ebdd2b8b47c6/html5/thumbnails/2.jpg)
- 1일차 : Tuning 도구- D/B Tuning이 어려운 이유- Oracle D/B 구조- Tuning Tools : AutoTrace, SQL*Trace, V$SQLAREA
- 2일차 : SQL Tuning #1 : Optimizer- Rule-based Optimizer- Cost-based Optimizer- 통계정보, Histogram- Hint
- 3일차 : SQL Tuning #2 : Index, Join- Index- Join
- 4일차 : Server Tuning- Shared pool tuning- Data buffer cache tuning* NoSQL 소개
![Page 3: [2015-06-26] Oracle 성능 최적화 및 품질 고도화 3](https://reader031.fdocuments.net/reader031/viewer/2022013108/55c2b05ebb61ebdd2b8b47c6/html5/thumbnails/3.jpg)
INDEX 설계 시 주의사항
1. 조건에 만족하는 Data가 전체의 10% 내외일때 가장 이상적
2. 대용량 Data를 가진 Table에 적용
( 20 ~ 30만건 이상인 경우는 적극적 고려)
3. 분포도가 나쁘더라도 Fast Index Scan이 가능한 경우 효과적
4. 여러가지 Index 중 적합한 Index로 생성해야 함
5. Index가 생성되는 Tablespace와 물리적 크기에 대해 고려
(Extent, Block 크기)
![Page 4: [2015-06-26] Oracle 성능 최적화 및 품질 고도화 3](https://reader031.fdocuments.net/reader031/viewer/2022013108/55c2b05ebb61ebdd2b8b47c6/html5/thumbnails/4.jpg)
Single Column INDEX vs Composite Index
SELECT * FROM BIG_EMP WHERE DEPTNO = 10 AND JOB = 'CLERK';
CREATE INDEX I_BIG_EMP_DEPTNO ON BIG_EMP(DEPTNO);CREATE INDEX I_BIG_EMP_JOB ON BIG_EMP(JOB);
CREATE INDEX I_BIG_EMP_DEPTNO_JOB ON BIG_EMP(DEPTNO, JOB);
![Page 5: [2015-06-26] Oracle 성능 최적화 및 품질 고도화 3](https://reader031.fdocuments.net/reader031/viewer/2022013108/55c2b05ebb61ebdd2b8b47c6/html5/thumbnails/5.jpg)
Composite INDEX 선행 Column 결정 기준
1. WHERE 절에서 자주 검색될수록
2. 분포도가 좋을수록
3. Data가 적을수록
4. 범위검색 (BETWEEN, >, <, LIKE)로 검색되지 않을 수록
![Page 6: [2015-06-26] Oracle 성능 최적화 및 품질 고도화 3](https://reader031.fdocuments.net/reader031/viewer/2022013108/55c2b05ebb61ebdd2b8b47c6/html5/thumbnails/6.jpg)
Composite INDEX 선행 Column 결정 기준 (예제 )
CREATE INDEX I_BIG_EMP_DEPTNO_HIREDATEON BIG_EMP(DEPTNO, JOB, HIREDATE);
Call Count CPU Time Elapsed Time Disk Query Current Rows------- ------ -------- ------------ ---------- ---------- ---------- ----------Parse 1 0.000 0.000 0 0 0 0Execute 1 0.000 0.001 0 0 0 0Fetch 2 0.000 0.000 0 137 0 3------- ------ -------- ------------ ---------- ---------- ---------- ----------Total 4 0.000 0.001 0 137 0 3
Rows Row Source Operation------- -----------------------------------------------------------------------
3 SORT ORDER BY (cr=137 pr=0 pw=0 time=0 us cost=0 size=0 card=0)3 SORT GROUP BY (cr=137 pr=0 pw=0 time=2 us)
131 CONCATENATION (cr=137 pr=0 pw=0 time=390 us)53 TABLE ACCESS BY INDEX ROWID BIG_EMP (cr=55 pr=0 pw=0 time=208 us)53 INDEX RANGE SCAN I_BIG_EMP_DEPTNO_HIREDATE (cr=2 pr=0 pw=0 time=52 us)50 TABLE ACCESS BY INDEX ROWID BIG_EMP (cr=52 pr=0 pw=0 time=98 us)50 INDEX RANGE SCAN I_BIG_EMP_DEPTNO_HIREDATE (cr=2 pr=0 pw=0 time=49 us)28 TABLE ACCESS BY INDEX ROWID BIG_EMP (cr=30 pr=0 pw=0 time=27 us)28 INDEX RANGE SCAN I_BIG_EMP_DEPTNO_HIREDATE (cr=2 pr=0 pw=0 time=27 us)
Call Count CPU Time Elapsed Time Disk Query Current Rows------- ------ -------- ------------ ---------- ---------- ---------- ----------Parse 1 0.000 0.000 0 0 0 0Execute 1 0.000 0.003 0 15 0 0Fetch 2 0.016 0.057 118 8062 0 3------- ------ -------- ------------ ---------- ---------- ---------- ----------Total 4 0.016 0.060 118 8077 0 3
Rows Row Source Operation------- -----------------------------------------------------------------------
3 SORT ORDER BY (cr=8062 pr=118 pw=0 time=0 us cost=0 size=0 card=0)3 SORT GROUP BY (cr=8062 pr=118 pw=0 time=0 us)
131 TABLE ACCESS BY INDEX ROWID BIG_EMP (cr=8062 pr=118 pw=0 time=195 us)28281 INDEX RANGE SCAN I_BIG_EMP_DEPTNO_HIREDATE (cr=119 pr=118 pw=0 time=293037 us)
CREATE INDEX I_BIG_EMP_DEPTNO_HIREDATEON BIG_EMP(HIREDATE, DEPTNO, JOB);
SELECT DEPTNO, COUNT(*), SUM(SAL)FROM BIG_EMPWHERE HIREDATE BETWEEN '1983-01,01' AND '1984-12-31'AND DEPTNO IN ( 70, 80 , 90 )
GROUP BY DEPTNOORDER BY SUM(SAL) DESC;
![Page 7: [2015-06-26] Oracle 성능 최적화 및 품질 고도화 3](https://reader031.fdocuments.net/reader031/viewer/2022013108/55c2b05ebb61ebdd2b8b47c6/html5/thumbnails/7.jpg)
INDEX를 사용하지 못하는 경우
1. Column을 함수로 변경
(SQL문을 적절히 바꾸던가… 아니면 Function-based Index를 사용하던가)
2. 부정문으로 비교 (<>, !=, ^=, NOT =, NOT BETWEEN, NOT LIKE)
( NOT EXISTS (SELECT 1 FROM … WHERE … ) 로 대체 가능 )
3. IS NULL, IS NOT NULL로 비교
(Index에 NULL값은 없다. 즉 모든 값이 NOT NULL)
(IN NOT NULL 대신 > ‘ ’ 이런식의 존재하는 한 무조건 만족하는 조건으로 검색을 할 수 있다.)
4. LIKE 연산자에서 %(와일드카드)가 앞에 있는 경우
![Page 8: [2015-06-26] Oracle 성능 최적화 및 품질 고도화 3](https://reader031.fdocuments.net/reader031/viewer/2022013108/55c2b05ebb61ebdd2b8b47c6/html5/thumbnails/8.jpg)
Function-based INDEX
1. Oracle 8i 부터 지원
2. WHERE의 함수를 적용한 Column 자체를 INDEX로 생성
3. Cost-based Optimizer에서만 사용이 가능
SELECT * FROM BIG_EMP WHERE NVL(SAL,0) < 4000;
CREATE INDEX I_BIG_EMP_SAL ON BIG_EMP(SAL) CREATE INDEX I_BIG_EMP_NVL_SAL ON BIG_EMP(NVL(SAL,0))
Call Count CPU Time Elapsed Time Disk Query Current Rows------- ------ -------- ------------ ---------- ---------- ---------- ----------Parse 1 0.000 0.000 0 0 0 0Execute 1 0.000 0.000 0 0 0 0Fetch 225 0.016 0.018 0 408 0 22395------- ------ -------- ------------ ---------- ---------- ---------- ----------Total 227 0.016 0.019 0 408 0 22395
Rows Row Source Operation------- -----------------------------------------------------------------------
22395 TABLE ACCESS FULL BIG_EMP (cr=408 pr=0 pw=0 time=6177 uscost=52 size=52128 card=1448)
Call Count CPU Time Elapsed Time Disk Query Current Rows------- ------ -------- ------------ ---------- ---------- ---------- ----------Parse 1 0.000 0.000 0 0 0 0Execute 1 0.000 0.009 0 2 0 0Fetch 225 0.031 0.052 48 22098 0 22395------- ------ -------- ------------ ---------- ---------- ---------- ----------Total 227 0.031 0.061 48 22100 0 22395
Rows Row Source Operation------- -----------------------------------------------------------------------
22395 TABLE ACCESS BY INDEX ROWID BIG_EMP (cr=22098 pr=48 pw=0 time=73745 uscost=50 size=52128 card=1448)
22395 INDEX RANGE SCAN I_BIG_EMP_NVL_SAL (cr=273 pr=48 pw=0 time=51442 uscost=2 size=0 card=261)
![Page 9: [2015-06-26] Oracle 성능 최적화 및 품질 고도화 3](https://reader031.fdocuments.net/reader031/viewer/2022013108/55c2b05ebb61ebdd2b8b47c6/html5/thumbnails/9.jpg)
Full Table Scan의 성능을 개선시키기 위한 솔루션
1. DB_FILE_MULTIBLOCK_READ_COUNT = 128 block
(라고 설정은 되어 있으나 실제로는 80 ~ 90 정도 성능)
2. Parellel-Query-Option
(Server Processor 가 Parallel query processor들을 생성하여 동시에 읽음)
![Page 10: [2015-06-26] Oracle 성능 최적화 및 품질 고도화 3](https://reader031.fdocuments.net/reader031/viewer/2022013108/55c2b05ebb61ebdd2b8b47c6/html5/thumbnails/10.jpg)
INDEX 생성
CREATE INDEX 를 실행하면…
-> Index 구성 Column 들의 Data를 Sorting 하고, Min, Mid Max 값 계산
-> 최초 Extent 생성 : 첫번째 Block에 Root Block 생성하고 Mid값 저장
-> 다음 Block부터 Sorting 된 Data들 저장 (Leaf Block)
-> Leaf Block의 정보를 저장하고 있는 Block 생성 (Branch Block)
- 최초 생성되는 Leaf Block 들 : Level 1
-> 새로 Data가 추가되었는데 Leaf Block이 꽉 찬 경우 ?
-> 해당 Leaf Block에 중간값을 두고, 양쪽으로 새로운 Leaf Block을 생성 : Level 2
-> 이런 식으로 Depth (Level)이 깊어질 수록 성능이 안좋아진다.
![Page 11: [2015-06-26] Oracle 성능 최적화 및 품질 고도화 3](https://reader031.fdocuments.net/reader031/viewer/2022013108/55c2b05ebb61ebdd2b8b47c6/html5/thumbnails/11.jpg)
INDEX Balancing 분석
ANALYZE INDEX [index_name] VALIDATE STRUCTURE;
SELECT (DEL_LF_ROWS_LEN / LF_ROWS_LEN) * 100 AS BALANCINGFROM INDEX_STATS;
* INDEX_STATS
• INDEX 현재 구조 분석
• Block 수
• 삭제된 행의 길이
• INDEX DEPTH (HEIGHT)
![Page 12: [2015-06-26] Oracle 성능 최적화 및 품질 고도화 3](https://reader031.fdocuments.net/reader031/viewer/2022013108/55c2b05ebb61ebdd2b8b47c6/html5/thumbnails/12.jpg)
INDEX 재구성
ALTER INDEX [index_name] REBUILD [NOLOGGING]TABLESPACE [tablespace_name];
• Balancing이 20% 초과하면 성능 저하가 심하므로 재구성 하는게 좋음 (사후조치)
(그럼 사전조치는 ? 물리적 설계 : 빈번한 DML 고려)
• INDEX 삭제 후 재 생성
• On-Line rebuild 가능 (DBMS_REDEFINITION Package)
• Tablespace 위치 변경도 가능
![Page 13: [2015-06-26] Oracle 성능 최적화 및 품질 고도화 3](https://reader031.fdocuments.net/reader031/viewer/2022013108/55c2b05ebb61ebdd2b8b47c6/html5/thumbnails/13.jpg)
INDEX 합병 (B*Tree)
ANALYZE INDEX [index_name] COALESCE;
SELECT INDEX_NAME, LEAF_BLOCKSFROM USER_INDEXES;
SELECT NAME, BLOCKS, LF_BLKS, BR_BLKSFROM INDEX_STATS;
• INDEX Key 값을 재 배치
• 불필요한 Block 검색 및 공간 낭비를 방지
• 하지만 빈 Node를 반환해주지는 않음
![Page 14: [2015-06-26] Oracle 성능 최적화 및 품질 고도화 3](https://reader031.fdocuments.net/reader031/viewer/2022013108/55c2b05ebb61ebdd2b8b47c6/html5/thumbnails/14.jpg)
INDEX 압축 (B*Tree, IOT)
SELECT INDEX_NAME, COMPRESSIONFROM USER_INDEXES;
• 디스크 공간 절약I/O를 줄일 수 있으므로 검색속도 향상
(하지만 Transaction이 조금만 증가해도 느려질 수 있다)
• 대용량 Data에 적용하면 효율적
• Non-Partitioned Index에만 적용 가능
CREATE INDEX [index_name] ON [table_name]([column_name,...]) [ COMPRESS | NOCOMPRESS ];
![Page 15: [2015-06-26] Oracle 성능 최적화 및 품질 고도화 3](https://reader031.fdocuments.net/reader031/viewer/2022013108/55c2b05ebb61ebdd2b8b47c6/html5/thumbnails/15.jpg)
INDEX Monitoring
• INDEX는 SELECT의 성능을 올려주지만,
DML 들의 성능을 떨어트린다.
• Optimizer가 안 쓰는 INDEX는 과감히 삭제하자.
• 9i부터 가능
• 사용되지 않은 Index를 검색하여 삭제 가능
• Table 당 Index를 32개까지 생성은 가능하나,
Index가 많을 수록 DML문의 성능이 저하됨
ALTER INDEX [index_name] [ MONITORING | NOMONITORING ] USAGE;
SELECT INDEX_NAME, USEDFROM V$OBJECT_USAGE;
![Page 16: [2015-06-26] Oracle 성능 최적화 및 품질 고도화 3](https://reader031.fdocuments.net/reader031/viewer/2022013108/55c2b05ebb61ebdd2b8b47c6/html5/thumbnails/16.jpg)
INDEX 분석용 Script
SELECT X.TABLE_NAME, X.NUM_ROWS,A.INDEX_NAME, A.TABLESPACE_NAME,DECODE(A.UNIQUENESS, 'UNIQUE','U','N') "UNIQUE",B.COLUMN_NAME,Y.NUM_DISTINCT,A.PCT_FREE, A.CLUSTERING_FACTOR, A.BLEVEL, A.LEAF_BLOCKS,(C.DEL_LF_ROWS_LEN / C.LF_ROWS_LEN) * 100 BALANCE
FROM DBA_TABLES X, DBA_TAB_COLUMNS Y, DBA_INDEXES A, DBA_IND_COLUMNS B, INDEX_STATS CWHERE X.OWNER = 'SCOTT'AND A.TABLE_OWNER = X.OWNER AND A.TABLE_NAME = X.TABLE_NAMEAND A.TABLE_OWNER = B.INDEX_OWNER AND A.TABLE_NAME = B.TABLE_NAMEAND X.OWNER = Y.OWNER AND X.TABLE_NAME = Y.TABLE_NAMEAND B.COLUMN_NAME = Y.COLUMN_NAMEAND B.INDEX_NAME = C.NAME(+)ORDER BY X.TABLE_NAME
![Page 17: [2015-06-26] Oracle 성능 최적화 및 품질 고도화 3](https://reader031.fdocuments.net/reader031/viewer/2022013108/55c2b05ebb61ebdd2b8b47c6/html5/thumbnails/17.jpg)
Join 종류
Join description
Natural Join 결합조건이 = 인 일반적인 Join조건에 맞는 것만 출력( = Equal Join , Inner Join )
Cross Join 결합조건이 없는 Join전체와 전체를 다 묶음 (묻지마 Join)( = Catesian Product )
Self-reference Join 하나의 Table을 다른 Alias를 붙여서 Join(마치 다른 Table인 듯 취급)
Outer Join 기준이 되는 Table은 결합조건에 맞지 않아도 출력
1. 문법적 측면
![Page 18: [2015-06-26] Oracle 성능 최적화 및 품질 고도화 3](https://reader031.fdocuments.net/reader031/viewer/2022013108/55c2b05ebb61ebdd2b8b47c6/html5/thumbnails/18.jpg)
Join 종류
Join description
Sort-Merge Join/*+USE_MERGE(a b)*/
Join에 참여하는 Column에 Index가 없을 경우Full Table Scan -> 그 결과를 Sort한 후 Merge(즉 3번의 Load가 필요함)가장 느린 방법
Nested-Loops Join/*+USE_NL(a b)*/
Index를 이용하여 Join
Cluster Join Index보다 성능이 좋은 Cluster를 이용하여 Join
Hash Join/*+HASH(a b)*/
v7.3.3부터 가능 : SMJ가 넘 느려서 성능 개선을 위해 개발왠만해서는 SMJ보다 빠름Optimizer가 SMJ를 선택하는 경우는 거의 없다.결합조건 별로 Buffer에 파티션을 나누어 Record를 Load
2. 실행적 측면
![Page 19: [2015-06-26] Oracle 성능 최적화 및 품질 고도화 3](https://reader031.fdocuments.net/reader031/viewer/2022013108/55c2b05ebb61ebdd2b8b47c6/html5/thumbnails/19.jpg)
Join 성능에 영향을 주는 요소
1. Driving Table
2. Join 순서
3. Data 량
4. Index 사용여부
WHERE 절의 Check 조건으로 걸러지는 것 기준으로
Data량이 가장 작은 것을 Driving Table로
Driving Table과 결합조건이 있는 Table중
Data량이 가장 작은 것을 Join
만약 결합 조건 중 한쪽만 Index가 있다면,
Join 할 Table을 Index가 있는 Table로 결정
Driving Table 결정 원리 (Rule-based Optimizer)
- Join에 참여하는 Column에 모두 INDEX가 있거나 없는 경우 (동등조건) : FROM에서 먼 쪽부터
-> 단, Single Index와 Composite Index 중에서는 Composite Index부터,
-> Unique Index와 Non-unique Index 중에서는 Unique Index 부터,
- Outer Join은 Data가 있는 쪽부터
- /*+ORDERED*/ 하면 FROM에서 가까운 쪽부터
- /*+LEADING(A)*/ 하면 해당 Table 부터