dbt를 사용한 단위 테스트 SQL

Dec 16 2022
수년 동안 데이터 과학 및 엔지니어링 작업을 한 후, 데이터 품질은 거의 모든 프로젝트에 나타나 비즈니스 성과를 떨어뜨리는 매달린 유령입니다. SQL은 사실상 데이터의 언어입니다.

수년 동안 데이터 과학 및 엔지니어링 작업을 한 후, 데이터 품질은 거의 모든 프로젝트에 나타나 비즈니스 성과를 떨어뜨리는 매달린 유령입니다.

SQL은 사실상 데이터의 언어입니다. 데이터 품질을 향상시키는 한 가지 방법은 단위 테스트 및 데이터 테스트로 SQL 코드베이스를 향상시키는 것입니다. 이 기사는 주로 Mrs Gao의 게시물 에서 영감을 받았습니다 .

이 기사에서는 dbt를 사용한 SQL 단위 테스트의 기본 논리를 간단한 데이터 세트로 설명합니다.

기본 아이디어

SQL에서 단위 테스트를 수행하는 기본 아이디어는 Python 코드에서 단위 테스트를 수행하는 것과 정확히 동일합니다.

  1. 제어 가능한 입력 모의 D
  2. 테스트 가능한 모듈/함수/알고리즘이 있습니다 . 이를 A라고 합니다.
  3. D를 입력으로 사용하여 예상 결과를 계산하고 O_should를 얻습니다.
  4. 예상 결과(O_should)와 A의 실제 출력(O_is)을 비교합니다.

때로는 정확히 일치할 필요가 없습니다. 즉, 소수점 이하 2자리까지만 일치해야 합니다.

위의 아이디어를 설명하기 위해 순진한 예를 만들어 봅시다. 다음과 같은 dbt 프로젝트 폴더 구조가 필요합니다.

-- dbt_project.yml

-- data/
------ iris.csv
------ selected_iris_expected.csv

-- models/
------ iris/
---------- selected_iris.sql
---------- schema.yml

# example: dbt_project.yml

# take things under data/ as seeds
data-paths: ["data"]

# configure seed, all going into unittesting schema
seeds:
    schema: unittesting

-- selected_iris.sql
{{ config(
        materialized='table',
        schema='unittesting',
        tags=['iris']
    )
}}

-- count the number of special iris id (above average in all aspects)
-- not a very meaningful logic, just for exemplare purpose
SELECT
distinct count(distinct id)
FROM "public"."iris";
where sepallengthcm > 5.9 and sepalwidthcm > 3.1 and petallengthcm > 3.8 and petalwidthcm > 1.2
-- selected_iris_expected.csv
count
150

# schema.yml 

version: 2

# table model selected_iris should be equal to iris
models:
  - name: selected_iris

    tests:
      - dbt_utils.equality:
          compare_model: ref('selected_iris_expected')
          tags: ['unit_testing']

1단계: 테스트 데이터를 데이터베이스에 로드

# here we use
# iris.csv will be loaded into unittesting.iris table
# selected_iris_expected.csv will be loaded into unittesting.selected_iris_expected table
dbt seed
# build selected_iris model into unittesting.selected_iris
dbt run

주장 a==b

2단계: 비교

# here we use
# all tests within folder model/iris/ with be executed
# of course, we can restrict to only unittesting using tags
dbt test --model iris

기술

단위 테스트 SQL은 간단해 보이죠? 그러나 실제로는 더 복잡할 수 있습니다.

  • 프로젝트에 따라 테스트를 분리하고 구성하려면 보다 정교한 폴더 구조(중첩된 하위 폴더 사용)가 필요할 수 있습니다.
  • 현재 환경 dev/prod에 따라 단위 테스트를 켜거나 꺼야 할 수도 있습니다.
  • 조롱하기 어려운 큰 입력 테이블이 있을 수 있습니다.
  • 예상 결과를 미리 계산하기 어려운 복잡한 모델이 있을 수 있습니다(모델을 테스트할 수 없음).
  • 부동 소수점 정밀도 등으로 인해 예상 결과가 실제 출력과 100% 일치하지 않을 수 있습니다(거의 동일하더라도).
  • 또는 흔하지 않은 이 프로젝트에 단순히 시간 예산이 없을 수 있습니다. 사람들은 2022년에 SQL을 단위 테스트하지 않습니다. SQL 문은 작성된 후에 올바른 것으로 간주됩니다.

팁: SQL 문 모듈화

위에 나열된 모든 문제에도 불구하고 Python과 같은 다른 일반적인 프로그래밍 언어뿐만 아니라 SQL의 경우 단위 테스트에 도움이 되는 한 가지가 있습니다.

그것이 바로 모듈화입니다. 좋은 모듈화된 모델/함수/알고리즘은 SQL에 대해서도 테스트 가능성과 가독성을 보장합니다.

sql 및 dbt를 사용하여 이를 실현하는 방법에는 여러 가지가 있습니다.

  • dbt 매크로(https://docs.getdbt.com/docs/build/jinja-macros)
  • 진술 (https://learnsql.com/blog/what-is-with-clause-sql/)

결론

SQL은 데이터의 기본 언어입니다. 이 기사에서는 dbt로 SQL 단위 테스트를 수행하는 방법을 시연했습니다.

마찬가지로 데이터 통합 ​​테스트 또는 rasgoQ L을 사용하여 Python과 같은 더 강력한 언어에 SQL 생성을 위임하는 것과 같은 기타 트릭을 수행할 수도 있습니다.