dbt でデータウェアハウスとして BigQuery を使う際、ローカル開発においては OAuth 方式を使うことが推奨されている。
そしてその場合はgcloud auth application-default login
コマンドを実行する必要がある。
確かにこのコマンドを実行すると BigQuery との接続が上手くいきローカルで開発できるようになる。
しかしこのコマンドは、具体的には何をしているのか。gcloud auth login
とは何が違うのか。何も分かっていなかったので調べてみた。
この記事の内容は、以下の環境で動作確認している。
- npm パッケージ
- @google-cloud/storage@7.14.0
- dbt
- dbt-core@1.9.1
- dbt-bigquery@1.9.0
Application Default Credentials
gcloud auth application-default login
について理解するためにはまず Application Default Credentials (以下 ADC)という概念について理解したほうがよい。
ADC とは、 Google Cloud のクライアントライブラリが認証情報を取得するための仕組み。
クライアントライブラリは Google Cloud の API を叩くためのツールだが、当然ながら認証情報がなければ API を叩くことはできない。
例えば以下はproject-x-123456
プロジェクトにある Cloud Storage のバケット一覧を表示するコードだが、クライアントライブラリである@google-cloud/storage
に認証情報を渡さなければ動作しない。
// bucket.js const { Storage } = require("@google-cloud/storage"); const storage = new Storage({ projectId: "project-x-123456" }); async function listBuckets() { try { const [buckets] = await storage.getBuckets(); buckets.forEach((bucket) => console.log(bucket.name)); } catch (err) { console.error("Error:", err); } } listBuckets();
例えば以下のようにStorage
インスタンスを作る際に認証情報を渡すと動作する(この例ではkeyFilename
にサービスアカウントキーのパスを渡している)。
const storage = new Storage({ projectId: "project-x-123456", keyFilename: "project-x-sa-key.json", });
だが ADC の仕組みを利用すれば、コードのなかに認証情報に関する情報を書くことなく、クライアントライブラリに認証情報を渡すことができる。
ADC は特定の順序で認証情報を検索し、最初に見つかった認証情報をクライアントライブラリに提供する。
最後まで認証情報が見つからなかった場合は、以下のようにエラーになる。
$ node bucket.js
Error: Error: Could not load the default credentials. Browse to https://cloud.google.com/docs/authentication/getting-started for more information.
GOOGLE_APPLICATION_CREDENTIALS
ADC はまず最初に、環境変数GOOGLE_APPLICATION_CREDENTIALS
に入っている値を使おうとする。
この環境変数に認証情報の JSON ファイルの場所を設定しておくことで、そのファイルの内容がクライアントライブラリに渡される。
「認証情報の JSON ファイル」として使えるものはいくつかあるが、今回はサービスアカウントキーを使う。
$ export GOOGLE_APPLICATION_CREDENTIALS=project-x-sa-key.json
この状態でbucket.js
を実行するとproject-x-123456
にあるバケットbucket-a
が表示される。
$ node bucket.js bucket-a
GOOGLE_APPLICATION_CREDENTIALS
を unset すると、bucket.js
は再び失敗するようになる。
$ unset GOOGLE_APPLICATION_CREDENTIALS $ echo ${GOOGLE_APPLICATION_CREDENTIALS-none} none $ node bucket.js Error: Error: Could not load the default credentials. Browse to https://cloud.google.com/docs/authentication/getting-started for more information.
~/.config/gcloud/application_default_credentials.json
GOOGLE_APPLICATION_CREDENTIALS
に値が入っていなかった場合 ADC は~/.config/gcloud/application_default_credentials.json
を使おうとする。
そして~/.config/gcloud/application_default_credentials.json
を用意するためのコマンドが、gcloud auth application-default login
なのである。
gcloud auth application-default login
を実行するとウェブブラウザでページが開くので、その内容に沿って操作を行うと、選択したアカウントに基づき以下の形式の~/.config/gcloud/application_default_credentials.json
が作られる。
{ "account": "", "client_id": "***.apps.googleusercontent.com", "client_secret": "***", "refresh_token": "***", "type": "authorized_user", "universe_domain": "googleapis.com" }
そうするとbucket.js
が再び成功するようになる。
$ node bucket.js bucket-a
gcloud auth application-default revoke
を実行すると~/.config/gcloud/application_default_credentials.json
は消える。
このように、gcloud auth application-default login
はあくまでも ADC 用の認証情報を用意するためのコマンドであり、gcloud
コマンドやbq
コマンドを実行するための認証を行うgcloud auth login
とは別のものである。
gcloud auth login
については以下の記事で詳しく書いた。
dbt での挙動
dbt と BigQuery を接続させるために必要な認証情報も ADC を使って渡すことができる。
冒頭に貼ったドキュメントに書かれているようにgcloud auth application-default login
を使ってもよいが、ここまで書いてきたようにGOOGLE_APPLICATION_CREDENTIALS
が設定されている場合はそちらが優先されるので注意する。