데이터 모델은 소프트웨어가 어떻게 작성됐는지 뿐아니라, 해결하려는 문제를 어떻게 생각해야하는지에 대해서도 지대한 영향을 미치므로 개발에서 중요한 부분이다.
아래와 같은 고민을하고 결정을 하면서 데이터 모델을 표현하게 된다.
- 개발자는 객체나 데이터 구조, 그리고 이러한 데이터 구조를 다루는 API를 모델링한다.
- 데이터 구조를 저장할때는 JSON이나 XML 문서, 관계형 데이터베이스 테이블이나 그래프 모델같은 범용 데이터 모델로 표현한다.
- 데이터베이스 소프트웨어를 개발하는 엔지니어는 데이터를 메모리나 디스크 또는 네트워크 상의 바이트 단위로 표현하는 방법을 결정한다.
- 그렇다면 더 하위 계층의 하드웨어 엔지니어는 자기장 등의 관점에서 바이트를 표현하는 방법을 알아낸다.
위의 예시에서 아래로 내려갈수록 더 하위 계층을 담당한다.
각 계층의 엔지니어들은 추상화를 통해 하위계층의 복잡성을 숨겨서 효율적으로 일할 수 있게 한다.
관계형모델과 문서모델
가장 잘 알려진 데이터 모델은 SQL이다.
데이터는 (테이블이라 불리는) 관계(relation)로 구성되고 각 관계는 순서없는 튜플(row)의 모음이다.
이러한 데이터의 관계를 잘 표현하기 위한 관계형 모델은 관계형 데이터베이스 관리 시스템(RDBMS)과 SQL을 통해서 구현되었다.
트랜잭션처리(은행거래, 항공예약 등)과 일괄처리(고객 송장 작성, 급여지불 등)에서 일반적으로 관계형데이터 베이스 시스템이 사용되었다. 당시 데이터 저장과 질의에 대한 많은 논의가 있었는데 이 RDBMS가 점차 메인이 되었다.
NoSQL의 탄생
2010년대에 등장하기 시작한 해당 데이터 베이스는 특정 데이터베이스를 뜻하는 것이 아니라 관계형 모델의 우위를 뒤집으려 등장한 비관계형 데이터베이스를 의미한다. 즉 Not Only SQL로 해석될 수 있다.
NoSQL은 아래와 같은 이유로 큰 인기를 얻었다.
- 대규모 데이터 셋이나 높은 쓰기 처리량에서 관계형데이터베이스보다 뛰어난 확장성이 필요
- 당시 오픈소스 소프트웨어에 대한 선호도가 확산
- 관계형 모델에서 지원하지 않는 특정 질의 언어를 지원했기 때문에 사용되기 시작했다.
실제로 애플리케이션의 요구사항은 제각각이므로 사용 사례에 맞는 최적의 기술 선택이 필요하다.
관계형 데이터베이스가 비관계형 데이터스토어와 함께 사용될 수도 있는 것이다. 이를 다중 저장소 지속성(polyglot persistence)라고 한다.
객체관계형 불일치
실제 애플리케이션에서 데이터 베이스를 사용하려 하면, 두 시스템 사이를 전환시켜줄 필요가 있었다.
이런 모델 사이의 분리를 종종 임피던스 불일치(impedance mismatch)라고 한다.
ORM 프레임 워크가 이러한 전환 계청을 줄여주었지만 여전히 차이를 보였다.
예시로 보여주고 있는 링크드인의 이력서 사례의 경우, 이력서 같은 데이터구조는 모든 내용을 갖추고 있는 문서라서 JSON표현에 매우 적합하다고 볼 수 있다. 대표적으로 몽고DB 같은 문서지향 데이터베이스에서 JSON 데이터 모델을 지원한다.
이러한 JSON모델이 임피던스 불일치를 줄인다고 생각하지만 데이터 부호화 형식으로서 JSON이 가진 문제도 있다.
그럼에도 JSON 표현은 다중 테이블 스키마 보다 더 나은 지역성을 갖는다. 이 의미는 관계형 예제에서는 프로필을 가져오려면 다중 질의를 수행하거나, 난잡한 다중 조인을 수행해야한다. 그러나 JSON 표현에서는 모든 관련정보가 한 곳에 있어서 질의 하나로 충분하다.
다대일 관계와 다대다 관계
하나의 정보를 여러 곳에서 참조해야 하는 경우, ID를 참조식별자로 사용하게 된다. 따라서 이러한 ID는 쓰기오버헤드와 불일치 즉, 중복과 관련된 위험이 있다. 이러한 중복을 제거하는 일이 데이터 베이스의 정규화 이면에 놓인 핵심 개념이다.
중복된 데이터를 정규화하려면 다대일 관계가 필요한데, 이러한 관계는 문서 모델에 적합하지 않다. 조인이 쉬운 관계형 데이터 베이스에서는 외래키로 다른 테이블의 로우를 참조할 수 있으나, 문서모델에서는 이러한 조인 지원이 약하다.
만약에 조인없느 문서 모델에 적합한 애플리케이션이라도 기능 추가로 인해서 데이터의 상호 관계성이 강해질수도 있다.
- 엔티티로서의 조직과 학교
- 추천서
이력서를 예제로 드는 경우 위와 같은 정보가 추가되어서 참조해야 하는 경우, 다대일 관계성이 필요해진다. 또한 추천서처럼 다대다 관계가 필요할 수도 있다. 이 때 다대다 관계를 표현하기위해서는 관계형 데이터베이스만큼 적절한 것도 없다.
문서 데이터베이스는 역사를 반복하고 있나?
위와 같은 논쟁들로 인해서 문서 데이터베이스와 NoSQL에서 다대다 관계를 표현하는 것에 대한 한계와 그 방법에 대해 논의되었다.
계층 모델
실제로 NoSQL 등장 이전에 관계형 데이터베이스가 아닌 IBM의 정보관리 시스템이 있었다. 이는 문서 데이터베이스에서 사용하는 JSON 모델과 비슷하다. 이 또한 일대다관계에서는 잘 동작하지만, 다대다관계 표현은 어려웠고 조인도 지원하지 않았다.
네트워크 모델
코다실 모델이라고도 불렸다. 이는 계층모델을 일반화하는데 계층모델의 트리구조에서는 모든 레코드는 하나의 부모가 있으나 네트워크 모델에서는 다중부모가 있을수 있다. 즉 다대다와 다대일 관계를 모델링 할 수 있는 것이다.
네트워크 모델에서는 레코드간 연결은 외래키보다 프로그래밍 언어의 포인터와 더 비슷하다. 레코드에 접근하는 유일한 방법은 최상위 레코드 부터 연결경로를 따라가는 즉 접근경로방법이 있다.
네트워크 모델에서 가장 간단한 경우는 연결목록의 순회와 같을 때다. 목록의 맨앞에서 시작해서 원하는 레코드를 찾을때까지 한번에 하나의 레코드를 보는 방식이다. 그러나 다대다 관계에서는 다양한 다른 경로가 같은 레코드로 이어질 수 있고 네트워크 모델을 사용하는 프로그래머는 경로의 맨앞에서 이런 다양한 접근 경로를 계속 추적해야한다.
이에 따라 데이터 베이스의 질의와 갱신을 위한 코드가 복잡하고 유연하지 못한 문제가 있었다. 즉 접근 경로는 제한된 하드웨어 성능에서는 효율적이나, 다른 한계가 존재했다.
관계형 모델
기본적으로 알려진 모든 데이터를 배치하는 것이다. 관계는 단순히 튜플(로우)의 컬렉션이 전부다. 임의조건과 일치하는 테이블의 일부 또는 모드 ㄴ로우를 선택해서 읽을 수 있고 일부 칼럼을 키로 지정해 칼럼와 일치하는 특정 로우를 읽을 수 있다.
계층모델이나 네트워크 모델처럼 따라가야할 접근 경로가 없다. 관계형 모델에서는 질의 최적화기는 질의의 어느 부분을 어떤 순서로 실행할지를 결정하고 사용할 색인을 자동으로 결정한다. 이는 실제로 접근경로인데 이러한 접근 경로를 질의 최적화기가 자동으로 만들어주므로 개발자가 별도로 생각할 필요가 없다.
새로운 방식으로 데이터에 질의하고 싶은 경우 새로운 색인을 선언하기만 하면 질의는 자동으로 가장 적합한 색인을 사용한다.
문서 데이터베이스와의 비교
문서 데이터베이스 또한 별도 테이블이 아닌 상위 레코트 내에 중첩된 레코드를 저장한다는 의미에서 계층모델로 돌아갔다고 보 ㄹ수 있다.
하지만 다대일과 다대다 관계를 표현할때는 관계형과 문서 데이터베이스는 근본적으로다르지 않다. 둘다 관련항목은 고유한 식별자로 참조한다. 관계형은 외래키라 부르고 문서모델에서는 문서참조라 부른다.
이 식별자를 조인이나 후속 질의를 사용해서 읽기 시점에 확인한다.
관계형 데이터베이스와 오늘날의 문서 데이터베이스
문서 모델을 선호하는 주요 이유는 스키마 유연성, 지역성에 기인한 성능이다.
일부의 경우 애플리케이션에서 사용하는 데이터 구조와 더 가깝기 때문이다.
관계형 모델은 조인, 다대일, 다대다 관계를 더 잘지원함으로써 문서 데이터 모델에 대항한다.
어떤 데이터 모델이 애플리케이션 코드를 더 간단하게 할까?
애플리케이션에서 데이터가 문서와 비슷한 구조(보통 일대다 관계)라면 문서 모델을 사용하는 것이 좋다. 오히려 문서와 같은 구조를 여러 테이블로 나누어 찢는 관계형 기법은 더 복잡한 애플리케이션 코드를 발생시킨다.
그러나 문서 모델에도 제한이 있다. 예를 들어 문서 내 중첩 항목을 바로 참조할수는 없어서 "사용자 123의 직위목록의 두번째 항목"과 같이 표현해야한다. 이는 계층 모델에서 접근 경로와 매우 유사하다.
즉 문서 데이터베이스의 미흡한 조인 지원은 애플리케이션에 따라 문제일 수도 있는 것이다. 대표적으로 다대다 관계를 사용할 경우이다.
비정규화로 조인의 필요성 줄이기가 가능하지만 애플리케이션 코드는 비정규화된 데이터의 일관성을 유지하기 위해 추가 작업을 해야한다.
또한 이 때 조인을 위해서 애플리케이션 코드에서 데이터베이스에 다중 요청을 만들어 흉내낼 수 있지만 복잡도가 애플리케이션으로 이동할 뿐만 아니라 일반적인 조인보다 더 느리다.
문서 모델에서의 스키마 유연성
스키마 유연성에 대해서는 논의가 다양하다. 우선 스키마가 없다는 뜻은 임의의 키와 값을 문서에 추가할 수 있고 읽을 때 클라이언트는 문서에 포함된 필드의 존재 여부를 보장하지 않는다는 의미이다.
문서 모델을 스키마가 없는 데이터라고 하기보다는 스키마가 약한 유형이라고 보는 것이 좋다.
스키마에는 쓰기 스키마(스키마가 명시적이고 데이터베이스가 이를 따라서 데이터를 적재)와 읽기 스키마(데이터 구조는 암묵적이고 읽을때만 해석된다)로 나뉘어 진다. 즉 강한 스키마 유형인 쓰기 스키마는 일종의 정적타입(컴파일)언어와 대응하여, 그리고 읽기 스키마는 동적 타입(런타임)언어와 대응되어 이야기 된다.
이러한 스키마에 따른 접근 방식 간 차인느 데이터 타입을 변경하고자 할때 뚜렷이 나타난다.
예를 들어 현재 하나의 필드에 사용자의 전체 이름을 저장하고 있지만 성과 이름을 분리해서 저장하고 싶다고 가정해보자. 읽기 스키마에서는 새로운 필드를 가지 ㄴ새로우 ㄴ문서를 작성하고 예전 문서를 읽은 경우를 처리하는 코드만 있으면 된다. 그러나 쓰기 스키마의 경우 마이그레이션을 수행해야 한다. 즉 스키마 변경이 필요하다.
기본적으로 대부분의 관계형 데이터 베이스 시스템은 이러한 스키마 변경을 수 밀리초안에 수행하는데 MySQL에서는 이 또한 예외다. 스키마 변경을 위한 Alter table 시에 전체 테이블을 복사한다. 이는 큰테이블 변경 시에 수시간까지 중단시간이 발생한다는 의미이다.
읽기 스키마는 컬렉션 안의 항목들이 모두 동일한 구조가 아닐때 유리하다. 이렇게 보면 스키마 리스가 득보다 실이 많아보인다. 그러나 모든 레코드가 동일한 구조라서 예상 가능하다면 스키마가 문서화와 구조를 강제하기 위해 유용하다.
질의를 위한 데이터 지역성
웹 페이지 상에 문서를 보여주는 동작처럼 애플리케이션이 자주 전체 문서에 접근해야할 때 저장소 지역성을 활용하면 성능 이점이 있다.
만약 데이터가 다중 테이블로 나눠졌으면 전체를 검색하기 위해 다중 색인 검색이 필요하다.
이와 관련해서 지역성으 ㅣ이점은 한번에 해당 문서의 많은 부분을 필요로 하는 경우에 적용된다고 볼 수 있다.
그러나 데이터베이스는 문서의 작은 부분에만 접근해도 전체 문서를 적재해야 하기에 한번에 하나만 읽어오는 경우가 아닌 작은 문서를 여러번 읽어야 하는 경우에는 지역성이 단점일 수 있다.
이러한 지역성은 문서모델에만 국한되지 않는다. 오라클에서는 다중테이블 색인 클러스터 테이블을 통해 지역성을 제공한다. 또한 빅ㄷ테이블 데이터 모델의 칼럼 패밀리 개념의 카산드라나 HBase에서 또한 테이블 내에서 테이블의 중첩된 로우를 가능하게 하는 등의 방식으로 지역성을 가능하게 한다.
문서형 데이터 베이스와 관계형 데이터 베이스의 통합
관계형 데이터 베이스와 문서 데이터 베이스는 서로의 기능을 참고하여 각자 새로운 기능을 추가함으로써 점점 더 비슷해지고 있다.
데이터를 위한 질의 언어
데이터를 질의하기 위한 언어에는 크게 명령형 언어/ 선언형 언어가 두가지가 있다. 명령형 언어는 대부분의 프로그래밍 언어로, 특정 순서로 특정연산을 수행하게끔 컴퓨터에게 명령을 내려서 원하는 값을 얻어내는 것이다. 이와 달리 선언형 언어는 방법이 아니라 알고자 하는 데이터의 패턴, 조건 등을 지정한다.
선언형 언어는 단순히 간결하다는 장점 뿐 아니라, 데이터 베이스 엔진의 상세구현이 숨겨져 있어서 질의를 변경하지 않고도 데이터 베이스의 시스템 성능을 향상시킬 수 있다.
명령형 코드의 경우, 원하는 데이터를 얻기위한 작업 순서를 지정해주고 있다. 따라서 내부적으로 로직을 변경하다가 레코드를 옮길때 원하는 데이터의 순서가 바뀔수도 있다.
그러나 SQL같은 선언형 코드는 특정순서를 보장하지 않으므로 순서가 바뀌어도 상관없다.
또한 선언형 코드는 병렬 실행에 적합하다. 명령형코드는 명령어를 턱정 순서로 수행하게끔 지정하기 때문에 다중 코어나 다중 장비에서 병렬처리가 매우 어렵다. 선언형 언어는 결과를 결정하기 위한 알고리즘을 지정하는게 아니라 결과의 패턴만 지정하기 때문에 병렬 실행으로 더 빨라질 가능성이 크다
웹에서의 선언형 질의
이는 단순히 데이터베이스 질의 언어 뿐 아니라 웹에서도 적용해 볼수 있다. 스타일을 적용하고자 할때, CSS나 XSL을 통해 더 간결하게 문서의 스타일을 지정할 수 있다. 이를 명령형 코드로 구현한 것이 자바스크립트에서 DOM API를 사용한 경우이다.
이런 경우 연관된 코드가 많아서 조금이라도 수정하려면 많은 코드 작업이 필요해질 수 있다.
맵리듀스 질의
맵리듀스는 대량의 데이터를 처리하기 위한 프로그래밍 모델이다. 몽고DB와 카우치DB를 포함한 일부 NoSQL 데이터 저장소는 제한된 형태의 멥리듀스를 지원한다. 이 메커니즘은 많은 문서를 대상으로 읽기 전용 질의를 수행할 때 사용한다.
몽고DB의 map과 reduce 함수는 수행할 때 약간의 제약사항이 있다. 두 함수는 순수함수여야 한다. 즉 입력으로 전달된 데이터만 사용하고 추가적인 데이터베이스 질의를 수행할 수 없어야 한다. 이런 제약 사항 덕분에 데이터베이스가 임의 순서로 어디서나 이 함수를 실행할 수 있고 장애가 발생해도 함수를 재실행할 수 있다.
그래프형 데이터 모델
다대다관계가 매우 일반적이게 된다면 관계형 데이터 모델보다 그래프형 데이터 모델이 나을수도 있다.
그래프는 두 유형의 객체로 이루어진다. 정점(vertex)(노드나 엔티티라고도 한다)과 간선(edge)(관계나 호라고도 한다)이다.
대표적으로 소셜그래프/웹그래프/도로나 철도 네트워크가 그 예이다.
그래프는 동종 데이터에만 국한되지 않으므로 단일 데이터 저장소에 완전히 다른 유형의 객체를 일관성있게 저장할 수 있는 강력한 방법을 제공한다. 가령 페이스북을 예로 들면, 정점은 사람, 장소, 이벤트 등이 될 수 있으며 간선은 어떤 사람이 친구인지 어떤 위치에서 체크인이 발생했는지 등을 나타낸다.
속성 그래프
속성 그래프 모델에서 각 정점은 다음과 같은 요소로 구성된다.
- 고유한 식별자
- 유출 간선 집합
- 유입 간선 집합
- 속성 컬렉션(키-값 쌍)
각 간선은 다음과 같은 요소로 구성된다
- 고유한 식별자
- 간선이 시작되는 정점(꼬리 정점)
- 간선이 끝나는 정점(머리 정점)
- 두 정점 간 관계 유형을 설명하는 레이블
- 속성 컬렉션(키-값쌍)
여기서 중요한 특징은 아래 세가지다
- 정점은 다른 정점과 간선으로 연결되며 특정 유형과 관련 여부를 제한하는 스키마는 없다
- 정점의 유입과 유출 간선을 효율적으로 찾을 수 있고 그래프를 순회할 수 있다.
- 다른 유형 관계에 서로 다른 레이블을 사용하면 단일 그래프에 다른 유형의 정보를 저장하면서도 데이터 모델을 깔끔하게 유지할 수 있다.
이를 통해 그래프는 데이터 모델링을 위한 많은 유연성을 제공한다는 것을 알 수 있다. 예를 들어 국가마다 지역 구조가 다르거나 국가안의 국가처럼 역사의 굴곡이 있는 경우도 다 표현가능하다.
사이퍼 질의 언어
사이퍼는 속성 그래프를 위한 선언형 질의 언어이다.
SQL의 그래프 질의
SQL로도 그래프 데이터를 표현할 수 있으나 어렵다. 관계형 데이터베이스에서는 대개 질의에 필요한 조인을 미리 알고있어야 하는데 그래프 질의에서는 찾고자 하는 정점을 찾기 전에 가변적인 여러 간선을 순회해아한다. 즉 미리 조인수를 고정할 수 없다.
따라서 가능은 하나 매우 복잡한 쿼리가 나온다.
트리플 저장소와 스파클
트리플 저장소 모델은 속성 그래프 모델과 거의 동등하다.
트리플 저장소에서는 모든 정보를 주어, 서술어, 목적어처럼 매우 간단한 세부분구문 형식으로 저장한다.
트리플의 주어는 그래프의 정점과 동등하다.
목적어나 서술어는 1. 문자열이나 숫자 같은 원시 데이터타입의 값인 경우, 주어 정점에서 속성의 키, 값과 동등하고 2. 그래프의 다른 정점일 경우, 서술어는 그래프의 간선이고 주어는 꼬리 정점이며 목적어는 머리 정점이다.
시멘틱 웹
시멘틱 웹은 트리플 저장소와 완전히 독립적이나 많은 사람들이 밀접한 관계가 있다고 생각한다.
시멘틱 웹이라는 개념은, 웹사이드가 이미 사람이 읽을 수 있는 텍스트와 그림으로 정보를 게시하고 있으니 컴퓨터가 읽게끔 기계가 판독 가능한 데이터로도 정보를 게시하는 건 어떨까라는 개념이다.
여기서 RDF(Resource Description Framework)라는 개념이 등장하는데, 서로 다른 웹사이트의 데이터가 일종의 전 인터넷 만물 데이터베이스인 데이터 웹에 자동으로 결합할 수 있게 하는 것이다.
-> 현재는 거의 사용되지 않는 듯 하다.
RDF 데이터 모델
RDF관점에서 서술어는 데이터를 다른 사람의 데이터와 결밯하기 위해서 URL을 사용할수도 있다. 여기서는 단순한 네임스페이스이다.
스파클 질의언어
RDF데이터 모델을 사용한 트리플 저장소 질의언어다.
[그래프 모델과 네트워크 모델의 차이]
네트워크 모델은 다른 레코드 타입과 중첩가능한 레코드 타입을 지정하는 스키마가 있다. 그래프 모델은 이러한 제한 없이 모든 정점은 다른 정점으로 가는 간선을 가질 수 있다. 즉 그래프 모델은 변화하는 요구 사항을 쉽게 적용할 수 있는 유연성을 준다.
네트워트 모델에서 특정 레코드에 도달하는 유일한 방법은 레코드의 접근 경로 중 하나를 탐색하는 것이다. 그래프 모델은 고유 ID를 가지고 임의 정점을 직접 참조하거나 색인을 사용해 특정 값을 가진 정점을 빠르게 찾을 수 있다.
네트워크모델에서 결국 하위 항목은 정렬된 집합이므로 데이터 베이스는 정렬을 유지해야 한다. 따라서 집합에서 새로운 레코드의 위치를 염두에 두어야 한다. 그래프 모델에서 정점과 간선은 정렬하지 않는다.
가장 큰 차이는 네트워크 모델 질의는 명령형이다.
초석: 데이터 로그
질의 언어의 기반이 되는 초석을 제공했다. 데이터로그의 데이터 모델은 트리플 저장소 모델과 유사하지만 조금 더 일반화 됐다.
데이터 로그 접근방식은 질의언어와는 다른 사고가 필요하다. 그러나 다른 질의 규칙을 결합하거나 재사용할 수 있기때문에 강력한 접근 방식이다. 간단한 일회성 질의에 사용하기는 편리하지 않지만 데이터가 복잡하면 더 효과적으로 대처할 수 있다.
정리
정리하면 데이터 모델은 사실 엄청나게 광범위한 주제이다. 상황에 따라 적절한 모델을 선택해서 사용하면 되는 것이다.
기본적으로 데이터를 하나의 큰 트리(계층)로 표현하려 했으나 다대다 관계에서는 적절하지 않았고, 이를 위해 관계형 모델이 고안됐다.
그러다 관계형 모델에도 적합하지 않은 애플리케이션이 있다는 사실을 발견했고 이 것이 NoSQL이다. 이외에도 다양한 데이터 모델이 있다.
대표적인 세가지 모델인 문서, 관계형 그래프 모델은 현재 널리 사용되고 있다. 그러나 각각은 단일 만능 솔루션이 아니라서 각기 목적에 맞는 다양한 시스템을 보유해야한다.
문서및 그래프 모델이 가진 공통점 중 하나는 일반적으로 저장할 데이터를 위한 스키마를 강제하지 않아 변화하는 요구사항에 맞춰 애플리케이션을 쉽게 변경할 수 있다는 점이다. 하지만 애플리케이션은 데이터가 특정 구졸르 갖는다고 가정할 가능성이 높다.
또한 각 데이터 모델은 고유한 질의 언어나 프레임 워크를 제공한다.
'WIR(What I Read)' 카테고리의 다른 글
[데이터 중심 애플리케이션 설계] CH 03. 저장소와 검색(2) (0) | 2023.04.11 |
---|---|
[데이터 중심 애플리케이션 설계] CH 01. 신뢰할 수 있고 확장 가능하며 유지보수하기 쉬운 애플리케이션 (0) | 2023.03.21 |
[하둡 완벽 가이드]Ch07. 맵리듀스 작동방법 (0) | 2022.10.23 |
[하둡 완벽 가이드]Ch04. YARN (1) | 2022.10.09 |
[하둡 완벽 가이드]Ch03. 하둡분산 파일 시스템 (0) | 2022.10.04 |