옵티마이저와 힌트 1 정렬 알고리즘 레코드를 정렬할 때 레코드 전체를 소트 버퍼에 담을지 또는 정렬 기준 컬럼만 소트 버퍼에 담을지에 따라 "싱글 패스(Single-pass)"와 "투 패스(Tow-pass)" 두 가지 정렬 모드로 나눌 수 있다. 최신 버전에서는 일반적으로 싱글 패스 정렬 방식을 주로 사용하지만, 아래의 경우에는 싱글 패스 정렬 방식을 사용하지 못하고, 투 패스 정렬 방식을 사용한다. 레코드의 크기가 max_length_for_sort_data 시스템 변수에 설정된 값보다 클 때 BLOB이나 TEXT 타입의 칼럼이 SELECT 대상에 포함할 때 싱글 패스 정렬 방식 소트 버퍼에 정렬 기준(ORDER BY) 칼럼을 포함해 SELECT 대상이 되는 칼럼 전부를 담아서 정렬을 수행하는 방식이다..
MySQL에서 쿼리를 최적으로 실행하기 위해 각 테이블의 데이터가 어떤 분포로 저장되어 있는지 통계 정보를 참조하며, 그러한 기본 데이터를 비교해 최적의 실행 계획을 수립하는 작업이 필요하다. MySQL 서버를 포함한 대부분의 DBMS에서는 옵티마이저가 이러한 기능을 담당한다. 쿼리 실행 절차 MySQL 서버에서 쿼리가 실행되는 과정은 크게 세 단계로 나눌수 있다. 사용자로부터 요청된 SQL 문장을 잘게 쪼개서 MySQL 서버가 이해할 수 있는 수준으로 분리(파스 트리)한다. SQL의 파싱 정보(파스 트리)를 확인하면서 어떤 테이블로부터 읽고 어떤 인덱스를 이용해 테이블을 읽을지 선택한다. 두 번째 단계에서 결정된 테이블의 읽기 순서나 선택된 인덱스를 이용해 스토리지 엔진으로부터 데이터를 가져온다. 첫 ..
인덱스 1은 여기에서 확인하실 수 있습니다. 클러스터링 인덱스 클러스터링 인덱스는 테이블의 프라이머리 키에 대해서만 적용되는 내용이다. 즉, 프라이머리 키 값이 비슷한 레코드끼리 묶어서 저장하는 것을 클러스터링 인덱스라고 표현한다. 여기서 중요한 것은 프라이머리 키 값에 의해 레코드의 저장 위치가 결정된다는 것이다. 프라이머리 키 값이 변경된다면 그 레코드의 물리적인 저장 위치가 바뀌어야 한다는 것을 의미한다. 일반적으로 InnoDB와 같이 항상 클러스터링 인덱스로 저장되는 테이블은 프라이머리 키 기반의 검색이 매우 빠르지만, 레코드의 저장이나 프라이머리 키의 변경이 상대적으로 느리다는 특징이 있다. 위 그림의 클러스터링 인덱스 구조를 보면 클러스터링 테이블의 구조 자체는 일반 B-Tree와 비슷하지만,..
랜덤 I/O와 순차 I/O 랜덤 I/O라는 표현은 하드 디스크 드라이브의 플래터(원판)을 돌려서 읽어야 할 데이터가 저장된 위치로 디스크 헤더를 이동시킨 다음 데이터를 읽는 것을 의미하는데, 사실 순차 I/O 또한 이 작업 과정은 동일하게 이루어진다. 디스크에 데이터를 쓰고 읽는 데 걸리는 시간은 디스크 헤더를 움직여서 읽고 쓸 위치로 옮기는 단계에서 결정된다. 위 그림에서 순차 I/O는 디스크에 기록해야 할 위치를 찾기 위해 디스크의 헤드를 1번 움직였고, 랜덤 I/O는 디스크 헤드를 3번 움직였는데, 이는 순차 I/O는 랜덤 I/O보다 거의 3배 정도 빠르다고 볼 수 있다. 따라서 여러 번 쓰기 또는 읽기를 요청하는 랜덤 I/O 작업이 작업 부하가 훨씬 더 크다. 대부분의 작업은 이러한 작은 데이터를..
MySQL 5.7 버전부터 지원되기 시작한 데이터 암호화 기능은 처음에는 데이터 파일(테이블스페이스)에 대해서만 암호화 기능이 제공됐지만, MySQL 8.0으로 업그레이드되면서 데이터 파일뿐만 아니라 리두 로그나 언두 로그, 복제를 위한 바이너리 로그 등도 모두 암호화 기능을 지원하기 시작했다. MySQL 서버의 데이터 암호화 MySQL 서버의 암호화 기능은 아래 그림과 같이 데이터베이스 서버와 디스크 사이에 데이터 읽고 쓰기 지점에서 암호화 또는 복호화를 수행하기 때문에, 디스크 입출력 이외의 부분에서는 암호화 처리가 전혀 필요하지 않다. 즉, MySQL 서버(InnoDB 스토리지 엔진)의 I/O 레이어에서만 데이터의 암호화 및 복호화 과정이 실행되는 것이다. MySQL 서버에서 사용자의 쿼리를 처리하..
MySQL 서버에서 디스크에 저장된 데이터 파일의 크기는 일반적으로 쿼리의 처리 성능과도 직결되지만 백업 및 복구 시간과도 밀접하게 연결된다. 디스크의 데이터 파일이 크면 클수록 쿼리를 처리하기 위해서 더 많은 데이터 페이지를 InnoDB 버퍼 풀로 읽어야 할 수도 있고, 새로운 페이지가 버퍼 풀로 적재되기 때문에 그만큼 더티 페이지가 더 자주 디스크로 기록돼야 한다. 그리고 데이터 파일이 크면 클수록 백업 시간이 오래 걸리며, 복구하는 데도 그만큼의 시간이 걸린다. 때문에 많은 DBMS에서 이런 문제를 해결하기 위해 데이터 압축 기능을 제공한다. MySQL 서버에서 사용 가능한 압축 방식은 크게 테이블 압축과 페이지 압축의 두 가지 종류로 구분할 수 있는데, 두 방식은 매우 다르게 작동하므로 하나씩 구..
트랜잭션 및 잠금에 관한 내용은 여기에서 확인하실 수 있습니다. 트랜잭션의 격리 수준(Isolation Level)이란, 여러 트랜잭션이 동시에 처리될 때 특정 트랜잭션이 다른 트랜잭션에서 변경하거나 조회하는 데이터를 볼 수 있게 허용할지를 결정하는 것이다. 격리 수준은 크게 READ UNCOMMITED, READ COMMITED, REPEATABLE READ, SERIALIZABLE 4가지로 나뉘는데, "DIRTY READ"라고도 하는 READ UNCOMMITED는 일반적인 데이터베이스에서는 거의 사용하지 않고, SERIALIZABLE 또한 동시성이 중요한 데이터베이스에서는 거의 사용되지 않는다. 4개의 격리 수준에서 순서대로 뒤로 갈수록 각 트랜잭션 간의 데이터 격리(고립)정도가 높아지며, 동시 처리..
트랜잭션에 관한 내용은 여기에서 확인하실 수 있습니다. 잠금은 여러 커넥션에서 동시에 동일한 자원(레코드나 테이블)을 요청할 경우 순서대로 한 시점에는 하나의 데이터만 변경할 수 있게 해주는 역할을 한다. MySQL 엔진의 잠금 MySQL에서 사용되는 잠금은 크게 스토리지 엔진 레벨과 MySQL 엔진 레벨로 나눌 수 있다. MySQL 엔진은 MySQL 서버에서 스토리지 엔진을 제외한 나머지 부분으로 이해하면 되는데, MySQL 엔진 레벨의 잠금은 모든 스토리지 엔진에 영향을 미치지만, 스토리지 엔진 레벨의 잠금은 스토리지 엔진 간 상호 영향을 미치지는 않는다. MySQL 엔진에서는 테이블 데이터 동기화를 위한 테이블 락 이외에도 테이블의 구조를 잠그는 메타데이터 락(Metadata Lock), 사용자의 ..
트랜잭션은 작업의 안정성을 보장해주는 것이다. 즉, 논리적인 작업 셋을 모두 완벽하게 처리하거나, 처리하지 못할 경우에는 원 상태로 복구해서 작업의 일부만 적용되는 현상(Partial update)이 발생하지 않게 만들어주는 기능이다. 잠금(Lock)과 트랜잭션은 서로 비슷한 개념 같지만 사실 잠금은 동시성을 제어하기 위한 기능이고, 트랜잭션은 데이터의 정합성을 보장하기 위한 기능이다. 하나의 회원 정보 레코드를 여러 커넥션에서 동시에 변경하려고 하는데 만약 잠금이 없다면 하나의 데이터를 여러 커넥션에서 동시에 변경할 수 있게 되고, 결국 해당 레코드의 값은 예측할 수 없는 상태가 된다. 트랜잭션 지금은 많이 달라졌지만 여전히 MySQL 서버에서는 MyISAM이나 MEMORY 스토리지 엔진이 더 빠르다고..
InnoDB 스토리지 엔진 아키텍처 1 InnoDB 스토리지 엔진 아키텍처 2 InnoDB 스토리지 엔진 아키텍처 3 MyISAM 스토리지 엔진 아키텍처 이번에는 MyISAM 스토리지 엔진의 성능에 영향을 미치는 요소인 키 캐시와 운영체제의 캐시/버퍼에 대해 살펴보자. 아래는 MyISAM의 간략한 구조이다. 키 캐시 InnoDB의 버퍼 풀과 비슷한 역할을 하는 것이 MyISAM의 키 캐시(Key cache, 키 버퍼라고도 불림)다. 하지만 이름 그대로 MyISAM 키 캐시는 인덱스만을 대상으로 작동하며, 또한 인덱스의 디스크 쓰기 작업에 대해서만 부분적으로 버퍼링 역할을 한다. key_reads는 인덱스를 디스크에서 읽어 들인 횟수를 저장하는 상태 변수이며, key_read_requests는 키 캐시로부..
- Total
- Today
- Yesterday
- 백준
- 인프런
- 스프링 부트
- 스프링부트
- kotlin
- 릿코드
- 노마드
- 파이썬
- 자료구조
- 김영한
- 문자열
- mysql 8.0
- 그리디
- 알고리즘
- webflux
- 구현
- 북클럽
- MySQL
- 노마드코더
- 데이터베이스
- Algorithm
- 코틀린
- 정렬
- Spring
- 코테
- leetcode
- Real MySQL
- spring boot
- 리팩토링
- 스프링
일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
1 | 2 | 3 | 4 | |||
5 | 6 | 7 | 8 | 9 | 10 | 11 |
12 | 13 | 14 | 15 | 16 | 17 | 18 |
19 | 20 | 21 | 22 | 23 | 24 | 25 |
26 | 27 | 28 | 29 | 30 | 31 |