[MLOps 기초] DVC(Data Version Control) - PART3. Data Pipelines


PART2 데이터 접근에 이어서…

데이터 파이프라인 (Data Pipelines)

이전 포스팅까지는 데이터 버전관리와 접근에 대해서 알아봤다.
지금부터는 DVC를 통해 데이터 파이프라인을 만드는 방법에 대해서 살펴본다.

생각해보면 굳이 파이프라인 기능까지 쓰지 않아도
데이터 버전관리와 접근 기능만으로도 DVC는 사용할만한 가치가 있어 보인다.
그래도 파이프라인까지 연결해서 사용해야 MLOps라는 개념에 좀 더 부합하도록 DVC를 사용하는 것이 아닐까 싶다.

파이프라인은…

  1. 코드 실행 및 데이터 생성 등 일련의 분석 과정에 대한 자동화,
  2. 어떤 데이터와 명령어를 사용할지 yaml 파일로 지정하여 결과(모델)를 빠르게 재생성하여 버전관리와 공유를 쉽게 관리하는 재현성,
  3. ML을 위한 CI/CD 와 같은 장점이 있다

데이터 파이프라인 : 최종 결과(모델 또는 데이터)를 생성하기 위한 일련의 데이터 처리 과정들

DVC로 생성하는 파이프라인과 데이터 또한 앞서 PART1/2에서 살펴본 것과 같이 버전관리 및 접근을 할 수 있다.


  • Pipeline stages

파이프라인을 구성하는 스테이지(stage)를 생성하기 위한 명령어는 dvc run 이다. 스테이지는 실행할 코드와 입력/출력용 데이터를 연결한 형태이다. (python script를 데이터와 연결하여 어떤 결과를 만들어내는 걸 하나의 스테이지라고 생각하면 된다)

튜토리얼 예시용 스크립트 다운로드

dvc run -n [스테이지 네이밍] \ # dvc.yaml 파일에 하나의 섹션 이름이 됨
        -p [파라미터] \ # params.yaml(by default) 파일로 접근
        -d [경로] \ # 스테이지에 실행될 파일의 경로 (스크립트 또는 데이터) 
        -o [파일 또는 폴더명] \ # 스테이지 출력값이 저장될 파일 또는 폴더
        [스테이지에서 처리할 실행 명령어]
# run 명령어를 실행하면 dvc.yaml에 스테이지가 생성되고 옵션들이 저장된다

# 튜토리얼 예시 - 데이터 준비
dvc run -n prepare -f \
        -p prepare.seed,prepare.split \
        -d src/prepare.py -d data/data.xml \
        -O data/prepared \
        python src/prepare.py data/data.xml
-------------------[output]------------------
Running stage 'prepare' with command:                                 
	python src/prepare.py data/data.xml
Creating 'dvc.yaml'                                                                                                                                                                                     
Adding stage 'prepare' in 'dvc.yaml'
Generating lock file 'dvc.lock'
Updating lock file 'dvc.lock'

To track the changes with git, run:

	git add data/.gitignore dvc.yaml dvc.lock
---------------------------------------------

tree
------------[output]----------
.
├── data
│   ├── data.xml
│   ├── data.xml.dvc
│   └── prepared
│       ├── test.tsv
│       └── train.tsv
├── dvc.lock
├── dvc.yaml
├── params.yaml
└── src
    ├── evaluate.py
    ├── featurization.py
    ├── prepare.py
    ├── requirements.txt
    └── train.py
-----------------------------

여기까지 실행하고 추가로 dvc add를 실행할 필요는 없다.
dvc run을 실행하면 자동으로 변경사항이 추가된다. 따라서 (만약 필요하다면) dvc push를 통해 저장소에서 저장하기만 하면 된다.


  • Dependency graphs (DAGs)

dvc run을 여러 번 실행하면 여러 개의 스테이지가 생성된다.

# 튜토리얼 예시 - 특징 추출
dvc run -n featurize -f \
        -p featurize.max_features,featurize.ngrams \
        -d src/featurization.py -d data/prepared \
        -O data/features \
        python src/featurization.py data/prepared data/features
-------------------------[output]-----------------------------
Running stage 'featurize' with command:                               
	python src/featurization.py data/prepared data/features
The input data frame data/prepared/train.tsv size is (20017, 3)
The output matrix data/features/train.pkl size is (20017, 502) and data type is float64
The input data frame data/prepared/test.tsv size is (4983, 3)
The output matrix data/features/test.pkl size is (4983, 502) and data type is float64
Adding stage 'featurize' in 'dvc.yaml'                                                                                                                                                                  
Updating lock file 'dvc.lock'

To track the changes with git, run:

	git add dvc.lock data/.gitignore dvc.yaml
--------------------------------------------------------------

# 튜토리얼 예시 - 모델 학습
dvc run -n train \
        -p train.seed,train.n_estimators \
        -d src/train.py -d data/features \
        -o model.pkl \
        python src/train.py data/features model.pkl
--------------------[output]---------------------
Running stage 'train' with command:                                   
	python src/train.py data/features model.pkl
Input matrix size (20017, 502)
X matrix size (20017, 500)
Y matrix size (20017,)
Adding stage 'train' in 'dvc.yaml'                                    
Updating lock file 'dvc.lock'

To track the changes with git, run:

	git add .gitignore dvc.lock dvc.yaml
-------------------------------------------------

파이프라인을 구성하는 각 스테이지를 생성하기 위해서는 소스코드와 데이터(학습용/실험용 데이터 및 모델) 저장 구조를 미리 잘 잡아놔야 하겠다. 물론 수정될 때마다 변경된 사항을 다시 push 하면 되지만(그럴려고 버전관리가 있는거라고 말할 수 있겠지만, 엄연히 ‘버전’이라는게 존재한다는 것이 가정이므로), 예시에서 보듯이 데이터 준비 -> 전처리 -> 모델 학습 과정에서 새로 생성되는 artifacts들이 많기 때문에 구조가 체계적이지 않으면 복잡해질 것이다.

파이프라인을 다 구성했으면, 드디어 Git에 변경사항을 저장하기 좋은 시점이 된 것이다.
파이프라인을 구성하는 파일들을(.gitignore dvc.lock 그리고 dvc.yaml ) commit 한다.

  • Reproduce

dvc repo 명령어는 생성한 파이프라인을 전부 또는 일부에 대해 재실행할 수 있다.

dvc repro dvc.yaml # dvc.yaml은 파이프라인 정보를 담은 파일

# dvc repro 는 dvc.yaml 파일에서 실행할 단계를, dvc.lock 파일에서 해쉬 정보를 취하여 파이프라인을 재실행한다.


  • Visualize

dvc dag 명령어는 생성한 파이프라인의 구조를 터미널에서 그래프로 보기 위한 명령어

dvc dag

요약해보면, DVC는 dvc.yaml파일과 dvc run, dvc repro 명령어를 통해 파이프라인을 생성하고 재실행하는 기능을 제공한다.
실제 프로젝트에서 이 기능을 유용하게 사용하려면 dvc.yaml 이 어떻게 구성돼야하는지를 기준으로 소스코드 구조와 데이터 저장 구조를 미리 설계해야 할 것이다.


다음으로 PART4 실험 (Experiments) 에 대해 알아보자.