본문 바로가기

DB

(31)
MySQL 쿼리 작성 및 최적화 쿼리 작성에 필요한 기초 지식 MySQL은 영어 대소문자를 구분한다. 이유는 통상적으로 DB 내용이 디렉토리나 파일로 관리되는데 윈도우OS에선 디렉토리나 파일의 대소문자를 구분하지 않지만, 유닉스 계열에서는 대소문자를 구분하기 때문이다. 설정 파일에서 모두 소문자로만 저장되도록 할 수 있긴하다. 리터럴 표기법 문자열은 항상 홑 따옴표(')로 감싼다. 예약어와 충돌이 예상되는 경우 백 틱(`)으로 감싼다. (사실 예약어는 되도록 다른 곳에 사용하지 않는 게 정석이다.) 문자열과 상수 비교 시 숫자를 우선으로 하여 문자를 숫자로 변환한다. 숫자 값을 상수로 SQL에서 사용할 때는 DBMS가 자동으로 타입에 맞게 변경해준다. SELECT * FROM tab_test WHERE number_column='100..
MySQL의 동작 방식 MySQL의 주요 동작 방식 MySQL이 일련의 쿼리를 수행할 때 동작하는 방식에 대해서 이해해본다. 세세한 부분까지 다 파악한다기보다 일반적인 쿼리 사용자 레벨에서 주의를 기울여야 하는 부분만 알아본다. 풀 스캔 인덱스를 타지 않고 스토리지 엔진이 처음부터 끝까지 전부 다 읽어서 요청된 작업을 처리하는 방법이다. MySQL은 언제 풀 테이블 스캔 방식을 실행계획으로 선택하는가? 테이블의 레코드 건 수가 너무 적어서 인덱스를 통해 읽는 것 보다 풀 테이블 스캔이 빠를 것으로 예상되는 경우 WHERE 절이나 ON 절에 인덱스를 이용할 수 있는 적절한 조건이 없는 경우 인덱스 레인지 스캔을 사용할 수 있는 경우더라도 조건에 일치하는 레코드 건수가 너무 많을 것으로 예상되는 경우 ORDER BY 처리(Usin..
MySQL LIMIT 최적화(feat. 구글이 검색결과를 최대 1,000건만 제공하는 이유) 제가 말하는 것이 사실도, 정답도 아닐 수 있으니 비판적으로 읽어주시면 감사하겠습니다. MySQL LIMIT 최적화하는 방법 MySQL에서 페이징 처리를 위하여 LIMIT 키워드를 제공한다. 오라클에서는 페이징 처리를 위해 rownum 으로 레코드에 번호를 부여하고 WHERE 절에 조건 걸어서 일일이 페이징 처리하던 것에 비해 훨씬 편리하여 자주 사용된다. 이러한 페이징 처리 방법을 오프셋(offset) 페이징이라 한다. MySQL에서 제공하는 LIMIT 즉, 오프셋 페이징에는 치명적인 단점이 있다. 그것은 바로 오프셋 만큼 레코드를 읽어온 후에 필요한 레코드 수를 제외한 "나머지는 버리는 방식"으로 동작하는 것이다. 예를 들어 쿼리가 SELECT ... LIMIT 5000000, 10 처럼 LIMIT ..
MySQL 실행 계획(좋은 쿼리는 못 만들어도 뭐같은 쿼리는 만들지 말아야지) DB의 꽃 옵티마이저의 실행 계획 수립 RDBMS에서 가장 복잡하면서 가장 중요한 것은 옵티마이저(Optimizer)가 쿼리를 어떻게 실행할지 실행 계획을 결정하는 부분이다. 똑같은 쿼리라 할지라도 다양한 방법과 순서로 실행 될 수 있다. 어떤 실행 계획이 좋고 어떤 실행 계획이 안 좋은지 판단하는 건 온전히 옵티마이저의 몫이지만 개발자 역시도 어떤 실행 계획으로 수행되어야 좋은지를 알아야 최적의 실행 계획을 사용할 수 있도록 옵티마이저에게 힌트를 줄 수 있기 때문에 중요하고 반드시 학습해야하는 부분이다. 사전 지식 실행 계획에 대해 자세히 살펴보기 전에 아래의 사전 지식이 있어야 한다. 쿼리 실행 절차 SQL을 SQL 파서가 파싱하여 파서 트리(parser tree)를 만든다. 파서 트리를 기준으로 옵..
MySQL 인덱스 구조와 원리의 이해 인덱스란? 어떤 문제를 해결하기 위한 기술인가 관계형 데이터베이스는 기본적으로 데이터 영속화라는 목적이 있는 기술이다. 쉽게 말하면 어떤 애플리케이션에 필요한 데이터를 유지(저장)하는데 목적이 있다. 그러나 단순히 저장만 하는 게 아니라 저장된 데이터를 가지고 서비스를 해야 한다. 그렇다 보니 수많은 데이터 중에서 특정 조건을 만족하는 데이터를 조회하는데 일일이 검사를 하게 되면 조회 시간이 점차 증가하게 되기 마련이다. (이것은 성능 저하이자 곧 서비스 품질 저하다.) 데이터를 하나하나 전부다 조건을 검사하게 되면 검색 성능이 매우 떨어지는 문제가 발생하는데 이 문제를 해결하기 위한 기술이 바로 인덱스다. 어떻게 해결하는지 쉽게 설명하면, 일반적으로 책 뒤에 "색인"처럼 어느 페이지에 어떤 단어가 있는..
MySQL 트랜잭션과 락 - InnoDB 락, 이렇게 동작한다! 트랜잭션과 락(Transaction, Lock) 트랜잭션과 락 트랜잭션 : 논리적인 작업 단위로 전부 처리되거나 처리되지 않는 (commit/rollback) 원자성을 보장하기 위한 기능이다. 락 : 서로 다른 작업에서 같은 자원을 동시에 필요로 할 때 자원 경쟁이 일어나는데, 이때 순서대로 사용되는 동시성을 보장하기 위한 기능이다. MySQL에서 사용되는 락(LocK)은 크게 MySQL 엔진 레벨의 락과 스토리지 엔진 레벨의 락으로 나눠볼 수 있다. 스토리지 엔진 레벨의 락 스토리지 엔진(InnoDB)에서 제공하는 락(Lock, 잠금)이 있다. 기본적으로 비관적 락(Pessimistic locking)을 사용한다. 비관적 락 : 트랜잭션에서 변경하려는 레코드에 대해 락을 획득하고 쿼리를 수행하는 방식 ..
MySQL 아키텍처 (MySQL 엔진 구조, 스토리지 엔진 구조, 스레드 구조, 메모리 구조, 쿼리 실행 구조, Replication 구조) MySQL 서버 = MySQL 엔진 + 스토리지 엔진 MySQL 서버는 크게 MySQL 엔진과 스토리지 엔진으로 나눠볼 수 있다. MySQL 엔진은 클라이언트로부터 오는 요청 처리(요청된 SQL 문장을 분석, 최적화, ...)를 담당하고, 스토리지 엔진은 실제 데이터를 디스크 스토리지에 저장하거나 조회하는 부분을 담당한다. MySQL 엔진 Connection Handler : 커넥션 및 쿼리 요청을 처리 담당 SQL 인터페이스 : DML, DDL, Procedure, View 등 SQL 인터페이스 제공 담당 SQL 파서(parser) : SQL문법 오류 탐지 및 SQL 쿼리 문장을 MySQL이 처리하기 좋은 토큰 단위로 나눠서 트리 형태로 파싱 하는 작업 담당 SQL 옵티마이저(optimizer) : 쿼..
데이터베이스 성능 개선 포인트! 데이터베이스 Call 수 줄이기, 네트워크 부하 줄이기(array processing, 부분 범위 처리) 데이터베이스 SQL 쿼리 호출(Call) 수 줄이기 DB 성능 최적화를 하기 위해서 가볍게 개선 포인트를 알아보는 시간을 지난 포스트에 이어 갖는다.지난 포스트에서는 SQL 쿼리가 날라왔을 때 SQL 쿼리를 파싱하고 실행 계획을 캐시하고 최적화하는 부분을 살펴봤다.이번 포스트에서는 애초에 데이터베이스에 쿼리를 적게 날리는 즉, 호출 수를 줄이는 부분과 오고가는 데이터의 양(네트워크 부하)을 줄이는 부분을 알아볼 것이다.(다음 포스트에서는 데이터베이스가 파일시스템(ex. SSD)과 데이터 I/O하는 부분에서 최적화를 알아볼 것이다. 아래 그림을 참조하면 좋다.)데이터베이스 Call과 성능 위에서는 편의를 위해 애플리케이션을 통해 호출되는 Call이 전부인양 말했지만 엄밀히 따지면 Call을 종류는 다양하다..