0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

Databricks の UniForm が有効なテーブルを Snowflake にて Secure Data Sharing する方法

Last updated at Posted at 2025-03-17

概要

Databricks の UniForm が有効になっているテーブルを、Snowflake の Apache Iceberg テーブル(外部カタログを使用するテーブル)として登録し、別の Snowflake アカウントに共有する手順を紹介します。

本記事は下記記事の一部です。

手順

Databricks 上でテーブルを作成

まず、データベースとテーブルを作成し、データを挿入します。

%sql
CREATE CATALOG IF NOT EXISTS sf_iceberg;
%sql
CREATE TABLE sf_iceberg.default.nation_iceberg (
  n_nationkey  integer
  ,n_name       string
  ,n_regionkey  integer 
  ,n_comment    string
)
TBLPROPERTIES(
  'delta.columnMapping.mode' = 'name',
  'delta.enableIcebergCompatV2' = 'true',
  'delta.universalFormat.enabledFormats' = 'iceberg'
);
%sql
INSERT OVERWRITE sf_iceberg.default.nation_iceberg
SELECT
  n_nationkey
  ,n_name
  ,n_regionkey 
  ,n_comment
FROM
  samples.tpch.nation

image.png

テーブルのデータを取得できることを確認します。

%sql
SELECT * FROM sf_iceberg.default.nation_iceberg;

image.png

Snowflake で利用する Databricks のサービスプリンシパルを作成

Databricks SDK を使用して、Snowflake で利用するサービスプリンシパルを作成します。

from databricks.sdk import WorkspaceClient

client = WorkspaceClient()
service_account = client.service_principals.create(
    display_name="snowflake-share-account",
)
print("Service account created with ID:", service_account.id)

image.png

次に、このサービスプリンシパルに対してデータベースオブジェクトに対する権限を付与します。

application_id = service_account.application_id
spark.sql(f"""
GRANT USE CATALOG ON CATALOG sf_iceberg
    TO `{application_id}`;
""").display()
spark.sql(f"""
GRANT SELECT ON SCHEMA sf_iceberg.default
    TO `{application_id}`;
""").display()

続いて、サービスプリンシパルの OAuth シークレットを取得します。まず、Databricks Workspace の右上にあるアカウントメニューから 設定 を選択します。

image.png

IDとアクセス タブを選択し、サービスプリンシパル管理 を選択します。

image.png

先ほど作成したサービスプリンシパルを選択します。

image.png

シークレット タブを開き、シークレットを生成 をクリックします。

image.png

存続期間を任意の日数に設定し、生成 を選択します。

image.png

表示されたシークレットの値を控えます。

image.png

共有元 Snowflake にテーブル作成

まず、カタログ統合を作成します。

CREATE OR REPLACE CATALOG INTEGRATION {catalog_integration_name}
  CATALOG_SOURCE = ICEBERG_REST
  TABLE_FORMAT = ICEBERG
  CATALOG_NAMESPACE = 'default'
  REST_CONFIG = (
    CATALOG_URI = '{workspace_url}/api/2.1/unity-catalog/iceberg',
    WAREHOUSE = '{catalog_name}'
  )
  REST_AUTHENTICATION = (
    TYPE = OAUTH
    OAUTH_TOKEN_URI = '{workspace_url}/oidc/v1/token'
    OAUTH_CLIENT_ID = '{client_id}'
    OAUTH_CLIENT_SECRET = '{secret}'
    OAUTH_ALLOWED_SCOPES = ('all-apis', 'sql')
  )
  ENABLED = TRUE;
プレースホルダー 説明
{catalog_integration_name} カタログ統合の名前を指定します。統合設定を一意に識別するための名称です。
{workspace_url} Databricks ワークスペースの URL を指定します。
{catalog_name} Databricks のカタログ名を指定します。
{client_id} OAuth 認証のクライアント ID を指定します。
{secret} OAuth 認証のシークレットを指定します。

image.png

次に、Snowflake で外部 Volume を作成します。

CREATE OR REPLACE EXTERNAL VOLUME {external_volume_name}
STORAGE_LOCATIONS = (
    (
        NAME = '{name}'
        STORAGE_PROVIDER = 'AZURE'
        STORAGE_BASE_URL = 'azure://{azure_storage_account_name}.blob.core.windows.net/{azure_storage_container_name}'
        AZURE_TENANT_ID = '{tenant_id}'
    )
);
プレースホルダー 説明
{external_volume_name} Snowflake の外部 Volume 名を指定します。
{name} Snowflake の外部 Volume の名前を指定します。
{azure_storage_account_name} Azure ストレージアカウントの名前を指定します。
{azure_storage_container_name} Azure ストレージアカウントのコンテナ名を指定します。
{tenant_id} Azure のテナント ID を指定します。

image.png

続いて、下記クエリで AZURE_CONSENT_URL の値を取得します。

DESC EXTERNAL VOLUME azure_sf_share_exvol;
SELECT 
    PARSE_JSON($4):AZURE_MULTI_TENANT_APP_NAME::string AS AZURE_MULTI_TENANT_APP_NAME,
    PARSE_JSON($4):AZURE_CONSENT_URL::string AS AZURE_CONSENT_URL
FROM TABLE(RESULT_SCAN(LAST_QUERY_ID()))
WHERE $2 = 'STORAGE_LOCATION_1';

