こんにちは、データ基盤の開発・運用をしている谷口です。
本記事では、BigQueryで秘密情報を守るためのリソースである、ポリシータグをご紹介します。ポリシータグの概要から採用理由、仕様を考慮したデータ連携の仕組みや運用における注意点まで幅広くお伝えします。
ポリシータグとは
ポリシータグは、BigQueryでカラム単位のアクセス制御が可能なリソースです。BigQueryに保存されている秘密情報を、機密性高く管理するために利用します。
これまで、BigQueryではテーブルやデータセット単位でのアクセス制御はできましたが、カラム単位でのアクセス制御はできませんでした。1つのテーブルに複数の秘密情報が管理されている場合には、テーブル単位のアクセス制御だと、必要以上の秘密情報を参照できてしまいます。
例えば会員情報を扱う場合、1つのテーブルに名前や性別、年齢など様々な秘密情報が管理されます。それらは下図のように機密性も様々です。それらの秘密情報を掛け合わせることで個人の特定に繋がってしまいます。カラム単位のアクセス制御を導入することにより、個人を匿名化し、個人情報の漏洩リスクを防ぐことに役立ちます。
引用:BigQuery でポリシータグを使用する際のベスト プラクティス | Google Cloud
BigQueryのスキーマ情報からどのスキーマが秘密情報で、どのようなポリシータグが付与されているか、下図のように把握できます。
A column can have only one policy tag. A table can have at most 1,000 unique policy tags.
引用:制限事項 - BigQuery の列レベルのセキュリティの概要 | Google Cloud
そして、ポリシータグはTerraformでも管理できます。ここではその流れを紹介します。
まず、親となる分類「taxonomy」リソースを作ります。
resource "google_data_catalog_taxonomy" "taxonomy" {
project = var.project_private
provider = google-beta
region = "us"
display_name = "policytag-taxonomy-${var.env}"
description = "A collection of policy tags"
activated_policy_types = ["FINE_GRAINED_ACCESS_CONTROL"]
}
次に、子のリソースとなる「ポリシータグ」を作ります。名前や年齢など、秘密情報の分類に基づいたポリシータグを作ります。
resource "google_data_catalog_policy_tag" "child_policy_name" {
provider = google-beta
taxonomy = google_data_catalog_taxonomy.taxonomy.id
display_name = "name"
description = "name"
parent_policy_tag = google_data_catalog_policy_tag.parent_policy_secret.id
}
作成したポリシータグは、GCPコンソール上で確認できます。例えば、親子関係でリソースを作った場合、下図のような表示になります。弊社では、親リソースとして「secret」を用意し、子リソースとして分類ごとのポリシータグを作成しています。
そして、コードとして取り扱うので、Git上で「誰にどの権限を付与しているのか」を管理できます。
resource "google_data_catalog_policy_tag_iam_binding" "child_policy_name_viewer" {
provider = google-beta
policy_tag = google_data_catalog_policy_tag.child_policy_name.name
role = "roles/DataCatalog.categoryFineGrainedReader"
members = var.zozo_datapool_private_policy_tag_name_viewer
}
なお、ポリシータグを付与したカラムは、権限がないと参照できなくなります。参照するには「Fine-Grained Reader role」権限が必要です。権限がない状態で参照しようとすると、以下のエラーが発生します。これは、オーナー権限を持っている管理者であっても同様です。
Access Denied: Policy tag projects/<project_id>/locations/<locations>/taxonomies/<taxonomies-id>/policyTags/<policyTags-id>: User does not have permission to access policy tag "<policytag-taxonomy-name> : tell" attached to table(s) <project>.<dataset>.<table>
引用:きめ細かい読み取りのロール - BigQuery の列レベルのセキュリティによるアクセス制限 | Google Cloud
前述の通り、ポリシータグはカラム単位のアクセス制御により個人情報を匿名化します。最初は「データベース × テーブル」でポリシータグを作ろうと考えましたが、分類あたりのポリシータグの上限が100と決まっているため、それは実現できませんでした。「テーブル × カラム」で秘密情報を保護する思想にはなっていないようです。
Maximum number of policy tags per taxonomy 100
引用:割り当てと上限 | Data Catalog のドキュメント | Google Cloud
ポリシータグを採用した理由
BigQueryにおける秘密情報への参照を制限する方法は、ポリシータグ以外にも、承認済みビューなどの承認済みリソースを使う方法も考えられます。
承認済みビューを使うと、元テーブルへの参照権限がなくても承認済みビューからは参照できるようになります。秘密情報のカラムを除いた承認済みビューを用意することで、秘密情報ではないレコードのみを参照できます。
なぜ承認済みビューではなく、ポリシータグを採用したのか、その判断理由を順に説明します。
続きはこちら