Post

[dbt 101] Day 1: ETL에서 ELT로, 그리고 dbt의 등장

[dbt 101] Day 1: ETL에서 ELT로, 그리고 dbt의 등장

지난주 우리는 Apache Airflow를 통해 데이터 파이프라인의 흐름을 제어하는 방법(Orchestration)을 다뤘다. Airflow는 ‘언제’ 작업을 실행할지 결정하고 의존성을 관리하는 데 탁월하다. 하지만 ‘무엇을’, 즉 데이터의 실질적인 변환 로직을 어떻게 관리할 것인가에 대한 물음은 여전히 남는다.

복잡한 SQL 파일들이 폴더 구석구석에 흩어져 있고, 테이블 간의 의존성을 파악하기 위해 수백 줄의 쿼리를 눈으로 디버깅해본 경험이 있다면, 오늘부터 시작하는 dbt(data build tool) 시리즈가 그 해답이 될 것이다.

데이터 처리 패러다임의 변화: ETL vs ELT

dbt를 논하기 전에 데이터 처리 아키텍처의 변화를 짚고 넘어가야 한다.

전통적인 ETL (Extract, Transform, Load)

과거에는 스토리지와 컴퓨팅 비용이 비쌌다. 따라서 데이터를 웨어하우스에 적재하기 전에 별도의 서버(ETL 서버)에서 불필요한 데이터를 정제하고 변환(Transform)하여 사이즈를 줄인 후 적재(Load)해야 했다.

이 방식은 데이터 웨어하우스의 부하를 줄여주지만, 변환 로직이 변경될 때마다 파이프라인 전체를 수정해야 하는 경직성을 가진다. 또한, 원본 데이터(Raw Data)가 유실될 가능성이 있다.

현대적인 ELT (Extract, Load, Transform)

Snowflake, BigQuery, Redshift와 같은 클라우드 데이터 웨어하우스(CDW)의 등장은 판도를 바꿨다. 스토리지는 저렴해졌고, 컴퓨팅 파워는 강력해졌다. 이제는 굳이 데이터를 밖에서 가공할 필요가 없다.

  1. Extract: 소스에서 데이터를 추출한다.
  2. Load: 가공하지 않은 Raw 데이터를 그대로 웨어하우스에 밀어 넣는다.
  3. Transform: 웨어하우스 내부의 강력한 SQL 엔진을 사용하여 변환한다.

이 변화는 데이터 엔지니어링의 중심축을 프로그래밍 언어(Python, Java)에서 SQL로 이동시켰다. 그리고 이 지점에서 dbt가 등장한다.

dbt란 무엇인가?

dbt(data build tool)는 ELT 파이프라인의 ‘T(Transform)’ 과정을 담당하는 오픈소스 도구다. 간단히 말해, 데이터 웨어하우스 안에서 SQL을 실행하여 테이블과 뷰를 생성하고 관리해 주는 프레임워크다.

하지만 단순히 SQL을 실행해 주는 도구라고만 하기엔 부족하다. dbt의 핵심 가치는 “데이터 변환 로직을 소프트웨어 엔지니어링의 모범 사례(Best Practices)처럼 다루게 해준다”는 점에 있다.

dbt가 제공하는 핵심 기능

  • Modular SQL: 긴 SQL을 모듈화 하여 재사용성을 높인다.
  • Version Control: 모든 변환 로직을 Git으로 관리할 수 있다.
  • Testing: 데이터 품질 검사(Primary Key 중복, Null 체크 등)를 코드 레벨에서 수행한다.
  • Documentation: 스키마와 테이블에 대한 문서를 자동으로 생성한다.

dbt 프로젝트의 기본 구조

dbt를 설치(pip install dbt-core)하고 프로젝트를 초기화하면 다음과 같은 구조를 갖게 된다.

1
2
3
4
5
6
7
8
my_dbt_project/
├── dbt_project.yml   # 프로젝트 설정 파일
├── models/           # SQL 파일들이 위치하는 핵심 디렉토리
│   ├── staging/      # Raw 데이터를 다듬는 계층
│   └── marts/        # 분석용 최종 테이블 계층
├── tests/            # 데이터 무결성 테스트
└── profiles.yml      # 데이터베이스 연결 정보 (보통 ~/.dbt/ 에 위치)

이 중 가장 중요한 것은 models 디렉토리다. 이곳에 작성된 .sql 파일 하나하나가 웨어하우스 내의 테이블 혹은 뷰(View)가 된다.

“SELECT 문만 작성하세요”

기존에는 테이블을 만들기 위해 DDL(Create Table…)과 DML(Insert/Update…)을 섞어서 작성해야 했다. dbt에서는 오직 SELECT 문만 작성하면 된다.

예를 들어, models/customers.sql 파일을 다음과 같이 작성했다고 가정하자.

1
2
3
4
5
6
7
-- models/customers.sql
select
    id as customer_id,
    first_name,
    last_name
from raw.jaffle_shop.customers

이제 터미널에서 dbt run을 실행하면, dbt는 이 파일을 감싸(Wrap) 대상 데이터 웨어하우스에 맞는 DDL로 변환하여 실행한다.

1
2
3
4
5
6
7
8
9
-- 실제 웨어하우스에서 실행되는 쿼리 (예시)
create or replace table analytics.customers as (
    select
        id as customer_id,
        first_name,
        last_name
    from raw.jaffle_shop.customers
);

개발자는 테이블을 어떻게 생성(Create)하고 갱신(Update/Replace)할지 신경 쓸 필요가 없다. 그저 비즈니스 로직(Select)에만 집중하면 된다. 이것이 dbt가 가져온 생산성 혁신의 시작이다.

마치며

오늘은 ETL에서 ELT로의 전환과 dbt의 철학에 대해 간략히 살펴보았다. dbt는 단순한 SQL 실행기가 아니라, SQL을 코드로 관리하게 해주는 프레임워크다.

This post is licensed under CC BY 4.0 by the author.