google-cloud-bigqueryのlist_jobsがUnknownJobを返してきてハマってしまった

小さいハマりなのですが、具体的にはGCP BigQueryのPythonクライアントライブラリである、google-cloud-bigqueryのlist_jobsが手元とDataflowのサーバ側で挙動が違う状態に遭遇しました。

デバッグログを見ながらエラーのポイントは判明しました。list_jobsの関数の返り値の型が手元だと LoadJobs とか QueryJob とかなるところを、 google.cloud.bigquery.job.UnknownJob という型が返ってきていました。

結論

UnknownJobが返ってきた時は権限を疑ってみる。特に all_users=True のオプションを使う時は bigquery.jobs.listAll の権限が必要なので、処理を実行しているアカウントに権限があることを確認するようにします。

調査

UnknownJobという名前であることと、APIは複数の値を返してきていたので何かが返ってきている。つまりは権限では無いと考えていました。 ただ、試行錯誤していても、どうしても原因がわからずにコードの変更の理由を確認してみました。

ここのconfigが無い時みたいだけど、それってどんな時だろう。でも手元で再現できないからDataflowのジョブ実行してログと格闘。でもわからない。

https://github.com/googleapis/google-cloud-python/blob/bigquery-1.23.1/bigquery/google/cloud/bigquery/client.py#L1131-L1140

そして、どんな理由でUnknownJobという型が追加されたのか調べてみるという思考に今更いきあたりました。

github.com

We had a meeting with the BQ backend team this morning, and this was the conclusion / compromise. My opinion is the backend should return a 403 on permissions errors rather than redacting, but that's still an ongoing conversation.

あれ?これ権限の話?

そして、更に先を読んでみると。完全に権限の話でした。

Yes, it happens when calling list_jobs with all_users=True while not having the bigquery.jobs.listAll permission.

github.com

そして権限つけて実行したら無事に動きました。

教訓

ググったり、試行錯誤も大切だが、早めにソースやリポジトリをちゃんと読む。(数時間無駄にしてしまった・・)

参考URL

cloud.google.com

https://github.com/googleapis/google-cloud-python/blob/bigquery-1.23.1/bigquery/google/cloud/bigquery/client.py#L1232

https://cloud.google.com/bigquery/docs/reference/rest/v2/jobs/list