[머신러닝 시스템 설계] Ch.3 머신러닝 엔지니어링 기초
<머신러닝 시스템 설계>의 'ch.3 머신러닝 엔지니어링 기초'의 내용을 요약 및 정리한 내용입니다.
https://product.kyobobook.co.kr/detail/S000201212403
머신러닝 시스템 설계 | 칩 후옌 - 교보문고
머신러닝 시스템 설계 | 프로덕션 환경에서 머신러닝을 다룰 때무수히 생겨나는 물음표를 해결해줄 MLOps 지침서머신러닝 시스템 개발은 선형이 아닌 순환 프로세스다. 모델을 개발해 배포하고
product.kyobobook.co.kr
0. 개요
'ch.3 머신러닝 엔지니어링 기초'에서는 데이터 엔지니어링의 기본을 다룹니다.
전체적인 개요는 아래와 같습니다.
- 1. 데이터 소스
- ML 프로젝트에서 사용하는 다양한 데이터 소스를 살펴봅니다.
- 2. 데이터 포맷
- 데이터를 저장하는 포맷에 대해 알아봅니다.
- 3. 데이터 모델
- 특정 데이터 포맷으로 저장된 데이터가 구조화되는 방식인 데이터 모델에 대해 알아봅니다.
- 4. 데이터 스토리지 엔진 및 처리
- 데이터 스토리지는 다른 말로 데이터베이스라고 하며 데이터가 시스템에 저장되는 방식에 대해서 알아봅니다.
- 5. 데이터 플로 모드
- 프로덕션에서는 일반적으로 여러 프로세스 및 서비스에 걸쳐 처리합니다. 이때 프로세스에서 다른 프로세스로 데이터가 전달되는 데이터플로에 대해서 알아봅니다.
- 6. 배치 처리 vs. 스트림 처리
- 데이터 스토리지 엔진에서 사용하는 두 가지 데이터 유형과 각 유형에 필요한 처리 패러다임에 대해서 알아봅니다.
1. 데이터 소스
ML 시스템은 다양한 소스에서 온 데이터로 작동합니다. 데이터마다 특성, 목적, 처리 방법이 다르며 데이터 소스를 파악하면 데이터를 보다 효율적으로 사용하는 데 도움이 됩니다. 따라 다양한 프로덕션 데이터 소스를 간략히 소개합니다.
1.1 사용자 입력 데이터
- 사용자가 명시적으로 입력하는 데이터 (텍스트, 이미지, 비디오, 업로드된 파일 등)
- 사용자가 원격으로 잘못된 데이터를 입력할 수 있기에 잘못되기 쉽습니다. (잘못된 길이, 형식, 파일 업로드)
- 오류가 발생 될 가능성이 높기에 철저한 검사와 처리가 필요합니다.
- 사용자가 데이터를 입력했을 때, 빠른 결과 처리가 필요한 경향이 있습니다.
1.2 시스템 생성 데이터
- 시스템의 여러 구성 요소에서 생성 (다양한 로그와 모델 예측 같은 시스템 출력 등)
- 로그
- 시스템의 상태와 중요한 이벤트를 기록합니다. (메모리 사용량, 인스턴스 수, 사용된 패키지 등)
- 데이터 처리 및 모델 훈련을 위한 대규모 배치 작업을 비롯한 다양한 작업의 결과를 기록합니다.
- 애플리케이션의 디버깅과 잠재적으로 성능을 개선하기 위해 시스템이 어떻게 작동하는지에 대한 가시성을 제공합니다. 이는 사고가 발생했을 때 매우 중요합니다.
- 시스템에서 생성되므로 포맷이 잘못될 가능성이 사용자 입력 데이터에 비해 훨씬 낮습니다.
- 일반적으로 사용자 입력 데이터와 달리 빠르게 처리하기 보단 주기적으로 처리가 필요합니다. 단, 사고가 발생했을때 감지하고 알람을 받기 위해서는 빠르게 처리해야 하기도 합니다.
- ML 시스템을 디버깅하기는 어려우므로 일반적으로 가능한 모든 것을 기록합니다. 이는 로그 볼륨을 빠르게 증가시킵니다.
- 로그 볼륨이 증가할 경우의 문제점 두 가지
- 신호에 잡음이 섞여 문제를 파악하기 어렵습니다. 따라 다양한 서비스에서 로그를 처리하고 이해하는데 도움을 줍니다.
- 급증하는 로그를 저장할 방법을 결정하기 어렵습니다. 대부분은 로그가 유용할 때만 저장하고 시스템을 디버깅하는데 관련이 없어지면 삭제합니다. 하지만 로그에 자주 액세스하지 않을 경우에가 요구 될 경우에는 낮은 액세스 스토리지에 저장해 비용을 절약해야 합니다.
- ML 시스템에서 사용자 행동을 기록하는 데이터를 생성하기도 합니다. (클릭, 제안 선택, 스크롤, 확대 및 축소 등)
- ML 시스템에서 생성되었다 하더라도 사용자 행동을 기록하는 데이터는 사용자 데이터의 일부로 간주되며 개인 정보 보호 규정이 적용됩니다.
1.3 내부 데이터베이스
- 회사의 다양한 서비스 및 엔터프라이즈 애플리케이션에서 생성됩니다.
- 재고, 고객 관계, 사용자를 비롯한 자산을 관리합니다.
- ML 모델에서 직접 사용되거나 ML 시스템의 다양한 구성 요소에서 사용됩니다.
1.4 다양한 파티 데이터
- 퍼스트 파티 데이터
- 회사에서 사용자 또는 고객에 대해 이미 수집하고 있는 데이터
- 세컨드 파티 데이터
- 다른 회사에서 자체 고객에 대해 수집하는 데이터
- 제공을 받기 위해선 비용을 지불해야 합니다.
- 서드 파티 데이터
- 회사의 직접적인 고객이 아닌 공공 데이터
- 인터넷과 스마트폰의 발달로 수집하기 쉬워졌습니다.
- 다양한 데이터의 종류가 존재합니다. (소셜 미디어 활동, 구매 내역, 웹 브라우징 습관 등)
- 사용자의 관심사와 관련된 결괏값을 생성하는데 유용하며, 공급업체에서 정리 및 처리한후 판매됩니다.
2. 데이터 포멧
데이터는 일회성으로 사용하지 않는 이상 저장이 필요합니다. 기술 용어로는 데이터를 '지속'시킨다고 말합니다. 데이터는 다양한 소스에서 가져오고 액세스 패턴도 다르므로 저장하기가 항상 간단하지는 않으며 때때로 비용이 많이 듭니다. 따라서 데이터가 향후 어떻게 사용될지 고려해 포맷을 선택해야 합니다.
고려해야 할 질문의 예시는 아래와 같습니다.
- 멀티모달 데이터 (예: 이미지와 텍스트를 모두 포함하는 데이터)는 어떻게 저장하나요?
- 저렴하고 빠르게 액세스 하려면 데이터를 어디에 저장해야 하나요?
- 복잡한 모델을 다른 하드웨어에서 올바르게 로드하고 실행하려면 어떻게 저장해야 하나요?
데이터 직렬화란 데이터 구조나 객체 상태를 저장 혹은 전송하고 나중에 재구성할 수 있는 포맷으로 변환하는 프로세스입니다. 직렬화 포맷은 매우 다양합니다. 작업할 포맷을 고려할 때는 액세스 패턴, 사람이 읽을 수 있는지, 텍스트인지 이진인지(이는 파일 크기에 영향을 미침) 등 다양한 특성을 고려합니다. 아래의 표는 작업에서 흔히 맞닥뜨리는 몇 가지 포맷 예시입니다.
포멧 | 이진/텍스트 | 사람이 읽을수 있는가? | 유스 케이스 |
JSON | 텍스트 | 예 | 매우 다양함 |
CSV | 텍스트 | 예 | 매우 다양함 |
파케이 | 이진 | 아니오 | 하둡, 아마존 레드시프트 |
Avro | 이진 포맷이 기본 | 아니오 | 하둡 |
Protobuf | 이진 포맷이 기본 | 아니오 | 구글, 텐서플로(TFRecord) |
Pickle | 이진 | 아니오 | 파이썬, 파이토치 직렬화 |
이어서 몇 가지 포맷을 살펴보겠습니다. 먼저 JSON을 알아본 뒤 공통점이 있으면서도 각각 고유한 패러다임을 나타내는 CSV와 파케이(Parquet)를 살펴봅니다.
2.1 JSON
JSON(JavaScript Object Notation)은 자바스크립트에서 파생되어 현재 널리 활용되는 포맷입니다.
- 장점
- 언어 독립적이며 최신 프로그래밍 언어는 대부분 JSON 생성과 파싱을 지원합니다.
- JSON은 사람이 읽을 수 있습니다.
- 키-값 쌍 패러다임은 단순하지만 강력하며 다양한 수준의 정형 데이터를 처리합니다.
- 단점
- JSON 파일의 데이터는 스키마에 커밋한 후 스키마를 변경하기 위해 다시 되돌아가는 일이 상당히 번거롭습니다.
- JSON 파일은 텍스트 파일이므로 저장 공간을 많이 차지합니다.
다음은 JSON 파일의 예시입니다.
{
"firstNmae": "Boatie",
"lastName": "McBoatFace",
"isVibing": true,
"age": 12,
"address": {
"streetAddress": "12 Ocean Drive".
"city": "Port Royal",
"postalCode": "10021-3100"
}
}
다음은 동일한 데이터를 비정형 텍스트 블롭으로 저장하는 예입니다.
{
"text" : "Boatie McBoatFace, aged 12, is vibing, at 12 Ocean Drive, Port Royal, 10021-3100"
}
2.2 행 우선 포맷 vs. 열 우선 포맷
2.2.1 행 우선 포맷 (CSV)
- CSV는 행 우선으로, 행의 연속 요소가 메모리에 나란히 저장됩니다. 즉, 데이터를 행렬로 저장하고 검색합니다.
- 테이블이 행 우선이라면 행에 액세스 하는 편이 더 빠릅니다. (샘플에 액세스하기에 좋음)
- 데이터 쓰기를 많이 수행할 때 행 우선 포맷이 더 빠릅니다. (데이터에 새로운 예제를 추가해야 되는 상황 등)
2.2.2 열 우선 포맷 (파케이_Parquet)
- 파케이는 열 우선으로, 열의 연속 요소가 메모리에 나란히 저장됩니다. 즉, 데이터를 열별로 저장하고 검색합니다.
- 테이블이 열 우선이라면 열에 액세스 하는 편이 더 빠릅니다. (피처에 액세스하기에 좋음)
- 열 기반 읽기를 많이 수행할 때는 열 우선 포맷이 더 빠릅니다. (데이터에서 원하는 피처만 추출하는 상황 등)
2.3 텍스트 포맷 vs. 이진 포맷
2.3.1 텍스트 포맷
- CSV 와 JSON 등이 있습니다.
- 텍스트 파일은 일반 텍스트로 된 파일로, 대개 사람이 읽을 수 있습니다.
2.3.2 이진 포맷
- 피케이 파일 등이 있습니다.
- 텍스트가 아닌 모든 파일을 말하며, 0과 1만 포함합니다.
- 원시 바이트를 해석하는 방법을 알고 있는 프로그램에서 읽거나 사용하기 위한 파일입니다.
- 텍스트 파일에 비해 공간을 절약합니다.
3. 데이터 모델
- 데이터 모델은 데이터가 어떻게 표현되는지 설명합니다.
- 예) 자동차일 경우
- 데이터 베이스 : 자동차 제조사, 모델, 연도, 색상, 가격 등
- 데이터 모델 : 위의 데이터 베이스의 속성으로 구성된 자동차 모델
- 예) 자동차일 경우
- 데이터를 표현하는 방법을 시스템을 구축하는 방식뿐 아니라 시스템이 해결하는 문제에도 영향을 미칩니다.
3.1 관계형 모델
- 관계형 모델에서 데이터는 관계로 구성되며 각 관계는 튜플의 집합입니다.
- 테이블은 관계를 시각적으로 표현한 것으로 테이블의 각 행이 튜플을 구성합니다.
- 관계는 순서가 없습니다. 그렇기에 행의 순서나 열의 순서를 섞더라도 여전히 동일한 관계입니다.
- 관계형 모델을 따르는 데이터는 일반적으로 CSV나 파케이 같은 파일 포맷으로 저장됩니다.
아래의 테이블은 관계형 모델의 예시입니다.
제목 | 작가 | 포맷 | 출판사 | 출판 국가 | 가격 |
해리 포터 | J.K. 롤링 | 종이책 | 바나나 출판 | UK | $20 |
해리 포터 | J.K. 롤링 | 전자책 | 바나나 출판 | UK | $10 |
셜록 홈즈 | 코난 도일 | 종이책 | 파인애플 출판 | US | $30 |
호빗 | J.R.R. 톨킨 | 종이책 | 바나나 출판 | UK | $30 |
셜록 홈즈 | 코난 도일 | 종이책 | 파인애플 출판 | US | $15 |
3.1.1 관계의 정규화
- 관계형의 경우 정규화 하는 편이 좋은 경우가 많습니다.
- 데이터 정규화는 제1정규형 (1NF), 제2정규형 (2NF) 등 정규화를 따릅니다.
- 데이터 정규화는 데이터의 값을 수정하는데 유리합니다.
- 정규화의 주요 단점은 데이터가 여러 관계로 분산되는 점입니다. 분산된 테이블은 다시 조인할 수도 있지만 테이블이 크다면 조인에 비용이 많이 드는 문제가 있습니다.
아래의 표는 위의 관계형 모델의 예시를 '출판사 관계'로 정규화한 예시입니다.
출판사 ID (열 1) | 출판사 (열 2) | 출판 국가 (열 3) |
1 | 바나나 출판 | UK |
2 | 파인애플 출판 | US |
3.1.2 관계형 데이터 베이스와 쿼리 언어
- 관계형 모델을 기반으로 구축된 데이터 베이스를 관계형 데이터베이스라고 합니다.
- 데이터 베이스에 저장된 데이터를 검색하여 원하는 데이터를 지정하는데 사용하는 언어를 쿼리언어라고 합니다.
- 오늘날 관계형 데이터베이스에서 가장 많이 사용하는 쿼리 언어는 SQL 입니다.
- SQL 은 선언적 언어이며, 이는 원하는 출력을 지정해주면 컴퓨터가 쿼리된 출력을 얻는데 필요한 단계를 파악합니다.
- 몇 가지 피처의 추가를 통해 튜링하여 이론적으로는 SQL로 모든 계산 문제를 해결할 수 있습니다.
- 하지만 실제로는 특정 작업을 해결하기 위해 쿼리를 작성하는 일이 항상 쉽지는 않으며, 쿼리를 실행하는 일 또한 항상 가능하거나 다루기 쉽지 않습니다.
- 임의의 쿼리를 실행하는 방법을 알아내기는 어렵기에, 쿼리 옵티마이저를 통해 가능한 쿼리 실행 방법을 모두 검사해 빠른 방법을 찾습니다.
- ML을 사용해 들어오는 쿼리에서 학습한 내용을 기반으로 쿼리 옵티마이저를 개선합니다.
- 쿼리 최적화는 데이터 베이스 시스템에서 매우 어려운 문제입니다. 그렇기에 쿼리 옵티마이저는 개발하기 어렵지만 하나만 있어도 일반적으로 모든 애플리케이션에서 활용할 수 있다는 장점이 존재합니다.
3.2 NoSQL
- 관계형 데이터 모델은 수많은 유스케이스로 보편화되어있지만, 데이터가 엄격한 스키마를 따라야 하고 스키마 관리가 어렵다는 점, 특화된 애플리케이션을 위한 SQL 쿼리를 작성하고 실행하기 어렵다는 단점이 존재합니다.
- 위의 단점을 해결하기 위해 등장한 것이 바로 NoSQL 입니다.
- NoSQL은 비관계형 데이터 베이스를 논의하는 모임의 해시태그로 시작했으나, 현재는 'Not Only SQL'로 재해석됐습니다.
- 비관계형 모델의 주요 유형 두 가지는 문서 모델과 그래프 모델입니다.
- 문서 모델이 유용한 경우는 데이터가 독립적인 문서로 제공되고, 한 문서와 다른 문서 간의 관계가 드문 유스케이스 입니다.
- 그래프 모델이 유용한 경우는 데이터 항목 간의 관계가 흔하며 중요한 유스케이스 입니다.
3.2.1 문서 모델
- '문서'라는 개념을 기반으로 구축됐습니다.
- 문서는 종종 단일 연속 문자열로, JSON, XML 또는 이진 형식인 BSON으로 인코딩 됩니다.
- 문서 데이터베이스 내 모든 문서는 동일한 포맷으로 인코딩됐다고 가정합니다.
- 각 문서마다 고유한 키가 있어 문서를 검색하는데 사용됩니다.
문서 컬렉션과 관계형 데이터 베이스
- 문서 컬렉션은 관계형 데이터베이스의 테이블과 유사하며 문서는 행과 유사합니다. 그렇기에 이러한 방식을 ㅗ관계를 문서 컬렉션으로 변환할 수도 있습니다.
- 문서 컬렉션은 테이블보다 훨씬 유연합니다. 그렇기에 테이블에서는 모든 행이 동일한 스키마를 따라야하지만 같은 컬렉션에 있는 문서들 간에는 스키마가 완전히 다를 수 있습니다.
아래의 경우 문서 컬렉션의 예시입니다.
{
"제목": "해리포터",
"작가": "J. K. 롤링",
"출판사": "바나나 출판",
"출판 국가": "UK",
"판매 정보": [
{"포맷": "종이책", "가격": "$20"},
{"포맷": "전자책", "가격": "$10"},'
]
}
- 문서 모델은 스키마를 적용하지 않아 종종 스키마리스 모델이라고 부릅니다. 하지만 이는 오해의 소지가 있으며, 문서를 읽는 애플리케이션에서 문서의 구조를 가정합니다.
- 문서 모델은 관계형 모델보다 지역성이 우수합니다. 그렇기에 검색할 경우, 관계형 모델보다 더 유리합니다.
- 하지만 문서간 조인은 관계형 모델보다 어렵고 비효율적입니다.
- 문서 모델과 관계형 모델의 강점이 각각 다릅니다. 그렇기에 한 데이터베이스 시스템에서 두 모델을 각기 다른 작업에 사용하는 일이 일반적입니다. 따라 PostSQL과 MySQL 을 비롯해 점점 더 많은 데이터베이스 시스템에서 두 모델을 모두 지원합니다.
3.2.2 그래프 모델
- 그래프 개념을 기반으로 구축됐습니다.
- 그래프는 노드와 에지로 구성되며, 에지는 노드 간의 관계를 나타냅니다.
- 그래프 구조로 데이터를 저장하는 데이터베이스를 그래프 데이터베이스라고 하며, 이는 데이터 항목 간의 관계가 우선시 됩니다.
- 그래프 모델에서는 관계를 명시적으로 모델링하므로 관계를 기반으로 검색하는 것이 빠릅니다.
데이터 모델에 따라 수행하기 쉬운 쿼리가 있고 어려운 쿼리가 있습니다. 따라서 애플리케이션에 적합한 데이터 모델을 선택하는 것이 바람직합니다.
3.3 정형 데이터 vs. 비정형 데이터
3.3.1 정형데이터
- 정형 데이터는 미리 정의된 데이터 모델, 즉 데이터 스키마를 따릅니다.
- 정형 데이터를 저장하는 저장소를 데이터 웨어하우스라고 부릅니다.
- 일반적으로 데이터 웨어하우스는 사용 가능한 형식으로 처리된 데이터를 저장하는데 사용합니다.
- 장점
- 미리 정의된 구조를 사용하기에 데이터를 분석하기가 더 쉽습니다.
- 단점
- 데이터를 미리 정의된 스키마에 맞춰줘야 합니다.
- 스키마가 변경되면 모든 데이터를 소급해 업데이트해야하며, 이때 종종 버그가 발생하기도 합니다.
3.3.2 비정형 데이터
- 미리 정의된 데이터 스키마를 따르지 않습니다.
- 일반적으로 텍스트 형태이지만, 숫자, 날짜, 이미지, 오디오 등의 형태의 데이터도 가능합니다.
- 스키마를 따르지 않지만 구조를 추출하는데 도움이 되는 고유 패턴을 포함하기도 합니다.
- 비정형 데이터를 저장하는 저장소를 데이터 레이크라고 부릅니다.
- 일반적으로 데이터 레이크는 처리 전 원시 데이터를 저장하는데 사용됩니다.
- 장점
- 모든 행이 해당 패턴을 따라야 할 필요가 없으며, 포맷을 따르지 않더라도 새로운 행으로 추가할 수 있습니다.
- 보다 유연한 스토리지 옵션을 허용합니다. 이는 유형과 포맷에 관계없이 모든 데이터를 바이트스트링으로 변환해 함께 저장할 수 있음을 의미합니다.
- 단점
- 스키마와 구조가 존재하지 않기에 관리하기에 어렵습니다.
위의 내용을 정리하면 아래와 같습니다.
정형 데이터 | 비정형 데이터 |
스키마가 명확히 정의됨 | 스키마를 따르지 않아도 됨 |
검색 및 분석이 간편함 | 전처리 등을 하지 않고 바로 저장 가능함 |
특정 스키마를 따르는 데이터만 처리 가능함 | 어떤 소스에서 온 데이터든 처리 가능함 |
스키마 변경이 많은 문제를 야기함 | 스키마 변경을 아직 걱정하지 않아도 됨 (데이터를 사용하는 다운스크팀 애플리케이션에서 고려) |
데이터 웨어하우스에 저장됨 | 데이터 레이크에 저장함 |
4. 데이터 스토리지 엔진 및 처리
데이터 포맷과 데이터 모델은 사용자가 데이터를 저장하고 검색하는 방법과 관련한 인터페이스를 지정합니다. 데이터베이스라고도 하는 스토리지 엔진은 데이터가 시스템에 저장되고 검색되는 방식을 구현합니다.
일반적으로 데이터베이스가 최적화되는 워크로드에는 트랜잭션 처리와 분석 처리, 두 가지 유형이 있습니다. 둘 사이에는 큰 차이가 존재하기에 해당 차이점을 알아본 후, 프로덕션에서 ML시스템을 구축할 때 반드시 접하게 되는 ETL(추출, 변환, 적재) 프로세스의 기본을 알아봅니다.
4.1 트랜잭션 처리와 분석 처리
트랜잭션
- 트랜잭션은 트윗 보내기, 신규 모델 업로드하기, 유튜브 동영상 보기 등 온갖 작업을 의미합니다.
- 트랜잭션마다 포함하는 데이터는 각기 다르지만 그 처리 방식은 애플리케이션 간에 유사합니다.
- 온라인 트랜잭션 처리(OLTP)
- 트랜잭션은 생성될 때 삽입되고 때때로 변경될 때 업데이트되며 필요하지 않아지며 삭제됩니다. 이러한 처리를 온라인 트랜잭션 처리(OLTP)라고 합니다.
- 트랜잭션에는 사용자가 관련되는 경우가 많으므로 사용자가 기다리지 않도록 빠르게 처리해야하며 처리 방법은 가용성이 높아야 합니다. 즉, 처리 시스템은 사용자가 트랜잭션을 수행하고자 할 때 언제든지 사용 가능해야 합니다.
- 시스템에서 트랜잭션을 처리할 수없으면 트랜잭션이 진행되지 않습니다.
트랜잭션 데이터베이스
트랜잭션 데이터베이스는 온라인 트랜잭션을 처리하고 낮은 레이턴시와 고가용성 요구사항을 충족하고자 설계됐습니다.트랜잭션 데이터베이스라고 하면 일반적으로 ACID(원자성, 일관성, 격리성, 지속성)를 생각합니다. 각각의 정의는 아래와 같습니다.
- 원자성
- 트랜잭션의 모든 단계가 하나의 그룹으로서 성공적으로 완료되도록 보장합니다. 한 단계가 실패하면 나머지 단계들도 모두 실패합니다.
- 일관성
- 들어오는 모든 트랜잭션이 미리 정의된 규칙을 따라야 함을 보장합니다. 예를 들어, 유효한 사용자가 트랜잭션을 수행해야 합니다.
- 격리성
- 두 트랜잭션이 마치 격리된 것처럼 동시에 발생하도록 보장합니다. 사용자 두 명이 동일한 데이터에 액세스 하는 경우 둘이 동시에 데이터를 변경하지 않습니다.
- 지속성
- 트랜잭션이 커밋된 후에는 시스템 장애가 발생하더라도 커밋된 상태를 유지하도록 보장합니다.
다만 트랜잭션 데이터베이스가 반드시 ACID일 필요는 없습니다.
- 온라인 분석 처리 (OLAP)
- 각 트랜잭션은 종종 다른 트랜잭션과 별개의 단위로 처리되므로 트랜잭션 데이터베이스는 행 우선일 때가 많습니다. 이러한 방법은 여러 행에 걸쳐 있는 열 데이터를 집계하는데 비효율적입니다.
- 분석 데이터 베이스는 행 뿐만 아니라 열 등 데이터를 다양한 관점에서 바라보는 쿼리에 효율적이며, 이러한 목적으로 설계됐습니다.
- 이러한 처리를 온라인 분석 처리(OLAP)라고 합니다.
하지만 이런 OLTP와 OLAP라는 용어는 이제는 세 가지 이유로 인해 많이 사용하지 않습니다.
첫째, 트랜잭션 데이터베이스와 분석 데이터베이스가 분리된 것은 기술의 한계 때문이었습니다. 예전에는 트랜잭션 쿼리와 분석 쿼리를 모두 효율적으로 처리하는 데이터베이스를 갖기가 어려웠죠. 하지만 이제는 그렇지 않습니다.
둘째, 기존의 OLTP와 OLAP 패러다임에서는 스토리지와 처리가 밀접하게 결함 돼 있습니다. 즉, 데이터 저장 방식이 곧 데이터 처리 방식입니다. 따라서 동일한 데이터가 여러 데이터베이스에 저장되고 각각 다른 처리 엔진을 사용해 각기 다른 유형의 쿼리를 해결하기도 합니다. 하지만 지난 10년간 많은 데이터 공급 업체에서 처리(컴퓨팅)와 스토리지를 분리하는 패러다임이 관찰됐습니다. 이 패러다임에서는 데이터가 동일한 위치에 저장되며 처리 레이어에서 각기 다른 유형의 쿼리에 최적화합니다.
셋째, '온라인'이라는 용어는 많은 것을 의미하는 과부하된 용어가 됐습니다. 예전에는 단지 '인터넷에 연결됨'을 뜻했지만 의미가 확대돼 '프로덕션 중임'을 뜻하기도 합니다. 즉, 피치가 프로덕션에 배포됐다면 '피처가 온라인이다'라고 합니다.
따라 오늘날 데이터 세계에서는 데이터가 처리되고 제공되는 속도를 나타낼 때 온라인, 니어라인, 오프라인 등을 사용합니다. 위키백과에 따르면 온라인 처리는 데이터를 즉시 입력 및 출력할 수 있음을 의미합니다. 니어라인은 니어-온라인의 줄임말로, 데이터를 즉시 사용할 수는 없지만 사람의 개입 없이 빠르게 온라인으로 만들 수 있음을 의미합니다. 오프라인은 데이터를 즉시 사용할 수 없으며 온라인으로 만드는데 사람의 개입이 필요하다는 의미입니다.
4.2 ETL: Extract, Transform, Load
관계형 데이터 모델의 초기에는 데이터가 대부분 정형화됐습니다.
데이터가 소스에서 추출되면 데이터베이스나 데이터 웨어하우스 같은 대상에 적재되기 전에 먼저 원하는 포맷으로 변환됩니다. 이 프로세스를 ETL이라고 하며 각 알파벳은 추출, 변환, 적재를 의미합니다.
ETL은 데이터를 범용 처리 및 원하는 모양과 포맷으로 집계함을 의미합니다.
- 추출 (Extract)
- 모든 데이터 소스에서 원하는 데이터를 추출하는 일입니다. 일부 데이터는 손상되거나 포맷이 올바르지 않은데, 추출 단계에서 데이터를 검증하고 요구 사항을 충족하지 않는 데이터는 거부한 뒤 소스에 알리기도 합니다. 디는 프로세스의 첫 번째 단계이므로 올바르게 수행하면 다운스트림 처리에 드는 시간이 크게 줄어듭니다.
- 변환 (Transform)
- 변환은 대부분의 데이터 처리가 수행되는 프로세스의 핵심 단계입니다. 여러 소스에서 온 데이터를 조인하고 정제하며 값 범위를 표준화합니다. 표준화 외에도 전치, 중복제거, 정렬, 집계, 새로운 피처 도출, 더 많은 데이터 유효성 검사와 같은 작업을 적용합니다.
- 로드 (Load)
- 로드는 변환된 데이터를 파일, 데이터베이스, 데이터 웨어하우스와 같은 대상에 적재할 방법과 빈도를 결정합니다.
ETL 개념은 간단하지만 강력하며 많은 조직에서 데이터 계층의 기본 구조로 사용됩니다.
ELT(추출, 적재, 변환)
인터넷이 보편화되고 하드웨어가 훨씬 강력해지자 데이터 수집이 갑자기 훨씬 쉬워졌습니다. 데이터 양이 급격히 증가할 뿐 아니라 데이터의 성격도 변했습니다. 데이터 소스가 많아지고 데이터 스키마가 진화했습니다.
따라 점차 데이터를 구조화한 상태로 유지하기가 어려워지자 데이터를 먼저 스토리지에 적재한 뒤 나중에 처리하는 프로세스인 ELT(추출, 적재, 변환)가 등장했습니다. 이 패러다임은 데이터 저장 전에 필요한 처리가 거의 없어 데이터를 신속히 저장할 수 있습니다.
하지만 ELT는 데이터가 증가함에 따라 점점 유효성이 떨어지게 됩니다. 방대한 원시 데이터에서 원하는 데이터를 검색하는 일은 비효율적입니다. 게다가 기업들이 애플리케이션은 클라우드에서 실행하게 되고 인프라가 표준화됨에 따라 데이터 구조도 표준화됐습니다. 데이터를 미리 정의된 스키마에 커밋하는 편이 더 합리적입니다.
5. 데이터플로 모드
앞서 단일 프로세스의 컨텍스트 내에서 사용되는 데이터 포맷, 데이터 모델, 데이터 저장 및 처리를 알아봤습니다. 그런데 프로덕션에서는 대개 프로세스가 하나가 아닌 여러 개입니다. 이때 의문이 생깁니다. 메모리를 공유하지 않는 서로 다른 프로세스 간에 데이터를 어떻게 전달할까요?
데이터가 한 프로세스에서 다른 프로세스로 전달될 때 데이터가 한 프로세스에서 다른 프로세스로 흐른다고 합니다. 즉, 데이터 플로가 생깁니다. 데이터플로에는 세 가지 주요 모드가 있습니다. 세 가지 주요 모드는 아래와 같습니다.
- 데이터베이스를 통한 데이터 전달
- 서비스를 통한 데이터 전달 ( 예 : REST와 RPC API에서 제공하는 요청(POST/GET 등)을 사용)
- 실시간 전송을 통한 데이터 전달 ( 예: 아파치 카프카, 아마존 키네시스)
이어서 각 모드를 하나씩 살펴보겠습니다.
5.1 데이터베이스를 통한 데이터 전달
- 두 프로세스 간에 데이터베이스를 통해 데이터를 전달하는 가장 쉬운 방법입니다.
- 예를 들어, A프로세스에서 B프로세스로 데이터를 전달하려면 A 프로세스는 해당 데이터를 데이터베이스에 쓰고 B 프로세스는 단순히 해당 데이터베이스에서 읽으면 됩니다.
- 하지만 해당 모드는 항상 작동하지는 않습니다. 여기에는 두 가지 이유가 있습니다.
- 두 프로세스가 동일한 데이터베이스에 액세스해야 하는데 이것이 불가능할 때도 있습니다. 특히 두 프로세스가 서로 다른 회사에서 실행된다면 실현 불가능합니다.
- 데이터베이스에서 데이터에 액세스 하려면 두 프로세스가 모두 필요하며 데이터베이스에서 읽기 및 쓰기가 느려질 수 있습니다. 따라서 레이턴시 요구 사항이 엄격한 애플리케이션에는 적합하지 않습니다.
5.2 서비스를 통한 데이터 전달
- 두 프로세스 간에 둘을 연결하는 네트워크를 통해 직접 데이터를 전달하는 방법입니다.
- 예를 들어, B 프로세스에서 A 프로세스로 데이터를 전달한다고 합시다. A 프로세스는 필요한 데이터를 지정하는 요청을 B 프로세스에 보내고, B는 동일한 네트워크를 통해 요청된 데이터를 반환합니다.
- 프로세스가 요청을 통해 통신하므로 이를 요청 기반이라고 합니다.
- 해당 모드는 서비스 지향 아키텍처와 밀접하게 결합돼 있습니다.
- 서비스는 네트워크를 통해 원격으로 접근하는 프로세스를 의미합니다. 즉, 각각의 프로세스가 네트워크 요청을 통해 서로에게 서비스로서 노출되어야 합니다.
- 서로 통신하는 두 서비스는 독립적인 회사에서 별개의 애플리케이션에 의해 운영될 수도 있습니다.
- 서로 통신하는 두 서비스가 동일한 애플리케이션의 일부 일 수도 있습니다. 애플리케이션의 여러 구성 요소를 각각 별도의 서비스로 구성하면 각 요소를 독립적으로 개발하고 테스트 및 유지 관리할 수 있으며, 이렇게 구조화하는 것을 마이크로서비스 아키텍처라고 합니다.
- 네트워크를 통한 데이터를 전달에 사용하는 요청 스타일로는 REST와 RPC가 가장 인기 있습니다.
- 두 요청 스타일의 주요 차이점은 REST는 네트워크를 통한 요청을 위해 설계된 반면, RPC는 원격 네트워크 서비스에 대한 요청이 프로그래밍 언어로 함수나 메서드를 호출하는 것과 동일하게 보이도록 합니다.
- 마팀 클레프만에 따르면 REST는 공공 API의 주된 스타일이며 RPC 프레임워크의 초점은 일반적으로 동일한 데이터 센터 내에서 동일한 조직이 소유한 서비스 간의 요청에 있습니다.
- REST 아키텍처의 구현을 RESTful이라고 합니다. Rest 가 곧 HTTP라고 생각하는 사람들이 많지만 HTTP는 REST의 구현일 뿐이고 정확히 HTTP를 의미하지는 않습니다.
5.3 실시간 전송을 통한 데이터 전달
서비스가 매우 많으면 서비스 간 데이터 전달이 폭발적으로 증가하고 병목이 돼 전체 시스템 속도를 늦춥니다. 요청 기반 데이터 전달은 동기식입니다. 즉 대상 서비스는 요청을 수신하고 처리하도록 합니다. 이는 서비스가 데이터를 요청했는데 다른 서비스가 다운됐다면 시간이 초과될 때까지 요청을 계속 재전송하는 문제나 서비스가 응답을 받기 전에 다운되면 그 응답이 손실되는 문제가 발생됩니다. 즉, 서비스가 중단되면 해당 서비스의 데이터가 필요한 서비스들이 모두 중단됩니다.
그렇다면 서비스 간 데이터 전달을 데이터베이스를 통해서 요청하면 어떨까요? 그렇다면 서비스까리 직접 데이터를 요청하고 복잡한 서비스 간 데이터 전달망을 생성하는 대신 각 서비스가 데이터베이스와 통신하기만 하면 됩니다.
각 서비스는 데이터베이스에 데이터를 쓰고, 그 데이터가 필요한 서비스는 해당데이터 데이터베이스에서 데이터를 읽습니다. 하지만 데이터베이스에서 일고 쓰는 것은 레이턴시 요구 사항이 있는 애플리케이션에서는 너무 느립니다. 따라서 데이터 베이스가 아니라 메모리 내 스토리지를 사용해 중개합니다. 실시간 전송을 서비스 간 데이터 전달을 위한 인메모리 스토리지로 생각해도 됩니다.
실시간 전송으로 브로드캐스트 되는 데이터 조각을 이벤트라고 하며, 따라서 이 아키텍처를 이벤트 기반이라고도 합니다. 그리고 실시간 전송을 이벤트 버스라고도 합니다.
요청 기반 아키텍처는 데이터보다 로직에 더 의존하는 시스템에 적합하며 이벤트 기반 아키텍처는 데이터가 많은 시스템에서 더 잘 작동합니다.
실시간 전송의 가장 일반적인 유형 두 가지
- 실시간 전송의 가장 일반적인 유형 두가지로는 'pubsub'과 '메시지 큐'가 있습니다.
- pubsub
- pubsub 모델에서 모든 서비스는 실시간 전송으로 여러 토픽에 게시할 수 있으며, 토픽을 구독하는 모든 서비스는 해당 토픽의 모든 이벤트를 읽을 수 있습니다.
- 데이터를 생성하는 서비스는 그 데이터를 어떤 서비스에서 소비하는지 관심없습니다.
- pubsub 솔루션에선 종종 리텐션 정책이 존재합니다. 이는 데이터는 삭제되거나 영구 스토리지로 이동되기 전에 특정 기간 실시간 전송으로 보존되는 것을 의미합니다.
- pubsub 솔루션의 예로는 아파치 카프카와 아마존 키네시스가 해당합니다.
- 메시지 큐
- 메시지 큐 모델에서 이벤트에는 종종 대상 소비자가 있습니다.
- 메시지 큐는 메시지를 알맞은 소비자에게 전달합니다. 이때 대상 소비자가 있는 이벤트를 메시지라고 합니다.
- 메시지 큐의 예시로는 아파치 로켓MQ와 래빗MQ가 해당합니다.
6. 배치 처리 vs. 스트림 처리
6.1 배치 처리
- 데이터는 데이터 스토리지 엔진에 도착하면 과거 데이터가 됩니다.
- 과거 데이터는 주기적으로 시작되는 배치 작업에서 처리되는 경우가 많습니다.
- 데이터를 배치 작업에서 처리하는 것을 배치 처리라고 합니다.
- 배치 계산 엔진으로 스파크와 맵리듀스 등이 있습니다.
- 일반적으로 자주 변경되지 않는 피처를 계산하는데 사용합니다.
- 배치 처리를 통해 추출된 피처는 배치 피처이며, 정적 피처라고도 합니다.
6.2 스트림 처리
- 데이터 스토리지 엔진에 도착하지 않은 아직 스트리밍 데이터를 스트리밍 데이터라고 합니다.
- 스트림 처리는 스트리밍 데이터에 대한 계산을 의미합니다.
- 스트리밍 데이터에 대한 계산도 주기적으로 시작할 수 있지만 그 주기는 일반적으로 배치 작업보다 훨씬 짧습니다. 혹은 필요할 때마다 계산을 시작할 수도 있습니다.
- 스트림 처리가 제대로 수행되면 데이터가 생성되면 데이터베이스에 먼저 기록할 필요 없이 즉시 처리되기에 레이턴시가 짧습니다.
- 스트림 계산 엔진으로 아파치 플링크, KSQL, 스파크 스트리밍 등이 있습니다.
- 스트림 처리는 빠르게 변경되는 피처를 계산하는데 사용됩니다.
- 스트림 처리를 통해 추출된 피처는 스트리밍 피처이며, 동적 피처라고도 합니다.
- 스트림 처리의 강점
- 스트리밍 기술의 뛰어난 확장성과 완전 분산성이 입증됐습니다. 이는 병렬로 계산을 수행할 수 있음을 의미합니다.
- 스트림 처리는 상태 유지 계산에 뛰어납니다. 배치 작업과는 달리 신규 데이터만 계산하여 신규 데이터 계산을 통해 이전 데이터 계산과 결합해 중복을 방지할 수 있습니다.
- 스트림 처리의 단점
- 데이터 스트림에서 계산을 수행하려면 스트림 계산 엔진이 필요합니다. 이는 스트리밍 계산이 간단한 경우라면 아파치 카프카 등 실시간 전송의 내장 스트림 계산을 사용해도 되지만, 카프카 스트림 처리는 다양한 데이터 소스를 처리하는 기능에 한계가 있습니다.
- 스트리밍 기능을 활용하는 ML 시스템에서 스트리밍 계산은 간단하지 않습니다. 예를 들어 이상 거래 탐지나 신용 점수 계산 등에 사용되는 스트림 피처는 수천 개는 아닐지라도 수백 개에 이릅니다. 그렇기에 스트림 피처 추출 로직에는 서로 다른 차원을 따라 결합 및 집계가 포함된 복잡한 쿼리들이 필요합니다.
- 데이터가 들어오는 비율과 속도가 다양하고 그 양에도 제한이 없기에 스트림 처리가 훨씬 어렵습니다.