APC 技術ブログ

株式会社エーピーコミュニケーションズの技術ブログです。

株式会社 エーピーコミュニケーションズの技術ブログです。

Databricks Asset Bundlesを使い、CI/CDをやってみよう:前準備編

はじめに

こんにちは、GDAI事業部Lakehouse部の陳(チェン)です。

久しぶりにブログを執筆します。今回のテーマはDatabricks上、推奨されるCI/CDのプロセス・アセットバンドル(Asset Bundles)についてです。

アセットバンドル(Asset Bundles)の使い方などの紹介は一編のブログのみで紹介しきれないため、不定期に更新するシリーズにしたいと思います。第一編の本ブログでは、環境分けの考え方を交えながら、アセットバンドルの基本の使い方を紹介します。

もくじ

まえおき

Databricks上で、CI/CDプロセスを円滑に行うためのアセットバンドルの内容ですので、想定読者はDatabricksの基本的な使い方に概念を持っている方です。そのため、本文の中に出てくる、ワークスペースカタログパイプラインメダリオンアーキテクチャや、ローカルマシンにてDatabricksCLIの使用に関わる話題については説明をいたしません。必要に応じて、それぞれのテーマに合わせてDatabricksの公式ドキュメントを参照していただければと思います。

また、本ブログシリーズに示されている作業の行う場所はDatabricks Free Editionを利用して構成されたものです。そのため、様々な箇所において、設定に関わるものはシンプルになっていることにご注意ください。

アセットバンドルについて

使い方に入る前に、アセットバンドルの構成について軽く紹介します。

アセットバンドルはDatabricks上で作成されたアーティファクトをまとめて、他の環境への移行を行うツールです。バンドルされる(束ねられた)アーティファクトの中身として、コード類(Python Notebookなど)、リソース(WorkflowやPipeline)、実行環境(Databricks Workspaceやコンピュート構成など)が含まれています。また、それぞれの環境に応じて、Notebookの保存先、コンピュート構成などの変更も設定ファイル(databricks.ymlなど)にて設定することもできます。

アセットバンドルのフォルダー構成は色々ありますが、私が考えている一番シンプルな構成は下記の通りです。現業で使用する際にして、より複雑な構成が必要になると思いますが、ユーザー側にてニーズに応じてドキュメントを参照して構成を追加してください。

project_name/ 
├── resources/   # Databricks Asset Bundleのための追加YAMLファイルを配置 
├── src/   # ソースファイル(コード類のもの) 
└── databricks.yml  # 主要なYAMLファイル、必ず「databricks.yml」と名付ける

   

  • Databricks YAMLファイル:アセットバンドル全体を制御する設定ファイルです。移行先の設定や、移行対象のアーティファクトなどを記述するファイルになります。このファイルは、該当プロジェクトの配下の第一階層に置き、名前を「databricks.yml」にするのが決まりです。また、Databricks CLIを使用してひな形を作成しておいたのち、必要に応じて編集します。

  • srcフォルダー:移行対象のアーティファクトの元になるコード(Notebook)を配置する場所です。

  • resourceフォルダー:必要に応じて、追加のyamlファイルを置くフォルダーになります。本ブログでは使用しません。

開発のための環境分け

システム開発する際、どうしても環境を分けたいですね。様々な考え方があると思いますが、今回は(1)カタログと(2)ワークスペースの分け方についてご紹介します。

カタログによる環境を分ける

ワークスペースで区切りまではないが、「開発/ Development」・「ステージング/ Stagining」・「本番/ Production」を分けたいときに、カタログによる環境を分けるのは良いかと思います。また、それぞれの開発者が作業する場所が必要だと思い、前述のカタログの他、好みで「Sandbox」というカタログを追加してもいいかもしれません。

全体イメージとしてはFig1の通り、一つのワークスペースの中にそれぞれの環境に対応するカタログを作成します。

  • Sandboxカタログ:開発者は自由に使うようなカタログになり、配下にスキーマやVolumesも自由に使えるようにしています。

  • 開発/ Developmentカタログ:開発カタログであり、Sandboxでてきたものを開発の成果物としてこちらに集約し、少量なデータを使用して単体テスト的な作業を行う場所です。

  • ステージング/ Staginingカタログ:ステージングカタログのため、開発カタログでテスト済みしたものを、こちらの環境に移動します。中程度のデータ量を用いてテストを行い、結果確認及びパフォーマンス見積りを行う場所です。

  • 本番/ Productionカタログ:名前の通り、本番運用のためのカタログです。ステージングカタログにてテストやパフォーマンスチェックをできたシステムをこちらに移行し、本格な運用に移行します。

