이 분이 오라클의 대부로 불리는 토마스 카이트(Thomas Kyte)입니다. 미드에 나올 법한 수더분한 인상의 옆집 아저씨처럼 생겼네요. 오라클 5.1.5c 버전 때부터 현재에 이르기까지 오라클의 발전사와 함께 해온 분이죠. 그리고 『오라클 매거진(Oracle Magazine)』에서 운영하는 ‘Ask Tom’ 코너(http://asktom.oracle.com)를 통해 좌절하는 오라클 개발자, DBA들에게 광명을 제공하고 있기도 합니다.
원서도 800여 페이지가 넘지만, 번역서는 본문 포인트를 작게 했는데도 1,000페이지가 넘는 오라클 바이블로 출간이 됩니다. 페이지가 많다고 해서 바이블이 아니라, 아래 내용들을 보시면 오라클을 업무에 사용하시는 분은 누구나 한 권씩 준비하여 수시로 참고할 만한 내용이 가득한 것에 수긍할 것입니다.
번역과 편집 작업에만에도 근 1년 가까운 시간이 흘렀네요. 좋은 책을 내기 위해 오랜 인고의 시간을 보내고 이제 독자 여러분에게 다가가는데, 많은 사랑으로 아껴 주셨으면 합니다. 이 책의 번역은 국내 IT종합컨설팅 분야에서 좋은 평판을 받고 있는 (주)비투엔컨설팅의 컨설턴트 다섯 분이 바쁜 회사 업무와 병행해주시느라 정말 많은 수고를 해주셨습니다. 번역이라는 특성과 지식 전달 사이에서 용어에 대한 고민을 많이 하셨다고 합니다. 그리고 내용이 어려운 부분은 풀어 쓰거나 부연 설명을 통해 국내 독자들의 이해를 높이기 위해 많이 애써주셨습니다. 출간 후 맛있는 식사라도 대접하기 전에 먼저 노고에 박수를 보내봅니다. 짝!짝!짝!
각 장별 주요 내용은 아래에 정리해드립니다. 책은 6월 28일 출간될 예정이며, 현재 아래 서점들에서 예약판매 중입니다.
각 장의 주요 내용 1장: 성공적인 오라클 애플리케이션 개발
이 장에서는 데이터베이스 프로그래밍에서 필요한 주요 접근 방법을 설명하고 있다. 모든 데이터베이스가 똑같지 않기 때문에, 데이터베이스를 이용하는 애플리케이션을 주어진 기간 안에 성공적으로 개발하기 위해서는 사용하는 데이터베이스가 어떤 기능을 가졌는지 정확하게 이해해야 하며, 또한 어떻게 수행하는지 알고 있어야 한다. 데이터베이스가 무엇을 할 수 있는지 알지 못한다면, 데이터베이스가 이미 제공하는 기능을 애플리케이션으로 개발하기 위해 쓸데없이 시간을 낭비할 수 있다. 또한 데이터베이스가 어떻게 수행하는지 알지 못한다면, 오류를 발생시키거나 제대로 동작하지 않는 애플리케이션을 개발할 수 있다.
이 장에서는 데이터베이스에 대한 이해부족으로 말미암은 프로젝트 실패 사례에서 볼 수 있는 몇몇 애플리케이션을 살펴볼 것이다. 예제를 살펴보면서 개발자로서 이해할 필요가 있는 기본적인 특징과 기능에 대해 알아볼 것이다. 결론적으로 말하면, 데이터베이스를 단지 결과를 뱉어내는 블랙박스처럼 다루지 말아야 하며, 확장성과 성능에 관하여 관심을 기울여야 한다.
2장: 아키텍처 개요
이 장에서는 오라클 아키텍처의 기본 개념을 알아본다. 먼저 오라클 데이터베이스에서 자주 잘못 이해되고 있는 ‘인스턴스’와 ‘데이터베이스’ 두 가지 용어에 대해 정확하게 정의한다. 또한 오라클 인스턴스를 구성하는 SGA(System Global Area)와 프로세스에 대해 빠르게 살펴보고 있으며, 간단한 오라클의 접속 방식에 대해서도 살펴본다.
3장: 파일 이 장에서는 오라클 데이터베이스와 인스턴스를 구성하는 8가지 파일 유형을 자세히 살펴본다. 파라미터 파일부터 데이터 파일, 리두 로그 파일까지 각 파일이 어떤 파일인지 살펴보고, 존재하는 이유와 어떻게 다루어야 하는지에 대해 살펴본다.
4장: 메모리 구조
이 장에서는 오라클이 메모리를 어떻게 사용하는지를 살펴본다. 사용자 레벨에서 사용하는 PGA(Process Global Area) 메모리와 데이터베이스 전체적으로 사용하는 SGA(Shared memory)에 대해 알아본다. 오라클 10g에서 PGA 및 SGA를 수동으로 관리하는 방법과 자동으로 관리하는 방식 간의 차이점을 살펴보고, 각각이 어느 경우에 유리한지 살펴본다. 이 장을 읽고 나면 오라클이 메모리를 어떻게 사용하고 관리하는지 정확하게 이해할 수 있을 것이다.
5장: 오라클 프로세스
이 장은 오라클의 서버 프로세스와 백그라운드 프로세스의 유형에 대해 전반적으로 살펴본다. 또한 shared server 프로세스를 통한 접속 방식과 dedicated server 프로세스를 통한 접속 방식 간의 차이점을 자세히 설명하고 있다. 또한 오라클 인스턴스가 구동할 때 생성되는 백그라운드 프로세스(LGWR, DBWR, PMON, SMON 등)의 대부분을 살펴보고 있으며, 각각의 역할에 대해 언급하고 있다.
6장: 락킹과 래칭
데이터베이스는 데이터베이스만의 고유한 방식을 가지고 있기 때문에(SQL Server는 오라클과 같은 방식으로 수행하지 않는다), 오라클이 락킹과 동시성 제어를 어떻게 구현하는지 이해하는 것은 성공적인 애플리케이션 구현을 위해서 반드시 필요한 주제다. 이 장에서는 이러한 주제에 접근하는 기본적인 접근 방법을 설명하고 있고, DML, DDL, 래치에 따라 적용될 수 있는 락의 유형에 대해 알아보고, 락킹을 주의 깊게 구현하지 않았을 때에 발생할 수 있는 데드락킹(deadlocking), 블로킹(blocking), 락 상승(escalation) 등과 같은 문제점에 대해 살펴본다.
7장: 동시성과 멀티버저닝
이 장에서는 필자가 선호하는 오라클의 특징인 멀티버저닝과 동시성 제어를 살펴보고, 애플리케이션의 올바른 설계에 어떠한 영향을 미치는지 알아볼 것이다. 모든 데이터베이스가 동일하게 생성되지 않았기 때문에 데이터베이스마다의 작동 방법은 애플리케이션 설계에 영향을 미친다. 먼저 ANSI SQL에 기본적으로 정의되는 다양한 트랜잭션 고립화 수준에 대해 살펴보고, 오라클 구현 방식과 어떻게 연결되는지 알아본다. 또한 다른 데이터베이스에서도 이 표준과 어떻게 대응되는지 살펴본다. 그리고 오라클이 제공하는 멀티버저닝이 무엇인지 알아보고, 이 기능으로 인해 데이터베이스에서 non-blockng 읽기가 어떻게 가능한지 알아볼 것이다.
8장: 트랜잭션
트랜잭션은 모든 데이터베이스의 기본 개념으로 파일 시스템과 구별되는 데이터베이스의 특징 중 하나지만, 아직도 트랜잭션을 잘못 이해하고 있는 것을 종종 볼 수 있으며, 많은 개발자가 실수로 트랜잭션을 이용하지 않고 있다는 것조차 모르는 경우도 있다. 이 장에서는 오라클에서 트랜잭션을 어떻게 사용해야 하는지를 살펴보고, 다른 데이터베이스에서 사용하는 방식으로 잘못 사용하는 경우에 대해서도 알아볼 것이다. 특히 트랜잭션의 특징 중 하나인 원자성(atomicity)에 대해 알아보고, 오라클 명령문에 어떻게 영향을 미치는지도 살펴볼 것이다. 그리고 트랜잭션 제어 명령문인 COMMIT, SAVEPOINT, ROLLBACK에 대해서 알아보고, 무결성 제약조건(integrity constraints), 분산 트랜잭션(two-phase commit, 2PC)을 알아보고, 마지막으로 자율 트랜잭션에 대해 살펴볼 것이다.
9장: 리두와 언두
개발자들은 DBA만큼 리두와 언두에 대해 자세히 알 필요는 없지만, 개발자들도 데이터베이스에서 리두와 언두의 역할에 대해서는 알아야 한다. 제일 먼저 리두를 정의하고, COMMIT 명령문이 정확하게 무엇을 하는지 조사한다. 그리고 얼마만큼의 리두가 생성되는지를 확인하는 방법을 알아보고, 어떤 오퍼레이션에 의해 생성된 대량의 리두를 줄이기 위해 NOLOGGING 절을 사용하는 방법에 대해 살펴본다. 또한 블록 클린아웃(cleancout)과 로그 경합과 같은 이슈와 관련된 리두 생성에 관하여 알아본다.
언두 절에서는 언두 데이터의 필요성을 알아보고, 언두 데이터를 최대로 발생시키는 오퍼레이션과 최소로 발생시키는 오퍼레이션을 알아본다. 마지막으로, ORA-01555: snapshot too old error가 어떤 경우에 발생하는지 알아보고 피할 수 있는 방법을 살펴본다.
10장: 데이터베이스 테이블
오라클은 다양한 테이블 유형을 지원하고 있다. 이 장에서는 힙 구조 테이블(기본으로 생성되는 일반적인 테이블), 인덱스 구조 테이블, 인덱스 클러스터 테이블, 해시 클러스터 테이블, 중첩 테이블, 템포러리 테이블, 객체 테이블의 다양한 테이블 유형을 알아본다, 그리고 이 테이블이 언제 사용하는 것이 유리한가, 어떻게 사용해야 하는가, 왜 사용하는가를 알아볼 것이다. 대부분은 힙 구조 테이블로 구현해도 문제가 없지만, 이 장을 통해 다른 테이블 유형이 어떤 환경에서는 더 유리한 구조라는 것을 알게 될 것이다.
11장: 인덱스
인덱스는 애플리케이션 설계에 있어서 중요한 역할을 한다. 올바른 구현을 위해서는 데이터를 깊이 이해할 필요가 있고, 데이터를 어떻게 분산하는지, 어떻게 사용할 것인지에 대한 이해가 필요하다. 인덱스는 애플리케이션의 최종 마무리 단계에서 다뤄지는 경우가 대부분이어서 성능에 문제를 겪게 된다.
이 장에서는 B*Tree, 비트맵, 함수 기반과 애플리케이션 인덱스에 관한 다양한 인덱스 유형을 자세히 살펴보고, 인덱스 유형별로 어떤 경우에 사용해야 하고 사용하지 않아야 하는지 살펴본다. ‘뷰에서도 인덱스가 사용되는가?’, ‘해당 인덱스를 왜 사용하지 않을까?’ 등과 같은 인덱스에 관한 잦은 질문에 대해 살펴보고, 몇 가지 오해에 대해서도 알아본다.
12장: 데이터 타입
오라클에는 다양한 데이터 타입이 존재한다. 이 장에서는 22개 내장형 데이터 타입에 대해 살펴보고, 데이터 타입별로 어떤 특징이 있는지 알아보고, 언제 어떻게 어떤 데이터 타입을 선택해야 하는지 살펴본다. 먼저 NLS(National Language Support)에 대해 간단하게 살펴보고, 오라클에서 문자 타입을 충분히 이해하기 위한 기본 지식을 자세히 살펴본다. 그리고 익숙한 NUMBER 타입에 대해 살펴보고, 오라클 10g 버전에서 제공하는 숫자의 저장방식에 대해서도 살펴본다. 다음으로, 이제는 잘 사용하지 않는 LONG과 LONG RAW 데이터 타입에 대해 알아본다. 애플리케이션에서 과거의 LONG 컬럼을 어떻게 다뤄야 할지 보여주고, LOB 타입으로 이전하는 방법에 대해 설명한다. 다음으로, 일자와 시간을 다루는 다양한 데이터 타입을 살펴보고, 원하는 결과를 얻기 위해 다양한 데이터 타입을 다루는 방법에 대해서도 살펴보고 있으며, 타임 존(time zone)을 지원하는 방식에 대해서도 다루고 있다.
또한 LOB 데이터 타입을 살펴보고 있으며, 어떻게 저장하는지 알아보고 IN ROW, CHUNK, RETENTION, CACHE와 같은 다양한 설정의 의미에 대해 알아본다. LOB 데이터 타입을 다루기 위해 기본적으로 어떻게 구현되고 어떻게 저장되는지를 이해하는 것은 중요하며, 특히 추출결과와 저장공간의 활용방식을 이해하는 것이 중요하다. 마지막으로 ROWID와 UROWID 타입을 살펴보며, 이는 오라클에 국한된 특별한 데이터 타입으로서 로우의 주소를 의미한다. 테이블에서 데이터 타입으로 언제 사용해야 하는지 알아보고, 결과적으로 사용하지 않아야 한다는 결론을 얻게 된다.
13장: 파티셔닝
파티셔닝은 대용량 테이블과 인덱스를 분할정복(divide-and-conquer) 방식으로 관리하는 도구로서 고안되었고, 논리적인 단위로 테이블을 쪼개거나 관리할 수 있는 더 작은 조각으로 인덱스를 나누어 관리할 수 있게 한다. DBA와 개발자는 애플리케이션의 유용성과 성능 향상을 최대화하기 위해 협력해야 한다. 이 장에서는 테이블과 인덱스 파티셔닝에 대해 다루고 있으며, 데이터 웨어하우스에서 주로 사용하는 로컬 인덱스 파티셔닝과 주로 OLTP 환경에서 사용하는 글로벌 인덱스 파티셔닝에 대해 살펴본다.
14장: 병렬 처리
이 장에서는 오라클에서 병렬 처리의 개념과 처리방식에 대해 살펴본다. 먼저 언제 병렬 처리방식이 유용한가에 대해 살펴보고, 언제 사용해야 하는지, 또한 언제 사용하지 않아야 하는지를 살펴본다. 그리고 병렬 처리 메커니즘을 살펴보고, 병렬 처리와 관련된 기능을 알아본다. 다음으로, 병렬 처리 방식으로 수정을 처리하는 병렬 DML(PDML)에 대해 살펴보고, PDML이 물리적으로 어떻게 구현되는가와 PDML에 관련된 일련의 제한이 존재하는 이유에 대해 살펴본다.
또한 병렬 DDL을 살펴보는데, 필자가 생각하기에 병렬 DDL이야말로 병렬 처리의 백미라고 생각한다. 일반적으로 DBA는 거대한 작업을 관리하는 작은 단위 작업을 가지고 있게 마련인데, 병렬 DDL은 DBA가 사용 가능한 최대한의 시스템 자원을 이용하여 거대하고 복잡한 작업을 단일 프로세스로 처리했을 때보다 극적으로 짧은 시간에 마무리할 수 있게 한다.
마지막으로 애플리케이션을 병렬로 실행하는 방식으로 이해되는 프로시저 병렬 처리 방식에 대해 설명하며, 이를 구현하기 위한 두 가지 방식을 다룬다. 하나는 파이프라인 함수 또는 다이내믹 병렬을 구현하는 스토어드 함수로 구현하는 방식이고, 또 하나는 애플리케이션을 동시에 수행하도록 하는 ‘do it yourself(DIY)’ 병렬 처리 방식이다.
15장 데이터 로딩과 언로딩
전반부는 SQL*Loader(SQLLDR)를 설명하고, 이 툴을 이용하여 데이터를 로드하고 수정하는 다양한 방식에 대해 알아본다. 구분자를 가진 데이터를 로딩하고, 기존에 존재하는 데이터를 수정하고, 새로운 로우를 삽입하고, 데이터를 언로딩하고, 저장 프로시저에서 SQLLDR을 호출하는 방식에 대해 살펴본다. SQLLDR은 매우 훌륭하고 유용한 툴이지만, 실제 사용해보면 많은 질문이 생기는 툴이기도 하다. 후반부는 External 테이블에 집중적으로 살펴보며, 벌크 데이터를 로드하고 언로드하는 데는 의심의 여지가 없는 가장 강력한 수단이라는 것을 알 수 있을 것이다.
16장: 데이터 암호화
이 장은 오라클 데이터베이스에서 데이터 암호화를 위한 방법을 살펴본다. DBMS_CRYPTO 패키지를 이용하여 수동으로 설정하는 ‘do it yourself’ 암호화 방식으로 중요하게 다루지는 않는다. 오히려 패키지를 이용하는 암호화 방식을 왜 사용하지 않아야 하는지를 설명하고 있다. 이 장의 주요 관심사는 오라클 데이터베이스에서 TDE(Transparent Data Encryption) 방식에 대해 자세히 살펴보고 있다. 컬럼 수준과 테이블스페이스 수준에서 어떻게 암호화를 구현하는지 알아보고, 개발자 또는 DBA에게 어떤 의미가 있는지를 설명한다. 가능한 모든 설정 방법을 설명하지는 않고(이것은 오라클 도큐먼트를 참조하면 된다), 실제적인 구현을 위한 세부사항을 살펴보고 어떻게 사용자에게 영향을 주는지를 알아본다.