Blog
Pachydermによるデータ管理とパイプライン
AI Labの谷口です。
11月に入って急に寒くなってきましたね。
以前のSeldonに関する記事でもあるようにAI LabではResearch Engineeringの観点から様々なミドルウェアの調査などをやっています。
この記事ではデータのバージョン管理+パイプラインを提供するミドルウェアのPachydermを紹介します。
データを用いた研究をやっていく中で重要な要素の一つに「データの再現性」というものがあります。機械学習はその大部分のアルゴリズムがモデルを構築するデータに依存しますが、モデルを構築した際に利用したデータがわからなくなってしまった場合、そのモデルをもう一度再現することは非常に困難となります。また、特徴エンジニアリングなどをやっていく過程で一つのデータに対して複数の処理を様々なパターンで行うことがほとんどです。Pachydermはこのような問題に対してgitライクなデータのバージョン管理とデータ処理のパイプラインで解決することが出来ます。
Pachydermとは
PachydermはKubernetes上で動作するデータのバージョン管理+パイプラインを提供するミドルウェアになります。ソフトウェアは、OSSで公開されているものとは別にEnterpriseバージョンも提供されているようです。
Enterpriseバージョンでは、
- フルUI (各種可視化と設定画面など)
- アクセスコントロール
- 管理者
などの機能が追加されているようです。
下の画像がEnterpriseバージョンで提供されるUIの画面です。
用語説明
Repository
データソースの置き場になります。Exapmlesなどを見ていると例えば学習データとテストデータなどがあっても別々のRepositoryにしているので、データの種類というよりは用途別でRepositoryを作成するのが良さそうです。
Repositoryには後述するBranchとCommitが含まれています。この3つの名前を見るとおそらく大半の人は「git」を連想されると思いますが、Pachydermのバージョン管理は「git for data」なものをイメージするとわかりやすいです。
Commit
変更があった場合に記憶される単位で、gitのcommitとほぼ同義です。
各CommitにはParent Commitというどのコミットから処理されて出てきたものかを示すものが記憶されています。
Branch
Commitの流れの単位で、Parent Commitは同じBranchの前のCommit IDが記憶されています。
基本的にこれもgitと同じなのですが、mergeという概念がないため少し異なると言えそうです。
Pipeline
Pipelineはデータに対するあらゆる処理の一つの単位で、データは必ずPipelineを経由して、次のRepositoryに格納されます。また、Pipelineは1つのRepository/Branchを入力として利用できるだけではなく、複数のRepository/Branchを入力にすることも可能です。更にはデータが入力になるのではなく、cronをトリガーにして実行することも出来ます。
機械学習での利用例
※こちらの例は公式が用意しているものを解説しているだけです
全体像
ここで、
- 円柱で表現されているものがRepository
- 四角で表現されているものがPipeline
になります。
traning
が学習データを格納しているRepositoryで、attributes
が予測したいデータを格納するRepositoryになります。今回は特徴抽出などは行わず直接モデルを作っているので、model
というPipelineからmodel
というRepositoryを作っています。(Pipelineから作成されるRepositoryの名前はPipelineの名前と同じになります)生成したモデルが格納されているmodel
と予測したいデータが入っているattributes
の二つを入力にして、inference
のPipelineが予測値を計算します。計算された予測値はinference
というRepositoryに格納されていきます。
実際のコード
Repositoryへのデータ格納や取り出しなどは基本的にCLIから行うことができます。ここではPipelineのコードに焦点を当てて、解説していきます。Pipelineの処理はjson形式で記述されており、下記のようになります。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 |
{ "pipeline": { "name": "model" }, "transform": { "image": "pachyderm/iris-train:python-svm", "cmd": [ "python3", "/code/pytrain.py", "/pfs/training/", "/pfs/out/" ] }, "parallelism_spec": { "constant": "1" }, "input": { "atom": { "repo": "training", "glob": "/" } } } |
"input"
で入力されるRepositoryを指定しています。"transform"
ではdockerのimageをpullしてきて、そこで入力に対して実行したい処理を記述しておきます。このとき、/pfs/training/
や/pfs/out/
というものが出てきますが、
/pfs/{repository_name}/
で入力されるrepositoryのデータをここにマウントされる/pfs/out/
に出力されるデータはPipelineの結果として生成されるRepositoryの/
として格納される
のような動作をします。このようにVolumeをマウントすることで、Pipeline間でもデータのやり取りを実現しています。
また、入力を複数取るinference
のPipelineでは"input"
の部分に"cross"
というキーを利用しています。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 |
"input": { "cross": [ { "atom": { "repo": "attributes", "glob": "/*" } }, { "atom": { "repo": "model", "glob": "/" } } ] } |
詳しいPipelineの書き方は公式のこちらにまとまっています。
まとめ
研究や機械学習のモデリング、データ分析のイテレーション(PDCA的な意味)を加速させるために様々なミドルウェアなどを調査しているのですが、今回はPachydermについて紹介しました。公式の解説に留まりましたが、基本的な使い方は非常に簡単で、RepositoryとPipelineの設計もシンプルでわかりやすい設計になっているため、今後採用できる場所で使ってみようと思っています。
Author