Real MySQL 8.0 - 4장 (1)

minyeob·2024년 8월 13일
0

DB

목록 보기
1/6
post-thumbnail

MySQL 서버 구분

  • MySQL 엔진(두뇌)
    • 사용자 접속, 쿼리 요청을 처리, SQL 파싱 및 옵티마이저 담당하는 부분
  • 스토리지 엔진(손,발)
    • InnoDB, MyISAM, Memory 등이 있다.
    • 데이터를 실제로 어떻게 저장하고 읽어올지 담당하는 부분
    • 각 테이블 마다 다른 종류의 스토리지 엔진을 사용하는것이 가능하다.

MySQL의 전체 구조

핸들러 API

MySQL 엔진에서 Inno DB와 같은 스토리지 엔진에 데이터 읽기, 쓰기 요청을 헨들러 요청이라고 한다.

따라서 MySQL 엔진의 쿼리 실행기에서 데이터를 쓰거나 읽고자 할때 MySQL 엔진과 스토리지 엔진 사이에 데이터를 주고 받기 위해 ‘핸들러 API’ 를 사용하여 주고 받는다.


MySQL의 스레딩 구조

MySQL 서버는 멀티 프로세스 기반이 아니라 멀티 스레드 기반으로 작동한다. 그리고 크게 포그라운드 스레드와 백그라운드 스레드로 나뉠수 있다.

MySQL의 포그라운드 스레드(=클라이언트 스레드, 사용자 스레드)

사용자의 요청을 처리하는 스레드

데이터를 읽는 작업을 처리한다. 디스크에 직접 데이터를 쓰는 작업은 백그라운드 스레드에서 일어남.

데이터 캐시나 버퍼에서 데이터를 읽어오며, 만약 캐시나 버퍼에 데이터가 없으면 디스크나 인덱스파일에 데이터를 직접 읽어와 처리하기도 한다.

현재 MySQL에 접속된 클라이언트의 수 만큼 포그라운드 스레드가 존재한다.

MySQL의 백그라운드 스레드

디스크에 데이터를 직접 기록하는 작업은 백그라운드 스레드에서 일어난다.

현재 로그나, 버퍼풀에 있는 데이터를 디스크에 기록

기록 이외에 데이터를 버퍼로 읽어오거나, 락, 데드락 모니터하는 백그라운드 쓰레드도 존재한다.

MySQL(InnoDB)이 스레드를 포그라운드, 백그라운드로 나뉜 이유?

읽기 요청의 처리와 쓰기 요청의 처리를 분리하기 위함.

사용자의 요청을 처리하는 도중 데이터의 쓰기 작업은 지연되어 처리될 수 있지만, 데이터의 읽기 작업은 절대 지연될 수 없기 때문이다.


MySQL이 사용하는 메모리 영역

MySQL 에서 사용하는 메모리 영역은 크게 글로벌 메모리 영역과 로컬 메모리 영역으로 나뉜다.

글로벌 메모리 영역

MySQL 시작시 운영체제로 부터 할당받는 클라이언트 수와 무관하게 할당받는 모든 스레드가 공유하는 메모리 영역

버퍼, 캐시를 위해 사용된다.

대표적으로 InnoDB의 버퍼풀이 있다.

로컬 메모리 영역 (=세션 메모리 영역, 클라이언트 메모리 영역)

포워드 스레드(=클라이언트 스레드)가 사용자의 쿼리를 처리하기 위해 사용하는 메모리 공간

로컬 메모리 영역은 스레드별로 독립적으로 할당되며 절대 공유되지 않는다.

대표적으로 커넥션 버퍼나 정렬이나, 조인할때 사용하는 버퍼 등이 있다.

커넥션 버퍼나 결과 버퍼는 커넥션이 열려있는 동안 계속 메모리 공간에 남아있으며, 조인이나 정렬할때 사용되는 버퍼는 쿼리를 실행하는 순간에만 메모리공간에 할당 되었다가 해제된다.


