MySQL Troubleshooting 발췌
MySql 서버는 언제나 입력한 대로 쿼리를 실행하지 않는다.
대신 사용자가 더 빨리 결과를 얻을 수 있도록 쿼리 옵티마이저를 호출하여 더 좋은 실행계획을 만든다.
테이블이 Index를 가지고 있지 않는 경우 MySql는 결과를 제한할 수 있을때 인덱스를 사용한다.
따라서 Where, JOIN, Group By, Order by 절에 들어가는 열이 인덱스를 가지고 있다면 성능이 향상된다.
※ EXPLAIN EXTENDED SELECT 구문을 사용한 후 SHOW WARNINGS 을 사용하면 최적화된 쿼리를 보여준다.
id |
select_type |
table |
partitions |
type |
possible_keys |
key |
key_len |
ref |
rows |
filtered |
Extra |
컬럼 설명
select_type :
단순 쿼리 : Simple
복합 쿼리
PRIMAY |
가장 바깥쪽 쿼리 |
UNION |
UNION 중 두번째 OR 나중에 따라오는 SELECT |
DEPENDENT UNION |
바깥쪽 쿼리에 종속적인 UNION 쿼리 |
UNION RESULT |
UNION 결과물 |
SUBQUERY |
서브쿼리의 첫번째 SELECT |
DEPENDENT SUBQUERY |
바깥쪽 쿼리에 종속적이고 서브쿼리 중 첫 SELECT |
DERIVED |
SELECT로 추출된 테이블 즉 FROM 절 내부의 쿼리(임시테이블) => 임시테이블은 메모리나 디스크에 저장이 가능 |
UNCACHEABLE SUBQUERY |
서브 쿼리 결과를 내부 캐시 공간에 저장하지 못하는 경우 1.사용자 변수가 서브쿼리에 사용된 경우 2.RAND()와 같이 결과 값이 호출될때마다 달라지는 함수가 subQuery에 사용되는 경우 |
UNCACHEABLE UNION |
Union 쿼리 결과가 내부 캐시 공간에 저장하지 못하는 경우 |
table : 접근하는 Table 명
type : 위에서부터 아래로 갈수록 성능 저하가 발생된다.
system |
테이블이 하나의 열만 가지고 있다. |
const |
하나의 매칭 테이블을 가지고 있는데 쿼리가 시작되는 시점에서 이 테이블을 읽게된다. 여기에는 하나의 열만 가지고 있기 때문에 이 열에 있는 컬럼에서 얻는 값들은 나머지 옵티마이저에 의해서 상수로 인식 될 수 있다. const 테이블은 한번 밖에 읽혀지지 않기때문에 매우 빠르다. |
eq_ref |
테이블로부터 각 열을 조합하기 위해 테이블의 열을 하나 읽는다. system 및 const 타입과는 달리 가장 최선의 가능 조인 타입이다. |
ref |
JOIN의 순서와 인덱스의 종류에 상관없이 인덱스로 지정된 컬럼끼리의 '=', '<=>'와 같은 연산자를 통한 비교로 수행되는 Join |
ref_or_null |
ref와 유사하지만 Null을 가지고 잇는 열에 대해서도 검색을 한다. |
unique_subquery |
Where 조건절에서 사용될 수 있는 IN 서브 쿼리에 대해서 ref를 대체한다. 단 하나의 결과만을 반환하는 서브쿼리에 사용 |
index_subquery |
unique_subquery와 유사하지만 여러개의 결과를 반환하는 경우에 사용한다. |
range |
특정한 범위의 열을 매칭하는데 인덱스가 사용되는 경우 |
index_merge |
2개 이상의 인덱스를 이용해 각각의 검색 결과를 만들어 낸 후 그 결과를 병합하는 처리 방식 |
index |
인덱스 풀 스캔 |
all |
테이블 풀 스캔 |
possible_keys : MySql이 해당 테이블 검색에 사용할 수 있는 인덱스들
key : MySql이 실제 사용한 Key(인덱스)
key_len : 인덱스의 길이, Key 컬럼이 Null이면 이것도 Null
ref : 행을 추출하는데 키와 함께 사용된 컬럼이나 상수 값
rows : 쿼리 수행에서 MySql이 검색해야하는 Row의 갯수(옵티마이저 연산에 따른 추정치)
JOIN 시 Type이 ALL인 경우 ROW 행들은 곱연산이 된다.
Extra : MySql이 이 쿼리를 해석한 추가적인 정보를 나타낸다.
distinct |
매치되는 첫 행을 찾는 즉시 검색을 중단 |
not exist |
LEFT JOIN시 한 행을 찾으면 더 이상 매치되는 행을 검색을 중단 |
range checked for each record(index map) |
사용할 좋은 인덱스가 없음을 의미 |
using filesort |
정렬을 하기 위해 추가적인 과정이 필요함. |
using index |
컬럼 정보를 실제 테이블이 아닌 인덱스 트리에서 추출한다. 쿼리에서 단일 인덱스된 컬럼들만 사용하는 경우 |
using temporary |
결과를 재사용하기 위해 임시테이블을 사용한다. 쿼리가 컬럼을 서로 다르게 목록화 하는 Group by나 Order By 구문을 가지고 있는 경우에 발생한다. |
using where |
Where 절이 다음 조인에 사용될 행이나 클라이언트에게 돌려질 행을 제한하는 경우이다. 테이블에서 모든 열을 검색하는 경우가 아니라면 쿼리에 문제가 생길 수 있다. 만일 가능한 빠른 쿼리를 만들고 싶다면 using filesort 및 using temporary 값을 조사하도록 한다. |
using sort_union, using_union, using_intersect, using index for group-by |
using index와 접근 방식이 같으며 추가적인 디스크 접근 없이 Group by나 Distinct 쿼리에 사용된 모든 컬럼에 대한 인덱스를 찾았음을 의미한다. |
'개발관련 > DB' 카테고리의 다른 글
Non clustered Index, clustered Index (0) | 2022.12.20 |
---|---|
MYSQL>FIND_IN_SET (0) | 2019.03.29 |
MYSQL>집계함수 곱연산 (0) | 2019.03.26 |
MSSQL>페이징 처리 (0) | 2017.07.04 |