本文档介绍如何在 BigQuery 中创建和使用聚簇表。如需大致了解 BigQuery 中的聚簇表支持,请参阅聚簇表简介。
限制
BigQuery 中的聚簇表存在以下限制:
- 仅支持使用标准 SQL 查询聚簇表以及将查询结果写入聚簇表。
聚簇列必须是以下任一类型的顶级非重复列:
DATE
BOOL
GEOGRAPHY
INT64
NUMERIC
STRING
TIMESTAMP
如需详细了解数据类型,请参阅标准 SQL 数据类型。
您最多可以指定四个聚簇列。
使用
STRING
类型的列进行聚簇时,BigQuery 仅使用前 1024 个字符为数据划分聚簇。列中的值本身可以超过 1024 个字符。
创建聚簇表
您可以通过以下方式创建聚簇表:
- 使用查询结果:
- 使用 DDL
CREATE TABLE AS SELECT
语句创建。 - 通过运行创建聚簇目标表的查询创建。
- 使用 DDL
- 使用 DDL
CREATE TABLE
语句并附加一个包含clustering_column_list
的CLUSTER BY
子句。 - 使用
bq
命令行工具的bq mk
命令手动创建。 - 调用
tables.insert
API 方法以编程方式创建。 - 在加载数据时。
- 使用客户端库。
表命名
在 BigQuery 中创建表时,数据集中每个表的名称都必须具有唯一性。表名称可:
- 包含最多 1024 个字符。
- 包含类别 L(字母)、M(符号)、N(数字)、Pc(连接符,包括下划线)、Pd(短划线)、Zs(空格)中的 Unicode 字符。如需了解详情,请参阅常规类别。
例如,以下都是有效的表名称:table-01
、ग्राहक
、00_お客様
、étudiant
。
所需权限
如需创建表,您至少必须具有以下权限:
bigquery.tables.create
:创建表的权限bigquery.tables.updateData
:使用加载作业、查询作业或复制作业向表中写入数据bigquery.jobs.create
:用于运行向表中写入数据的查询作业、加载作业或复制作业
如需访问向表中写入的数据,可能还需要其他权限,例如 bigquery.tables.getData
。
以下预定义的 IAM 角色同时包含 bigquery.tables.create
和 bigquery.tables.updateData
权限:
bigquery.dataEditor
bigquery.dataOwner
bigquery.admin
以下预定义的 IAM 角色包含 bigquery.jobs.create
权限:
bigquery.user
bigquery.jobUser
bigquery.admin
此外,如果用户具有 bigquery.datasets.create
权限,则当该用户创建数据集时,系统会为其授予该数据集的 bigquery.dataOwner
访问权限。借助 bigquery.dataOwner
访问权限,用户可以在数据集内创建和更新表。
如需详细了解 BigQuery 中的 IAM 角色和权限,请参阅预定义的角色和权限。
遵循架构定义创建空聚簇表
在 BigQuery 中创建表时,您可以指定聚簇列。创建表后,您可以修改聚簇列;如需了解详情,请参阅修改聚簇规范。
聚簇列必须是以下任一简单数据类型的顶级非重复列:
DATE
BOOLEAN
GEOGRAPHY
INTEGER
NUMERIC
STRING
TIMESTAMP
您最多可以指定四个聚簇列。指定多个列时,对列进行指定的顺序决定了数据的排序方式。例如,如果表按 a、b 和 c 列进行聚簇,则数据按相同顺序排序:首先按 a 列排序,然后按 b 列排序,最后按 c 列排序。最佳做法是将最常过滤或聚合的列放在首位。
聚簇列的顺序也会影响查询性能和价格。如需详细了解查询聚簇表的最佳做法,请参阅查询聚簇表。
要创建遵循某个架构定义的空聚簇表,请执行以下操作:
控制台
在 Google Cloud Console 中,转到 BigQuery 页面。
在导航面板的资源部分中,展开您的项目并选择数据集。
在窗口右侧的详细信息面板中,点击创建表。
在创建表页面的来源部分,为基于以下数据创建表选择空表。
在目标位置下:
- 对于数据集名称,选择相应的数据集,然后在表名称字段中输入要创建的表的名称。
- 确认表类型设置为原生表。
在架构下,输入架构定义。
通过以下方式,手动输入架构信息:
启用以文本形式修改,并以 JSON 数组格式输入表架构。
使用添加字段手动输入架构。
(可选)在分区和聚簇设置下,选择按字段分区 (Partition by field),然后选择
DATE
或TIMESTAMP
列。如果架构不包含DATE
或TIMESTAMP
列,则此选项不可用。要创建提取时间分区表,请选择按提取时间分区。
(可选)在分区过滤条件中,点击需要分区过滤条件复选框,以要求用户添加
WHERE
子句来指定要查询的分区。要求分区过滤条件可以减少费用并提高性能。如需了解详情,请参阅查询分区表。对于聚簇顺序,请输入一至四个以英文逗号分隔的列名称。
(可选)点击高级选项,然后在加密部分点击客户管理的密钥以使用 Cloud Key Management Service 密钥。如果保留 Google 管理的密钥设置,BigQuery 将对静态数据进行加密。
点击创建表。
bq
使用带有以下标志的 bq mk
命令:
--table
(或-t
快捷方式)。--schema
。您能够以内嵌方式提供表的架构定义或使用 JSON 架构文件。--clustering_fields
。您最多可以指定四个聚簇列。
可选参数包括 --expiration
、--description
、--time_partitioning_type
、--time_partitioning_field
、--time_partitioning_expiration
、--destination_kms_key
和 --label
。
如果您要在非默认项目中创建表,请按以下格式将相应项目 ID 添加到数据集中:project_id:dataset
。
本文未演示 --destination_kms_key
。要了解如何使用 --destination_kms_key
,请参阅客户管理的加密密钥。
输入以下命令可创建包括架构定义的空聚簇表:
bq mk \ --table \ --expiration INTEGER1 \ --schema SCHEMA \ --time_partitioning_type=DAY \ --time_partitioning_field PARTITION_COLUMN \ --clustering_fields CLUSTER_COLUMNS \ --time_partitioning_expiration INTEGER2 \ --description "DESCRIPTION" \ --label KEY:VALUE,KEY:VALUE \ PROJECT_ID:DATASET.TABLE
替换以下内容:
INTEGER1
:表的默认生命周期(以秒为单位)。最小值为 3600 秒(一小时)。到期时间以当前世界协调时间 (UTC) 加上这个整数值为准。如果您在创建时间分区表时设置了该表的到期时间,则系统会忽略数据集的默认表到期时间设置。如果设置了此值,系统将在指定的时间后删除表和所有分区。SCHEMA
:采用COLUMN:DATA_TYPE,COLUMN:DATA_TYPE
格式的内嵌架构定义,或者是本地机器上 JSON 架构文件的路径。PARTITION_COLUMN
:用于创建分区表的TIMESTAMP
或DATE
列的名称。如果您创建分区表,则无需指定--time_partitioning_type=DAY
标志。CLUSTER_COLUMNS
:英文逗号分隔的聚簇列(最多 4 个)列表。该列表不能包含任何空格。INTEGER2
:表分区的默认生命周期(以秒为单位)。它没有最小值。过期时间以分区的日期加上这个整数值为准。分区过期时间虽然与表的过期时间无关,但它不会替换表的过期时间。如果设置的分区过期时间超过了表的过期时间,则以表过期时间为准。DESCRIPTION
:加英文引号的表说明。KEY:VALUE
:代表标签的键值对。您可以使用英文逗号分隔列表输入多个标签。PROJECT_ID
:您的项目 ID。DATASET
:项目中的数据集。TABLE
:您要创建的分区表的名称。
在命令行中指定架构时,您不能添加 RECORD
(STRUCT
) 类型和列说明,也不能指定列的模式。所有模式均默认为 NULLABLE
。如需添加说明、模式和 RECORD
类型,请改为提供 JSON 架构文件。
示例:
输入以下命令,在默认项目的 mydataset
中创建一个名为 myclusteredtable
的聚簇表。该表是一个分区表(按 TIMESTAMP
列分区)。分区的过期时间设置为 86400 秒(1 天),表的过期时间设置为 2592000(1 个月/30 天),说明设置为 This is my clustered table
,标签设置为 organization:development
。该命令使用 -t
快捷方式代替 --table
。
该架构以内嵌方式指定为:timestamp:timestamp,customer_id:string,transaction_amount:float
。指定的聚簇字段 customer_id
用于聚簇分区。
bq mk -t \
--expiration 2592000 \
--schema 'timestamp:timestamp,customer_id:string,transaction_amount:float' \
--time_partitioning_field timestamp \
--clustering_fields customer_id \
--time_partitioning_expiration 86400 \
--description "This is my clustered table" \
--label org:dev \
mydataset.myclusteredtable
输入以下命令,在 myotherproject
(非默认项目)中创建一个名为 myclusteredtable
的聚簇表。该表是一个提取时间分区表。分区过期时间设为 259200 秒(3天),说明设为 This is my
partitioned table
,标签设为 organization:development
。该命令使用 -t
快捷方式代替 --table
。此命令没有指定表过期时间。如果相关数据集有默认的表过期时间,则系统会应用该过期时间。如果数据集没有默认的表到期时间,则该表将永不过期,但该分区会在 3 天后过期。
相应架构在如下本地 JSON 文件中指定:/tmp/myschema.json
。customer_id
字段用于聚簇分区。
bq mk -t \
--expiration 2592000 \
--schema /tmp/myschema.json \
--time_partitioning_type=DAY \
--clustering_fields=customer_id \
--time_partitioning_expiration 86400 \
--description "This is my partitioned table" \
--label org:dev \
myotherproject:mydataset.myclusteredtable
API
使用指定了 timePartitioning
属性、clustering.fields
属性和 schema
属性的已定义表资源调用 tables.insert
方法。
Python
在尝试此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 Python 设置说明进行操作。如需了解详情,请参阅 BigQuery Python API 参考文档。
Go
在尝试此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 Go 设置说明进行操作。如需了解详情,请参阅 BigQuery Go API 参考文档。
Java
试用此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 Java 设置说明进行操作。 如需了解详情,请参阅 BigQuery Java API 参考文档。
基于查询结果创建聚簇表
您可以通过以下两种方法,基于查询结果创建聚簇表:
- 将结果写入新目标表并指定聚簇列。下文对此方法做了详细介绍。
- 使用 DDL
CREATE TABLE AS SELECT
语句创建。如需详细了解此方法,请参阅使用数据定义语言语句页面上的从查询结果创建聚簇表。
您可以通过查询分区表或非分区表来创建聚簇表。但不能使用查询结果将现有表更改为聚簇表。
基于查询结果创建聚簇表时,您必须使用标准 SQL。目前,无法使用旧版 SQL 查询聚簇表或将查询结果写入聚簇表。
控制台
使用 Cloud Console 查询数据时,除非使用 DDL 语句,否则无法为目标表指定聚簇选项。如需了解详情,请参阅使用数据定义语言语句。
bq
输入以下命令,基于查询结果创建一个新的聚簇目标表:
bq --location=LOCATION query \ --use_legacy_sql=false 'QUERY'
请替换以下内容:
LOCATION
:您的位置名称。--location
是可选标志。例如,如果您在东京地区使用 BigQuery,可将该标志的值设置为asia-northeast1
。您可以使用 .bigqueryrc 文件设置位置的默认值。QUERY
:使用标准 SQL 语法的查询。目前,无法使用旧版 SQL 查询聚簇表或将查询结果写入聚簇表中。该查询可以包含CREATE TABLE
DDL 语句,以便指定用于创建聚簇表的选项。您可以使用 DDL 而不是指定单独的命令行标志。
示例:
输入以下命令可将查询结果写入 mydataset
中名为 myclusteredtable
的聚簇目标表。mydataset
属于默认项目。该查询从非分区表 mytable 中检索数据。该表的 customer_id
列用于创建聚簇该表。该表的 timestamp
列用于创建分区表。
bq query --use_legacy_sql=false \
'CREATE TABLE
mydataset.myclusteredtable
PARTITION BY
DATE(timestamp)
CLUSTER BY
customer_id AS
SELECT
*
FROM
`mydataset.mytable`'
API
要将查询结果保存到聚簇表,请调用 jobs.insert
方法,配置一个 query
作业,并添加一个用于创建聚簇表的 CREATE TABLE
DDL 语句。
在作业资源 jobReference
部分的 location
属性中指定您的位置。
在加载数据时创建聚簇表
您可通过在向新表加载数据的过程中指定聚簇列来创建聚簇表。无需先创建空表再加载数据,创建聚簇表和加载数据可同时进行。
要详细了解如何加载数据,请参阅将数据加载到 BigQuery 简介。
要在定义加载作业时定义聚簇,请执行以下操作:
API
要在通过加载作业创建表时定义聚簇配置,您可以为该表填充 Clustering
属性。
Go
在尝试此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 Go 设置说明进行操作。如需了解详情,请参阅 BigQuery Go API 参考文档。
Java
试用此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 Java 设置说明进行操作。 如需了解详情,请参阅 BigQuery Java API 参考文档。
Python
在尝试此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 Python 设置说明进行操作。如需了解详情,请参阅 BigQuery Python API 参考文档。
控制对聚簇表的访问权限
如需配置对表和视图的访问权限,您可以在以下级层为实体授予 IAM 角色,这些级层按照允许的资源范围从大到小依次排列:
- Google Cloud 资源层次结构中的较高级层,例如项目、文件夹或组织级层
- 数据集级层
- 表/视图级层
对受 IAM 保护的任何资源的访问权限具有附加性。例如,如果某个实体没有项目等较高级层的访问权限,您可以在数据集级层向该实体授予访问权限,然后该实体便将有权访问该数据集中的表和视图。同样,如果实体没有较高级层或数据集级层的访问权限,您可以在表或视图级层向该实体授予访问权限。
在 Google Cloud 资源层次结构中授予更高级层(例如项目、文件夹或组织级层)的 IAM 角色,使实体可访问一组广泛的资源。例如,在项目级为实体授予角色会为该实体提供整个项目中所有数据集的访问权限。
在数据集级层授予角色可指定允许实体对该特定数据集中的表和视图执行的操作,即使实体没有更高级层的访问权限也可执行这些操作。如需详细了解如何配置数据集级层的访问权限控制,请参阅控制对数据集的访问权限。
在表或视图级层授予角色可指定允许实体对特定表和视图执行的操作,即使实体没有更高级层的访问权限也可执行这些操作。如需了解如何配置表级层的访问权限控制,请参阅控制对表和视图的访问权限。
您还可以创建 IAM 自定义角色。如果创建自定义角色,则您授予的权限取决于您希望实体能够执行的具体操作。
您无法对受 IAM 保护的任何资源设置“拒绝”权限。
如需详细了解角色和权限,请参阅:
- IAM 文档中的了解角色
- BigQuery 预定义的角色和权限
- 控制对数据集的访问
- 控制对表和视图的访问权限
- 通过 BigQuery 列级层安全性限制访问权限
使用聚簇表
获取有关聚簇表的信息
您可以通过以下方式来获取有关表的信息:
- 使用 Cloud Console。
- 使用
bq
命令行工具的bq show
命令。 - 调用
tables.get
API 方法。 - 查询
INFORMATION_SCHEMA
视图。
所需权限
如需获取有关表的信息,您至少必须获得 bigquery.tables.get
权限。以下预定义的 IAM 角色包含 bigquery.tables.get
权限:
bigquery.metadataViewer
bigquery.dataViewer
bigquery.dataOwner
bigquery.dataEditor
bigquery.admin
此外,如果用户具有 bigquery.datasets.create
权限,则当该用户创建数据集时,系统会为其授予该数据集的 bigquery.dataOwner
访问权限。借助 bigquery.dataOwner
访问权限,用户可以获取数据集内表的信息。
如需详细了解 BigQuery 中的 IAM 角色和权限,请参阅预定义的角色和权限。
获取聚簇表信息
要查看聚簇表的相关信息,请执行以下操作:
控制台
在 Google Cloud Console 中,转到 资源窗格。点击数据集名称将其展开,然后点击要查看的表名称。
点击详细信息。此页面会显示表的详细信息,包括聚簇列。
bq
发出 bq show
命令可显示所有表信息。使用 --schema
标志可仅显示表的架构信息。--format
标志可用于控制输出。
如果您要获取非默认项目中的表信息,请按以下格式将相应项目 ID 添加到数据集:project_id:dataset
。
bq show \ --schema \ --format=prettyjson \ PROJECT_ID:DATASET.TABLE
替换以下内容:
PROJECT_ID
:您的项目 IDDATASET
:数据集的名称TABLE
:表格的名称
示例:
输入以下命令可显示 mydataset
中有关 myclusteredtable
的所有信息。mydataset
属于默认项目。
bq show --format=prettyjson mydataset.myclusteredtable
输出应如下所示:
{ "clustering": { "fields": [ "customer_id" ] }, ... }
API
调用 bigquery.tables.get
方法并提供所有相关参数。
SQL
对于聚簇表,您可以查询 INFORMATION_SCHEMA.COLUMNS
视图中的 CLUSTERING_ORDINAL_POSITION
列,检索表的聚簇列的相关信息。
-- Set up a table with clustering. CREATE TABLE myDataset.data (column1 INT64, column2 INT64) PARTITION BY _PARTITIONDATE CLUSTER BY column1, column2; -- This query returns 1 for column1 and 2 for column2. SELECT column_name, clustering_ordinal_position FROM myDataset.INFORMATION_SCHEMA.COLUMNS;
通过 INFORMATION_SCHEMA
中的 TABLES
、TABLE_OPTIONS
、COLUMNS
和 COLUMN_FIELD_PATH
视图,可查看更多表元数据。
列出数据集中的聚簇表
您可以通过以下方式列出数据集中的聚簇表:
- 使用 Cloud Console。
- 使用
bq
命令行工具的bq ls
命令。 - 调用
tables.list
API 方法。 - 使用客户端库。
- 在
INFORMATION_SCHEMA.COLUMNS
视图中查询CLUSTERING_ORDINAL_POSITION
列。
列出聚簇表所需的权限以及步骤与列出分区表相同。如需详细了解如何列出表,请参阅列出数据集中的分区表。
修改聚簇规范
通过调用 tables.update
或 tables.patch
方法,可以更改或移除表聚簇规范。还可以将聚簇表中的聚簇列集更改为其他列集。这种聚簇列集更新方法对支持连续流式插入的表最有用,因为使用其他方法无法轻松交换这些表。
如果将表从非聚簇转换为聚簇,或者聚簇列集发生更改,则自动重新聚簇仅从那时起才起作用。例如,如果使用 tables.update
将大小为 1 PB 的非聚簇表转换为聚簇表,转换后的表仍会包含 1 PB 的非聚簇数据。自动重新聚簇仅适用于更新后提交到表的所有新数据。
后续步骤
- 要了解如何查询聚簇表,请参阅查询聚簇表。
- 如需大致了解 BigQuery 中的分区表支持,请参阅分区表简介。
- 如需了解如何创建和使用提取时间分区表,请参阅创建和使用提取时间分区表。
- 要了解如何创建和使用分区表,请参阅创建和使用分区表。
- 如需查看
INFORMATION_SCHEMA
的概览,请转到 BigQueryINFORMATION_SCHEMA
简介。