플러그인 스토리지 엔진 모델

플러그인

MySQL에서 기본적으로 제공되는 기능 이외에 부가적인 기능을 더 제공하기 위한 방법으로 플러그인 모델을 사용한다.

InnoDB 또한 플러그인 형태로 제공되는 하나의 스토리지 엔진에 해당한다.

스토리지 엔진 뿐만아니라 3장에서 살펴보았던, 사용자 인증을위한 Native Authentication, Caching SHA-2 Authentication과 같은 인증 모듈들도 전부 플러그인이다.

스토리지 엔진 확인 하기 - SHOW ENGINES

MySQL 서버에 포함되지 않은 스토리지 엔진을 사용하려면 MySQL 서버를 다시 빌드해야 한다. 하지만 플러그인 형태로 빌드된 스토리지 엔진 라이브러리를 다운로드해서 끼워넣기만 하면 손쉽게 사용할 수 있다.

플러그인 확인 하기 - SHOW PLUGINS;

스토리지 엔진 뿐만 아니라 인증이나 전문 검색 파서, 쿼리 재작성과 같은 기능을 플러그인 형태로 지원한다.


컴포넌트(MySQL 8.0부터)

MySQL 8.0부터 플러그인 아키텍처를 대체하기 위해 등장한 개념

플러그인 아키텍처의 단점

⇒ 플러그인들 끼리 통신이 안되고, 플러그인끼리의 상호 의존관계 설정이 안됨

⇒ 플러그인은 MySQL 서버의 변수나 함수를 직접 호출하기 때문에(캡슐화가 안되어있음) 안전하지 않음


쿼리 실행 구조

  1. 사용자 요청

  2. 쿼리 파서에서 쿼리 문장을 토큰으로 분리해 트리형태의 구조로 재구성⇒ 쿼리 문장의 기본 문법 오류 발견

  3. 전처리기 ⇒ 쿼리 구조적 오류, 테이블, 컬럼이름 검증, 권한 검증

  4. 옵티마이저 ⇒ 쿼리 문장을 저렴한 비용으로 가장 빠르게 처리할지 결정

  5. 쿼리실행기 ⇒ 옵티마이저에서 만든 계획대로 핸들러에게 실제 요청을 주고받음

  6. 스토리지엔진 ⇒ 실제 데이터를 디스크로부터 읽고 쓰는 작업을 수행


복제

데이터를 “물리적으로 다른 서버의 저장 공간” 안에 동일한 데이터를 복사하는 기술


쿼리 캐시

빠른 응답을 위해 SQL 실행 결과를 캐싱해두는 기능

캐시 저장결과가 실제 데이터와 달라지면 모두 삭제 해야하는 문제가 발생하고 이 과정에서 성능저하 유발

결과적으로, 8.0 부터 쿼리 캐시는 MySQL 서버의 기능에서 제거 됨


스레드 풀

내부적으로 사용자의 요청을 처리하는 스레드 개수를 줄여서 동시 처리되는 요청이 많다 하더라도 MySQL 서버의 CPU가 제한된 개수의 스레드 처리에만 집중할 수 있게 하여 서버의 자원 소모를 줄인다.

스레드 풀은 기본적으로 CPU 개수만큼 스레드 그룹을 생성하는데, 스레드 그룹의 개수는 thread_pool_size 시스템 변수를 변경해서 조정할 수 있다.


트랜잭션 지원 메타데이터

8.0 버전 부터는 ㄴ데이터베이스 서버에서 테이블의 구조정보 같은 메타데이터를 테이블에 모두 저장하도록 개선하여 기존의 파일 기반의 메타데이터 생성으로 인한 비정상 종료 시, 테이블이 깨지는 현상을 해결하였다.

profile
백엔드 개발자를 꿈꾸며 공부한 내용을 기록하고 있습니다.

0개의 댓글