스타트업에 현재 기존 개발자가 나간 상태, 1인 개발자 나 혼자 남은 상태에서 DB를 봤을 때 상태가 전혀 괜찮지 않았다. FK가 없으면 그것대신 트리거라도 있어야 하는데, 그야말로 그냥 테이블만 띡! 있는 관계형 데이터베이스의 의미가 존재하지 않는 상태인 것이다. 그래서 데이터베이스 리팩토링을 대표님에게 제안했고, 최소 6개월 최대 1년을 받아냈다. 기획과 설계에 약 6개월 이상을 잡고, 실제 설계를 3개월로 잡았으니 기간은 제법 넉넉하다. 현재 서비스가 초기 상태이기에 사용하는 테이블이 9개, 스키마가 100개 이내인 것을 생각해볼 때 지금이 바로잡기에 제일 좋은 시기임은 확실하니까 반드시 지금 해야한다는 생각이 가득했다. 또, 내 최종 목표인 DBA가 되기 위해서 엄청난 기회라고 생각한 것도 있다!..
DBMS
회사에 들어오고, 제일 큰 일 중에 하나가 주기적 데이터 갱신과 함께 view를 업데이트하는 것에 있었다.그래서 업데이트를 하게 되는데, 하다하다 이게 시간이 너무 걸리는 것이 아닌가? 열심히 하는데, view 업데이트 시간이 거의 한시간이 넘어가는 상황에 가만히 바라보다가 여러가지를 알게 되었다. Materialized view는 일반 view와는 다르게 사용자가 직접 업데이트 명령어를 실행해야 한다. view와 같이 물리적 데이터 없이 논리적 접근을 하는 게 아니라, 업데이트 명령을 통해 물리적으로 db에 적용이 된다. 복잡한 다중 쿼리를 사용할 수 있는 대신, 물리적으로 적재가 되기 때문에 그에 따른 비용이 발생하고, update를 실행하면 업데이트 되는 것만 가져가는 것이 아니라, 전체를 다시 ..
🪡 Nested Loop Join 💡기본 메커니즘중첩 루프의 기본적인 구조는 다른 프로그래밍 언어와 다르지 않다. 자바의 for 문을 생각한다면 다음과 같다.for(int i = 0; i 이와 같은 중첩 for문을 생각하고, NL Join을 생각하면 이것도 같은 구조로 돌아간다는 것을 알 수 있다.이것을 쿼리로 본다면 아래와 같다./* PL/SQL */begin for outer in (select deptno, empno, rpad(ename, 10) ename from emp) loop -- outer 루프 for inner in (select dname from dept where deptno = outer.deptno) loop -- inner 루프 dbms_output.put_li..
✨ B*Tree 인덱스를 정상적으로 사용하기 위해서는 범위 스캔 시작지점을 찾기 위하여 루트 블록부터 리프 블록까지의 수직적 탐색 과정을 거쳐야 한다. 만약, 인덱스 선두 칼럼이 조건절에 사용되지 않을 경우 범위 스캔에 대한 시작점을 찾을 수 없기 대문에 옵티마이저는 인덱스 전체 스캔을 하거나 테이블 전체 스캔 방식을 선택한다. 그렇다면 효율적인 인덱스 사용을 위해 어떤 조건이 있고, 어떤 방향으로 해결할 수 있는지 생각해보자. 🪡 범위 스캔 또는 인덱스 사용 불가능한 경우? 1. 범위 스캔이 불가능하거나 인덱스 사용이 아예 불가능한 경우- 인덱스 선두 컬럼을 조건절에서 가공- 부정형 비교를 사용 ( , not null)2. 인덱스 칼럼을 가공할 경우3. 형변환에 문제가 생길..
✨ 인덱스? 책의 제일 뒤를 보면 인덱스가 존재한다. 기준에 따라 정렬이 되어있고, 같은 키워드일 경우 페이지 순의 정리가 되어 있다.이와 같이 인덱스를 이용하면 원하는 키워드를 포함한 페이지를 빠르게 찾을 수 있다. 🪡 인덱스 구조 인덱스는 다양한 구조를 제공하는데, 기본적으로 원하는 데이터를 찾기 쉽도록 한다는 것이 동일하다. 그러나, DBMS마다 null 값을 다루는 방식 등의 세부적 차이가 있으므로 반드시 숙지하는 것이 중요하다. 🐣인덱스 탐색 수평적 탐색 - 인덱스 리프 블록에 저장된 레코드끼리 연결 순서에 따라 좌 또는 우, 우 또는 좌에서 스캔한다. 수직적 탐색 - 수평적 탐색을 위한 시작 지점을 찾는 과정으로, 루트에서 리프 블록까지 아래쪽으로 진행한다. 🧶 인덱스 스캔 방식 🐣Index ..
✨ 옵티마이저? 옵티마이저(Optimizer)는 SQL을 가장 빠르고 효율적으로 수행할 최적의 처리경로를 생성해주는 DBMS 내부의 핵심엔진이다. 사용자가 구조화된 질의언어(SQL)로 결과집합을 요구하면, 이를 생성하는데 필요한 처리경로는 DBMS에 내장된 옵티마이저가 자동 생성해준다. 이렇게 생성된 경로를 실행계획(Execution Plan)이라고 부르며, 최적화 과정은 다음과 같다. 1) 사용자가 던진 쿼리 수행을 위해, 후보군이 될만한 수행계획을 찾는다 2) 데이터 딕셔너리(Data Dictionary)에 미리 수집해 놓은 오브젝트 통계 및 시스템 통계정보를 이용해 각 실행계획의 예상비용을 산정한다. 3) 각 실행계획을 비교해서 최저비용을 갖는 하나를 선택한다. 기본적인 옵티마이저에 대한 정리는 여..
DBMS는 다수의 사용자가 이용할 것을 생각하고 있기 때문에, 다중 트랜잭션의 상호 간섭 작용에서 데이터베이스를 보호할 수 있어야 한다. 이것을 동시성 제어(Concurrency Control) 라고 한다. 동시성을 제어할 수 있도록 하기 위해 모든 DBMS가 공통적으로 Lock 기능을 제공하며, 이로 인해 여러 사용자가 데이터를 동시에 엑세스하는 것으로 보이더라도 내부적으로는 하나씩 실행되도록 직렬화가 진행된다. 또한, set transaction 명령어를 이용하여 트랜잭션 격리성 수준을 조정할 수 있는 기능도 제공한다. 동시성과 일관성은 트레이드 오프(Trade-off) 관계로, 동시성을 높이기 위해 Lock의 사용을 최소화할 경우 일관성 유지가 어렵고, 일관성을 높이기 위해 Lock을 적극적으로 사..
✨ 트랜잭션? 트랜잭션(Transaction)은 업무 처리를 위한 논리적 작업 단위이다. 작업의 논리적 단위는 단일 연산이 아닐 수 있고, 이 말인 즉 하나의 트랜잭션이 두 개 이상의 갱신 연산으로 이루어질 수도 있다. 데이터를 일관성 있게 처리하기 위해서는 트랜잭션에 속한 두 개 이상의 갱신 연산을 동시에 실행할 수 있어야 하는데, 이것은 불가능하기 때문에 대신 여러 개의 갱신 연산이 하나의 작업처럼 전부 처리되거나, 아예 하나도 처리되지 않도록 동시 실행을 구현한다. 🪡 트랜잭션의 특징 트랜잭션은 네가지의 주요 특징을 가지고 있는데, 영문 첫 글자를 따서 'ACID' 라고 부른다. 1) 원자성(Atomicity) 트랜잭션은 더 이상 분해가 불가능한 업무의 최소 단위이기 때문에, 전부 처리되거나 아예 ..
✨ Lock ? 고가의 DBMS를 사용하는 이유는 여러가지 측면이 있지만, 무엇보다 트랜잭션 처리 능력이 가장 기본적이고 핵심적인 요소라고 볼 수 있다. 같은 자원을 엑세스하려는 다중 트랜잭션 환경에서 데이터베이스의 일관성, 무결성을 유지하기 위해서는 트랜잭션의 순차적 진행을 보장할 수 있는 직렬화(Serialization) 장치가 필요하다. 직렬화가 가능하도록 하기 위해 사용하는 메커니즘이 Lock이며, DBMS마다 구현하는 방식과 세부적 기능이 많이 다르다. 🪡 Lock의 상태 🐣공유 Lock과 배타적 Lock DBMS는 각 트랜잭션의 오퍼레이션별로 적당한 수준의 Lock을 자동 설정한다. 그러나 필요할 경우, 일부 Lock에 대해서는 사용자가 직접 제어하는 방법도 제공한다. 1) 공유 Lock 공유..