[Real MySQL] 06. 데이터 압축

예니·2023년 2월 4일
0

Real MySQL

목록 보기
5/9
post-thumbnail

MySQL 서버에서 디스크에 저장된 데이터 파일의 크기는 일반적으로 쿼리의 처리 성능과도 직결되지만 백업 및 복구 시간과도 밀접하게 연결된다.

6.1 페이지 압축

  • Transparent page compression 라고도 한다. MySQL 서버가 디스크에 저장하는 시점에 데이터 페이지가 압축되어 저장되고, 반대로 MySQL 서버가 디스크에서 데이터 페이지를 읽어올 때 압축이 해제된다. 버퍼 풀에 데이터 페이지가 한 번 적재되면 InnoDB 스토리지 엔진은 압축이 해제된 상태로만 데이터 페이지를 관리한다. 그래서 MySQL 서버의 내부 코드에서는 압축 여부와 관계없이 투명하게 작동한다.
  • 펀치 홀 페이지를 유지하면서도 압축된 다양한 크기의 데이터 페이지를 디스크에 저장하고 압축된 만큼의 공간을 절약할 수 있다.
  • 문제는 이 펀치 홀 기능이 운영체제뿐만 아니라, 하드웨어 자체에서도 해당 기능을 지원해야 사용 가능하다는 점이다. 이런 이유로 실제 페이지 압축은 많이 사용되지 않는다.

6.2 테이블 압축

테이블 압축은 운영체제나 하드웨어에 대한 제약 없이 사용할 수 있기 때문에 활용도가 높다.

  • 단점
    • 버퍼 풀 공간 활용률이 낮음
    • 쿼리 처리 성능이 낮음
    • 빈번한 데이터 변경 시 압축률이 떨어짐

6.2.1 압축 테이블 생성

  • 테이블 압축을 사용하기 위한 전제 조건으로 압축을 사용하려는 테이블이 별도의 테이블 스페이스를 사용해야 한다.
  • KEY_BLOCK_SIZE 옵션을 이용해 압축된 페이지의 타깃 크기를 명시하는데, 2n으로만 설정할 수 있다.
  • 테이블 압축 방식에서 가장 중요한 것은 원본 데이터 페이지의 압축 결과가 목표 크기(KEY_BLOCK_SIZE)보다 작거나 같을 때까지 반복해서 페이지를 스플릿하는 것이다. 그래서 목표 크기가 잘못 설정되면 MySQL 서버 처리 성능이 급격히 떨어질 수 있다.

6.2.2 KEY_BLOCK_SIZE 결정

  • 테이블 압축에서 가장 중요한 부분은 압축된 결과가 어느 정도 될지를 예측해서 KEY_BLOCK_SIZE를 결정하는 것이다.
  • 압축 실패율은 3~5% 미만으로 유지할 수 있게 KEY_BLOCK_SIZE를 선택하는 것이 좋다.
  • 압축 실패율이 높다고 해서 압축을 사용하면 안되는 것은 아니다. 로그 테이블의 경우, 한 번 삽입되면 다시는 변경되지 않기 때문에 압축이 실패해서 재압축하더라도, 최종적으로 크기가 줄어든다면 큰 손해는 아닐 것이다.
  • 압축 실패율이 낮아도 테이블의 데이터가 매우 빈번하게 조회되고 변경된다면 압축은 하지 않는 것이 좋다.

6.2.3 압축된 페이지의 버퍼 풀 적재 및 사용

  • InnoDB 스토리지 엔진은 압축된 테이블의 데이터 페이지를 버퍼 풀에 적재하면 압축된 상태와 압축이 해제된 상태 2개 버전을 관리한다. 디스크에서 읽은 상태 그대로의 데이터 페이지 목록을 관리하는 LRU 리스트와 압축된 페이지들의 압축 해제 버전인 Unzip_LRU 리스트를 별도로 관리하게 된다.
  • 압축된 테이블에 대해서는 버퍼 풀의 공간을 이중으로 사용함으로써 메모리를 낭비하게 된다.
  • 위의 메모리 낭비 문제를 보완하기 위해 Unzip_LRU 리스트를 별도로 관리하고 있다가 MySQL 서버로 유입되는 요청 패턴에 따라 적절히 처리한다.
    • 버퍼 풀의 공간이 필요한 경우, Unzip_LRU 리스트에서 압축 해제된 버전을 제거한다.
    • 압축된 데이터 페이지가 자주 사용된다면, Unzip_LRU 리스트에서도 계속 유지한다.
    • 압축된 데이터 페이지가 사용되지 않아서 LRU 리스트에서 제거된다면, Unzip_LRU 리스트에서도 함께 제거한다.
  • 버퍼 풀에서 압축 해제된 버전의 데이터 페이지를 적절한 수준으로 유지하기 위해 다음과 같은 어댑티브 알고리즘을 사용한다.
    • CPU 사용량이 높은 서버에서는 가능하면 압축과 압축 해제를 피하기 위해, Unzip_LRU의 비율을 높게 유지한다.
    • Disk IO 사용량이 높은 서버에서는 가능하면 Unzip_LRU 리스트의 비율을 낮춰서 InnoDB 버퍼 풀의 공간을 더 확보한다.

6.2.4 테이블 압축 관련 설정

페이지의 압축 실패율을 낮추기 위해 필요한 튜닝 포인트가 될 수 있는 시스템 변수를 제공한다.

  • innodb_cmp_per_index_enabled 테이블 압축이 사용된 테이블의 모든 인덱스별로 압축 성공 및 압축 실행 횟수를 수집하도록 설정한다.
  • innodb_compression_level 압축률을 설정할 수 있다. 숫자가 클수록 압축률이 높아진다. 압축 속도가 빠르다는 것(압축률이 낮음)은 CPU 자원을 적게 사용한다는 의미다.

0개의 댓글