全ての環境は一つのワークスペースにあり、お互いの結果を参照しやすいと思います。 コンパクトの開発に適用するかと思います。

Fig1:カタログによる環境を分けるイメージ

ワークスペースによる環境分け

カタログの環境分けと似ていて、ただし、カタログをワークスペースに置換することになります(Fig2)。この場合、開発者のSandboxと開発環境は同一ワークスペースにまとめた構成も多いかと思います。

イメージとしてはFig2の通り、それぞれの環境に対応するワークスペースを作成します。また、バージョンの管理をはじめ、環境間の移動や成果物の管理はGitHubなどのツールと連携することも多いです。

  • Sandbox+開発/ Developmentワークスペース:開発者は自由に使うようなカタログや開発されたものを一箇所に集約し、開発環境として、単体テストを行う。この場合、このワークスペース配置されたやVolumesも自由に使えるようにしています。

  • ステージング/ Staginingワークスペース:開発ワークスペースでテスト済みした成果物を、こちらの環境に移動、中程度のデータでテストして、結果の確認及びパフォーマンスの見積りを行う場所になります。

  • 本番/ Productionワークスペース:名前の通り、本番で運用するものはこちらに移行します。

Fig2:ワークスペースによる環境を分けるイメージ

アセットバンドルを用いてアーティファクト移動

アセットバンドルを利用してアーティファクトの移動のイメージはFig3の感じになります。権限を持ったユーザが指示を出し、纏められた(バンドルされた)成果物の一式を環境間の移動を行います。この移動は、直接環境間の移動でも可能ですし、バージョン管理ツールGitHubなどを介して成果物の受け渡しも可能になっています。それぞれの開発チームのニーズに応じて選択してください。成果物のまとめ方やアセットバンドルを構成する仕方については各セクションにて紹介します。

Fig3:アセットバンドルを利用したアーティファクトの環境間移動のイメージ

アーティファクトーパイプライン

データ

シンプルなパイプライン構築のため、ニューヨークシティタクシーデータセットのうち、Yellow Taxiのデータ(parquet形式)を使用しています。今回は手動で、使用するデータを一旦自分のLocalにDownloadしてから、Databricks上のVolumesに配置します。本篇の場合、テストに該当するため、シンプルにDatabricks上でのデータ配置のイメージは下記の通りです(Fig1のCatalog Sandboxに該当)。この例では、Yellow TaxiのparquetファイルはVolumesの配下に該当のフォルダーに置いてあります。フォルダーの階層関係(上位から下位まで)は「catalog_Sandbox」、「Schema_for_raw_data」、「Volumes」、「raw_datafolder」になります。また、それぞれの階層やファイルのアクセス権限の設定に関しては、管理権限を持つユーザが必要に応じてそれぞれのユーザへ「can read」などの権限付与する必要があります。こちらも必要に応じて調整してください。

catalog_Sandbox  #テスト用カタログ/
└── Schema_for_raw_data  #raw dataのためのスキーマ/
    └── Volumes            # Volumesを作成/
        └── raw_datafolder  # 実際にraw dataを配置するフォルダー/
            ├── yellow taxi parquet file 1
            ├── yellow taxi parquet file 2
            └── ...

パイプラインの構成

サンプルアーティファクトのパイプラインはFig4の通りです。 

Fig4:パイプラインのフロー

上記のパイプラインの構成はメダリオンアーキテクチャを採用し、ブロンズ、シルバー、ゴールド、それぞれのレイアー(概念)に対応するテーブルを作成します。また、ブロンズレイアーにおけるデータ取り込みのプロセスは、事前にVolumesに配置しておいたファイルを使用します(現業では、クラウドストレージなどからの取り込みが多いかと思いますが、それぞれのユースケースに応じて改変することも可能)。それぞれの処理に関する説明は以下の通りです。

  • ブロンズレイアー(ストリーミングテーブル):事前にVolumesに配置されたparquetファイルを取り込みます。また、${INGEST_PATH}は環境によって取り込みパスが変更になるため、パイプライン構築の最初の段階でパラメータ化をしておきました。アセットバンドルにおけるパラメーターの改変などに関する説明は今後の楽しみにしておきましょう。
