本文介绍了如何在 BigQuery 中创建授权视图。
您可以通过以下方式在 BigQuery 中创建授权视图:
- 使用 Cloud Console。
- 使用
bq
命令行工具的bq mk
命令。 - 调用
tables.insert
API 方法。 - 提交
CREATE VIEW
数据定义语言 (DDL) 语句。 - 使用客户端库。
概览
在 BigQuery 中,为视图授予数据集访问权限也称为创建授权视图。已获授权的视图可让您与特定用户和群组共享查询结果,而无需为其授予底层源数据的访问权限。您还可以使用视图的 SQL 查询来限制用户可查询的列(字段)。
在其他数据集中创建已获授权的视图时,源数据数据集和已获授权的视图数据集必须位于同一区域位置。
有关如何创建授权视图的教程,请参创建授权视图。
所需权限
如需创建或更新授权视图,您需要拥有包含该视图的数据集的权限,以及提供对该视图访问权限的数据集的权限。
包含该视图的数据集
在 BigQuery 中,视图作为表资源处理,因此创建视图所需的权限与创建表相同。如需创建视图,您必须至少具备 bigquery.tables.create
权限。以下预定义的 IAM 角色包含 bigquery.tables.create
权限:
bigquery.dataEditor
bigquery.dataOwner
bigquery.admin
此外,如果用户具有 bigquery.datasets.create
权限,则当该用户创建数据集时,系统会为其授予该数据集的 bigquery.dataOwner
访问权限。具备 bigquery.dataOwner
访问权限的用户可以在数据集中创建视图。
如需详细了解 BigQuery 中的 IAM 角色和权限,请参阅预定义的角色和权限。
提供对该视图访问权限的数据集
如需更新数据集属性,您必须至少具备 bigquery.datasets.update
和 bigquery.datasets.get
权限。以下预定义 IAM 角色具有 bigquery.datasets.update
和 bigquery.datasets.get
权限:
bigquery.dataOwner
bigquery.admin
此外,如果用户具有 bigquery.datasets.create
权限,则当该用户创建数据集时,系统会为其授予该数据集的 bigquery.dataOwner
访问权限。借助 bigquery.dataOwner
访问权限,用户可以更新其创建的数据集的属性。
如需详细了解 BigQuery 中的 IAM 角色和权限,请参阅访问权限控制。
授予视图数据集访问权限
如需为视图授予数据集访问权限,请执行以下操作:
控制台
在探索器面板中,展开您的项目并选择数据集。
在详细信息面板中,点击共享数据集。
在数据集权限面板中,选择已获授权的视图标签页。
在共享已获授权的视图部分中:
- 对于选择项目,验证项目名称。如果视图位于不同的项目中,请务必选择该项目。
- 对于选择数据集,请选择包含该视图的数据集。
- 对于选择视图,选择您正在授权的视图。
点击添加,然后点击完成。
bq
使用
show
命令将现有数据集信息(包括访问权限控制设置)写入 JSON 文件。如果数据集不属于默认项目,请按以下格式将相应项目 ID 添加到数据集名称中:project_id:dataset
。bq show \ --format=prettyjson \ project_id:dataset > path_to_file
其中:
- project_id 是您的项目 ID。
- dataset 是您的数据集的名称。
- path_to_file 是本地机器上 JSON 文件的路径。
示例:
输入以下命令可将
mydataset
的访问权限控制写入 JSON 文件。mydataset
属于默认项目。bq show --format=prettyjson mydataset > /tmp/mydataset.json
输入以下命令可将
mydataset
的访问权限控制写入 JSON 文件。mydataset
属于myotherproject
。bq show --format=prettyjson \ myotherproject:mydataset > /tmp/mydataset.json
将授权视图添加到 JSON 文件的“access”部分。
例如,数据集 JSON 文件的“access”部分可能如下所示:
{ "access": [ { "role": "READER", "specialGroup": "projectReaders" }, { "role": "WRITER", "specialGroup": "projectWriters" }, { "role": "OWNER", "specialGroup": "projectOwners" } { "role": "READER", "specialGroup": "allAuthenticatedUsers" } { "role": "READER", "domain": "[DOMAIN_NAME]" } { "role": "WRITER", "userByEmail": "[USER_EMAIL]" } { "role": "READER", "groupByEmail": "[GROUP_EMAIL]" }, { "view":{ "datasetId": "[DATASET_NAME]", "projectId": "[PROJECT_NAME]", "tableId": "[VIEW_NAME]" } } ], }
修改完成后,运行
update
命令,并用--source
标志包括该 JSON 文件。如果数据集不属于默认项目,请按以下格式将相应项目 ID 添加到数据集名称中:project_id:dataset
。bq update \ --source path_to_file \ project_id:dataset
其中:
- path_to_file 是本地机器上 JSON 文件的路径。
- project_id 是您的项目 ID。
- dataset 是您的数据集的名称。
示例:
输入以下命令可更新
mydataset
的访问权限控制。mydataset
属于默认项目。bq update --source /tmp/mydataset.json mydataset
输入以下命令可更新
mydataset
的访问权限控制。mydataset
属于myotherproject
。bq update --source /tmp/mydataset.json myotherproject:mydataset
如需验证您的访问权限控制发生了变化,请再次输入
show
命令,但不要将信息写入文件。bq show --format=prettyjson [DATASET]
或
bq show --format=prettyjson [PROJECT_ID]:[DATASET]
API
调用 datasets.patch
并使用 access
属性更新访问权限控制设置。如需了解详情,请参阅数据集。
由于 datasets.update
方法会替换整个数据集资源,因此建议使用 datasets.patch
方法来更新访问权限控制设置。
Go
在尝试此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 Go 设置说明进行操作。如需了解详情,请参阅 BigQuery Go API 参考文档。
Java
试用此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 Java 设置说明进行操作。 如需了解详情,请参阅 BigQuery Java API 参考文档。
Python
在尝试此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 Python 设置说明进行操作。如需了解详情,请参阅 BigQuery Python API 参考文档。
使用视图强制执行行级访问权限
视图可用于限制对特定列(字段)的访问。如果您想要限制用户或群组只能访问表中的个别行,不需要为他们分别创建单独的视图,而可以使用 SESSION_USER()
函数返回当前用户的电子邮件地址。
为了向不同的用户显示不同的行,请在表中添加另一个字段,并在其中添加您要允许查看该行的用户,然后再创建一个使用 SESSION_USER()
函数的视图。在以下示例中,用户名存储在 allowed_viewer
字段中:
SELECT COLUMN_1, COLUMN_2 FROM `dataset.view` WHERE allowed_viewer = SESSION_USER()
这种方法的局限性在于,您一次只能为一名用户授予访问权限。如要解决这项限制,您可以将 allowed_viewer
设为重复字段。此方法可让您为每行提供一个用户列表。但是,即便您使用了重复字段,将用户名存储在表中后,您仍然需要手动跟踪拥有各行访问权限的个别用户。
因此,更好的做法是在 allowed_viewer
字段中填入群组名称,然后创建一个单独的表来将群组映射到用户。将群组映射到用户的表采用存储群组名称和用户名的架构,例如 {group:string, user_name:string}
。这种方法可让您通过包含相关数据的表单独管理用户和群组信息。
如果映射表的名称为 private.access_control
,则用于创建授权视图的 SQL 查询将如下所示:
SELECT c.customer, c.id FROM `private.customers` c INNER JOIN ( SELECT group FROM `private.access_control` WHERE SESSION_USER() = user_name) g ON c.allowed_group = g.group
后续步骤
- 有关如何创建授权视图的教程,请参创建授权视图。
- 要了解如何创建视图,请参阅创建视图。
- 如需了解如何列出视图,请参阅列出视图。
- 如需了解如何获取视图元数据,请参阅获取有关视图的信息。
- 如需了解如何更新视图,请参阅更新视图。
- 如需详细了解如何管理视图,请参阅管理视图。