Skip to content
튜닝 연습인덱스 스캔 효율과 테이블 액세스
ACC-018

상품 상세 화면이 열릴 때마다 조회 로그 1년 치를 훑는다

중급DDL이커머스93 / 700

이 문제는 교재 18화 졸업 과제와 같은 이커머스 데이터베이스를 씁니다. 『튜너의 1년』을 순서대로 읽고 있다면 졸업 과제를 먼저 풀고 오세요. 아래 「테이블과 인덱스」 칸에 과제의 답 일부(제약 조건, 인덱스, 통계의 실제 상태)가 나옵니다.

상황 ​

상품 상세 화면 오른쪽 위에는 「최근 1년 조회 n회」가 뜬다. 상세 화면은 하루 약 4만 번 열린다. 이 숫자를 세는 SQL은 밤마다 도는 「상품별 일 조회수」 집계 배치를 위해 만든 (view_date, product_id) 인덱스를 타는데, 한 번에 58블록을 읽는다. product_views는 상세 화면이 열릴 때마다 한 행씩 INSERT되는 로그 테이블이다.

테이블과 인덱스 ​

  • product_views 상품 조회 로그: 100,000행 · 367블록 · view_date DATE(시분초 있음) · 이 문제에서는 2020 ~ 2024년에 고르게 분포한다고 본다(하루 약 55건, 최근 1년 약 20,000행)
  • 상품 280개 · 상품당 평균 357행(최근 1년 평균 71행) · 아래 예시 상품은 최근 1년 74행
  • 인덱스: PK (view_id) · IX_PV_DT_PRD (view_date, product_id): 집계 배치용 · BLEVEL 1 · 리프 약 280블록(리프 한 블록에 약 360항목) · 통계 최신
  • 집계 배치(매일 02:00): view_date >= TRUNC(SYSDATE) - 1 AND view_date < TRUNC(SYSDATE)로 어제 하루를 상품별로 센다 · 하루 한 번

원본 SQL ​

sql
SELECT COUNT(*) AS view_cnt
  FROM product_views
 WHERE product_id = :p
   AND view_date >= ADD_MONTHS(TRUNC(SYSDATE), -12)
   AND view_date <  TRUNC(SYSDATE) + 1

실행계획 학습용 예시 · 행 수와 블록 수는 schemas 그대로 · 날짜 분포는 문제에 적은 가정 ​

xplan
---------------------------------------------------------------------------------------------
| Id  | Operation          | Name         | Starts | E-Rows | A-Rows |   A-Time   | Buffers |
---------------------------------------------------------------------------------------------
|   0 | SELECT STATEMENT   |              |      1 |        |      1 |00:00:00.01 |      58 |
|   1 |  SORT AGGREGATE    |              |      1 |      1 |      1 |00:00:00.01 |      58 |
|*  2 |   INDEX RANGE SCAN | IX_PV_DT_PRD |      1 |     71 |     74 |00:00:00.01 |      58 |
---------------------------------------------------------------------------------------------

Predicate Information (identified by operation id):
---------------------------------------------------
   2 - access("VIEW_DATE">=ADD_MONTHS(TRUNC(SYSDATE@!),-12) AND "PRODUCT_ID"=:P AND
              "VIEW_DATE"<TRUNC(SYSDATE@!)+1)
       filter("PRODUCT_ID"=:P)

문제 ​

  1. 상품 하나의 74건을 세는 데 58블록을 읽는 이유를 2번 줄로 설명하시오. 하루 4만 번이면 얼마인지도 계산하시오.
  2. 인덱스를 다시 설계해 DDL을 작성하시오. 새 인덱스를 더할지 기존 인덱스를 바꿀지 정하고, 집계 배치가 어떻게 되는지와 로그 테이블이라는 점을 근거로 설명하시오.
원본 SQL을 고쳐 쓰세요. 인덱스 DDL과 힌트도 쓸 수 있습니다.
무엇이 문제였고 왜 이렇게 고쳤는지 쓰세요.0자