CREATE OR REFRESH STREAMING TABLE 100_STREAM_BRONZE_YELLOW_TAXI
  TBLPROPERTIES ('delta.feature.timestampNtz' = 'supported') AS
SELECT
  *
FROM
  STREAM read_files("${INGEST_PATH}", format => "parquet");

   

  • シルバーレイアー(ストリーミングテーブル):ブロンズテーブルに取り込まれたレコードのクレンジングを行います。このサンプルにおいては、乗車人数(passenger_count)のNULL値を取り除く、及び日付けの表示(時まで)を変換する作業を行います。
CREATE OR REFRESH STREAMING TABLE 200_STREAM_SILVER_YELLOW_TAXI AS
SELECT
  VendorID,
  DATE_FORMAT(
    DATE_TRUNC('MINUTE', CAST(tpep_pickup_datetime AS TIMESTAMP)), 'yyyy-MM-dd HH'
  ) AS tpep_pickup_datehour,
  DATE_FORMAT(
    DATE_TRUNC('MINUTE', CAST(tpep_dropoff_datetime AS TIMESTAMP)), 'yyyy-MM-dd HH'
  ) AS tpep_dropoff_datehour,
  passenger_count,
  trip_distance,
  payment_type,
  fare_amount,
  extra,
  mta_tax,
  tip_amount,
  total_amount
FROM
  STREAM(100_STREAM_BRONZE_YELLOW_TAXI)
WHERE
  passenger_count IS NOT NULL

   

  • ゴールドレイアー(マテリアライズドビュー):結果を集計するレイアーです。シンプルに、乗車時刻、乗車人数、支払い方法を用いてグループ分けて、それぞれの状況に応じて、平均的な運賃などの結果を算出します。また、ゴールドテーブルの宣言の仕方が変わりましたため、ご注意ください。これまでは「CREATE OR REFRESH LIVE TABLE <TABLE_NAME>」として宣言してきましたが、よりゴールドレイアーの実態に沿うような宣言の仕方ができるようになりました!(※これまでのLIVE TABLEはそのまま使えます。)
CREATE OR REFRESH MATERIALIZED VIEW 300_STREAM_GOLD_YELLOW_TAXI AS
SELECT
  tpep_pickup_datehour,
  passenger_count,
  payment_type,
  ROUND(mean(trip_distance), 2) AS mean_distance,
  ROUND(mean(fare_amount), 2) AS mean_fare_amount,
  ROUND(mean(total_amount), 2) AS mean_totalamount
FROM
  200_STREAM_SILVER_YELLOW_TAXI
GROUP BY
  tpep_pickup_datehour,
  passenger_count,
  payment_type

     

パイプラインのYAMLファイル

アセットバンドルの構成には、YAML形式のパイプライン構成が必要になります。このYAMLファイルに関して、DatabricksのUI操作によって生成できます。生成されたYAMLファイルの中身を必要に応じて調整したうえ、アセットバンドルに組み込みます。Databricks上に作成されたすべてのアーティファクト(パイプライン、ワークフローなど)のYAMLファイルを同じ手順で生成ができます。色々と試してみてください。

本ブログで提示されたサンプルアーティファクト(Pipeline)のYAMLファイルを生成する手順はFig5の通りになります。まず、Pipelineの構成画面に移動します。次に、構成画面にあるケバブメニューをクリックしたのち、「View Settings YAML」という選択肢が現れ、「View Settings YAML」をクリックします。

Fig5:パイプラインのYAMLファイルを生成する手順

「View Settings YAML」をクリックした後に、PipelineのYAMLファイルはFig6のように表示されます。このYAMLファイルをコピーして、Notebookのパスなどを必要に応じて修正したうえ、アセットバンドルに組み込みます。

Fig6:Databricks上に自動生成されたYAMLファイル

ローカルマシンでアセットバンドルを構成・実行

これからは、ローカルマシンでアセットバンドルを構成した後、Sandboxカタログにデプロイします。

ローカルマシンでアセットバンドルを構成

まず、ローカルマシンにて、下記の構成のフォルダを作成します。202508_testの配下に、アセットバンドルの設定・移行したいアーティファクトなどを置きます。