image.png

Azure にログインしているブラウザで AZURE_CONSENT_URL にアクセスし、表示された画面で 承諾 を選択します。

image.png

すると、このサービスプリンシパルが Azure テナントに追加されます。そのため、必要に応じてストレージに対する権限(例:ストレージ BLOB データ共同作成者)を付与します。

image.png

外部 Volume へのアクセスが問題なく行えるか、下記クエリで確認します。

SELECT SYSTEM$VERIFY_EXTERNAL_VOLUME('azure_sf_share_exvol');

image.png

次にデータベースを作成します。

CREATE DATABASE IF NOT EXISTS databricks_uf_share_db;
USE databricks_uf_share_db;

image.png

Databricks の UniForm が有効なテーブルを、Snowflake 上で Iceberg テーブルとして作成します。

CREATE OR REPLACE ICEBERG TABLE nation_iceberg_from_db_by_uf
    EXTERNAL_VOLUME = 'azure_sf_share_exvol'
    CATALOG = 'databricks_uniform_catalog_integration'
    CATALOG_TABLE_NAME = 'nation_iceberg'
    CATALOG_NAMESPACE = 'default'
    AUTO_REFRESH = TRUE;

image.png

テーブルからデータが正しく取得できることを確認します。

SELECT * FROM nation_iceberg_from_db_by_uf;

image.png

データ共有先アカウントを作成

はじめに、ORGADMIN ロールに切り替えます。

-- ORGADMIN にカレントロールを変更
USE ROLE ORGADMIN;
SELECT CURRENT_ROLE();

image.png

データ共有先の Snowflake アカウントを新規で作成します。

-- データ共有先の Snowflake アカウントを作成
-- ToDo EMAIL と REEGION をかえる必要あり
CREATE ACCOUNT manabian_comsumer_01_account
   ADMIN_NAME = 'comsumer_admin'
   ADMIN_PASSWORD = 'MySecurePassword2025!'
   EMAIL = 'admin@example.com'
   MUST_CHANGE_PASSWORD = FALSE
   EDITION = ENTERPRISE
   REGION = 'AZURE_EASTUS2';

image.png

次に、データ共有先の新アカウントの URL を取得します。

-- アカウントの URL を取得
SHOW ACCOUNTS LIKE 'manabian_comsumer_01_account';

image.png

上記で作成したアカウントにログインします。

image.png

ワークスペースで下記クエリを実行し、Data Sharing Account Identifier の値を取得します。必要に応じてクラスタを作成してください。

SELECT
    CURRENT_ORGANIZATION_NAME() || '.' || CURRENT_ACCOUNT_NAME() AS "Data Sharing Account Identifier";

image.png

共有元 Snowflake アカウントにて共有の作成と権限付与

共有を作成します。

CREATE OR REPLACE SHARE db_by_uf_share;

image.png

続いて、共有に対する権限を付与します。

GRANT USAGE ON DATABASE databricks_uf_share_db TO SHARE db_by_uf_share;
GRANT USAGE ON SCHEMA databricks_uf_share_db.public TO SHARE db_by_uf_share;
GRANT SELECT ON ICEBERG TABLE nation_iceberg_from_db_by_uf TO SHARE db_by_uf_share;

image.png

先ほど取得した Data Sharing Account Identifier を使用して、共有先アカウントがこの共有を利用できるよう設定します。

-- 共有先アカウントで取得した Data Sharing Account Identifier の値をセット
SET data_sharing_account_identifier = 'LAMPVRN.MANABIAN_COMSUMER_01_ACCOUNT';
ALTER SHARE db_by_uf_share
    ADD ACCOUNTS = $data_sharing_account_identifier;

共有先 Snowflake アカウントにて共有に基づきデータベースを作成

共有先の Snowflake アカウントで、ACCOUNTADMIN ロールに切り替えます。

USE ROLE ACCOUNTADMIN;
SELECT CURRENT_ROLE();

次に、NAMEDB_BY_UF_SHAREowner_account_and_name を確認します。

SHOW SHARES;
SELECT
    CONCAT($3, '.', $4) AS owner_account_and_name
    ,$3 AS owner_account
    ,$4 AS name
FROM TABLE(RESULT_SCAN(LAST_QUERY_ID()));

image.png

取得した owner_account_and_name をもとに、共有されたテーブルを含むデータベースを作成します。

CREATE OR REPLACE DATABASE SHARE_BY_DB_UF_DB
    FROM SHARE LAMPVRN.OFA41652.DB_DELTA_UF_SHARE;
USE DATABASE SHARE_BY_DB_UF_DB;

image.png

テーブルにアクセスできるか確認します。

SHOW TABLES IN DATABASE SHARE_BY_DB_UF_DB;
SELECT * FROM NATION_ICEBERG_FROM_DB_BY_UF;

image.png

Databricks にて DELETE 実行後の 共有先 Snowflake の反映確認

Databricks 側でテーブルのデータを削除してみます。

%sql
DELETE FROM sf_iceberg.default.nation_iceberg WHERE n_nationkey > 3;

image.png

共有先の Snowflake でデータが反映されているか確認します。

SELECT count(*) FROM NATION_ICEBERG_FROM_DB_BY_UF;

image.png

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?