気づいたら実装されてました。マニュアルはこちら。あとで翻訳見直しておきます。
OAuthに関してはこちらが非常にわかりやすいです。
注意
2024/9/19 タイトルと用語を修正しました。
アカウントレベルの認証とワークスペースレベルの認証がありますが、ここではワークスペースレベルの認証を行なっていきます。
ステップ 1: OAuthコード検証子(verifier)とコードチャレンジのペアを生成する
Databricksノートブックなどで以下を実行します。
import uuid, hashlib, base64
# UUIDを生成
uuid1 = uuid.uuid4()
# UUIDを文字列に変換
uuid_str1 = str(uuid1).upper()
# コード検証子を作成
code_verifier = uuid_str1 + "-" + uuid_str1
# コード検証子に基づいてコードチャレンジを作成
code_challenge = base64.urlsafe_b64encode(hashlib.sha256(code_verifier.encode()).digest()).decode('utf-8')
# コードチャレンジからすべてのパディングを削除
code_challenge = code_challenge.replace('=', '')
# コード検証子とコードチャレンジを表示
# OAuth U2M認証のためにアクセストークンを手動で生成する際にこれらを使用します。
print(f"code_verifier: {code_verifier}")
print(f"code_challenge: {code_challenge}")
code_verifier: 30EFEF16-E24B-4CBC-9B69-140B6CEA3F1C-30EFEF16-E24B-4CBC-9B69-140B6CEA3F1C
code_challenge: 2pdbCyvBZQ9QbaNkYnuL3G5kgXuZRwlByfevYZYvJ1I
ステップ 2: 認可コードを生成する
ステップ1で作成したコードチャレンジを用いて、認可コードを生成します。以下では改行を挿入していますが、実際には改行は含みません。
-
<redirect-url>
をローカル コンピューターへのリダイレクト URL に置き換えます (例: http://localhost:8020 )。 -
<state>
を認可コードの整合性を検証するために使用できるプレーンテキスト文字列に置き換えます。以下ではtakaakiyayoi_oauth_test
としていますが、これはローカルマシンにリダイレクトされた際に、自分が入力したものであることを目検するために使用します。
https://<Databricksワークスペースのホスト名>/oidc/v1/authorize?
client_id=databricks-cli&
redirect_uri=http://localhost:8020&
response_type=code&state=takaakiyayoi_oauth_test&
code_challenge=2pdbCyvBZQ9QbaNkYnuL3G5kgXuZRwlByfevYZYvJ1I&
code_challenge_method=S256&
scope=all-apis+offline_access
ワークスペースにログインしていない際には、ログイン画面が表示されるのでログインします。すると、上で指定した<redirect-url>
にリダイレクトされます。ローカルで8020ポートでアプリケーションが動作していなければ、画面には何も表示されませんが、URLに認証コードが含まれています。以下では、灰色に塗りつぶしている箇所となります。これをコピーしておきます。また、state
の値が上で指定したものと同一であることを確認してください。
ステップ 3: 認可コードを使用して OAuth アクセス権を生成する
code_verifier
には、ステップ1で準備したコード検証子(verifier)を指定します。
curl --request POST \
https://<ワークスペースのホスト名>/oidc/v1/token \
--data "client_id=databricks-cli" \
--data "grant_type=authorization_code" \
--data "scope=all-apis offline_access" \
--data "redirect_uri=http://localhost:8020" \
--data "code_verifier=30EFEF16-E24B-4CBC-9B69-140B6CEA3F1C-30EFEF16-E24B-4CBC-9B69-140B6CEA3F1C" \
--data "code=<ステップ2で取得した認可コード>"
{"access_token":"<アクセストークン>","refresh_token":"doau....a4","scope":"all-apis offline_access","token_type":"Bearer","expires_in":3600}
ステップ 4: Databricks REST API を呼び出す
export OAUTH_TOKEN=<アクセストークン>
curl --request GET --header "Authorization: Bearer $OAUTH_TOKEN" \
"https://<Databricksワークスペースのホスト名>/api/2.0/clusters/list" | jq
{
"clusters": [
{
"cluster_id": "0828-090225-7qa5vjeb",
"creator_user_name": "takaaki.yayoi@databricks.com",
"spark_context_id": 4666640280775891000,
"driver_healthy": true,
"cluster_name": "Taka Yayoi's Personal Compute Cluster",
"spark_version": "15.4.x-cpu-ml-scala2.12",
"spark_conf": {
"spark.databricks.cluster.profile": "singleNode",
"spark.master": "local[*, 4]"
},
"aws_attributes": {
"first_on_demand": 0,
"availability": "ON_DEMAND",
"zone_id": "auto",
"spot_bid_price_percent": 100
},
"node_type_id": "i3.xlarge",
"driver_node_type_id": "i3.xlarge",
"custom_tags": {
"ResourceClass": "SingleNode"
},
"autotermination_minutes": 120,
"enable_elastic_disk": true,
"disk_spec": {},
"cluster_source": "UI",
"single_user_name": "takaaki.yayoi@databricks.com",
"policy_id": "DB62AD9785000228",
"enable_local_disk_encryption": false,
"instance_source": {
"node_type_id": "i3.xlarge"
},
"driver_instance_source": {
"node_type_id": "i3.xlarge"
},
"data_security_mode": "SINGLE_USER",
"runtime_engine": "STANDARD",
"effective_spark_version": "15.4.x-cpu-ml-scala2.12",
"state": "TERMINATED",
"state_message": "Termination requested by takaaki.yayoi+db@databricks.com",
"start_time": 1724835745533,
"terminated_time": 1725519639958,
"last_state_loss_time": 1725519034415,
"last_activity_time": 1725519080453,
"last_restarted_time": 1725519034460,
"num_workers": 0,
"default_tags": {
"Vendor": "Databricks",
"Creator": "takaaki.yayoi@databricks.com",
"ClusterName": "Taka Yayoi's Personal Compute Cluster",
"ClusterId": "0828-090225-7qa5vjeb"
},
"termination_reason": {
"code": "USER_REQUEST",
"type": "SUCCESS",
"parameters": {
"username": "takaaki.yayoi@databricks.com"
}
},
"init_scripts_safe_mode": false
}
]
}