202508_test      # Projectの名前 
├── resources/      # Databricks Asset Bundleのための追加YAMLファイルを配置
├── src/            # ソースファイル(コード類のもの)
│   ├── 100_stream_bronze_ingestion.sql
│   ├── 200_stream_silver_filtering.sql
│   └── 300_materialized_gold_aggregation.sql
└── databricks.yml  # 主要なYAMLファイル、必ず「databricks.yml」と名付ける

  

実際のローカルでのフォルダ構成はFig7を参照してください。また、srcフォルダーの配下に、パイプラインを構成するためのsqlスクリプトが配置されています。

Fig7:ローカルにてのアセットバンドルファイル

アセットバンドル全体を制御するdatabricks.ymlの中身は下記の通りです。本ブログでは、シンプルな構成を採用しております。必要に応じて、構成を変更や拡張していただければと思います。

bundle:
  name: 202508_APC_techblog  #本アセットバンドルの名前

resources:   #アーティファクトの情報を設定
  pipelines:
    APC_techblog_bundle_202508:   #Piplelineのプロジェクト名、リモート起動する際に必要
      name: 20250806_TEST
      configuration:
        INGEST_PATH: /Volumes/000_sandbox/000_ingestion_data/000_trip_data/  #Databricks上でのデータソースのパス
      libraries:   #Notebookのパスは、「databricks.ymlファイルから見る相対パス」を記述
        - notebook:
            path: ./src/100_stream_bronze_ingestion.sql
        - notebook:
            path: ./src/200_stream_silver_filtering.sql
        - notebook:
            path: ./src/300_materialized_gold_aggregation.sql
      schema: ${var.dev_schema}
      continuous: false
      development: true
      photon: true
      channel: PREVIEW
      catalog: 000_sandbox
      serverless: true

targets:   #移行先の設定、必要に応じて、幾つかの環境を設定が可能。本篇では、devのみの設定になる。
  dev:
    mode: development
    default: true
    workspace:
      host: https://dbc-xxxxxxxx-xxxx.cloud.databricks.com  #ターゲットワークスペースのURL(一部マスキング済み)を記入
      root_path: /Workspace/Users/yyyy@zzzz.co.jp/20250815_test #アセットバンドルの保存先@DatabricksPlatform(一部マスキング済み)、必要に応じて設定する

variables:   #ユーザー設定の変数、必要に応じて設定する
  def_schema:
    description: target schema for pipeline
    default: ingest_data

  dev_schema:
    description: target schema for dev
    default: 900_${var.def_schema}

Notebookのパスや変数設定の確認が終わりましたら、ローカルマシンでDatabricksCLIを使用し、アーティファクトをdev環境にデプロイします。

アセットバンドルを実行

ローカルのプロンプトフロントにて、アセットバンドルのプロジェクトフォルダ(本ブログの場合、202508_test)配下に移動しますした後に、下記の手順をコマンドを実行します(Fig8に参照)。

コマンドラインにて、DatabricksCLIを使用して、アセットバンドルをワークスペースへディプロイします。今の場合、「databricks bundle deploy -t dev -p 202508_DABtest」を入力します。オプションの「-t dev」と「-p 202508_DABtest」はそれぞれ、ターゲット環境=devとワークスペースへのアクセスのための設定は202508_DABtestと名付けられたDatabricks profileに参照する、という意味です。(※Databricksワークスペースへの接続のためのDatabricks Profileの設定については説明いたしません。)

無事にデプロイできた後に、ワークスペース上に、アーティファクトがWorkspakceに配置されたのと、パイプラインは作成されたのが確認できます。

Fig8:アセットバンドルの実行及びDatabricks上のデプロイ結果

デプロイされたパイプラインを起動

リモートでデプロイされたパイプラインを起動したい場合、「databricks bundle run -t dev APC_techblog_bundle_202508 -p 202508_DABtest」をコマンドプロンプトに入力します。そこから、パイプラインが起動されることを確認できます。

Fig9:(a)ローカルにてパイプラインの起動、及び(b)Databricks上のパイプライン実行状況

おわりに

長いブログを最後まで読んでいただき、ありがとうございました。

本シリーズはまだまだ続きますが、第一編として、アセットバンドルの基本のキに関する概念や使い方の感覚を少しでも伝わると幸いです。

最後に

私たちはDatabricksを用いたデータ分析基盤の導入から内製化支援まで幅広く支援をしております。もしご興味がある方は、お問い合わせ頂ければ幸いです。

また、一緒に働いていただける仲間も募集中です! APCommunicationsにご興味がある方の連絡をお待ちしております。