建立及使用叢集資料表

本文件說明如何在 BigQuery 中建立及使用叢集資料表。如需 BigQuery 中的叢集資料表支援總覽,請參閱叢集資料表簡介

建立叢集資料表

您可以使用下列方法建立叢集資料表:

資料表命名

在 BigQuery 中建立資料表時,每個資料集裡的資料表名稱不得重複。資料表名稱可以:

  • 包含的字元總數上限為 1,024 個 UTF-8 位元組。
  • 包含 L (字母)、M (符號)、N (數字)、Pc (連接號,包括底線)、Pd (破折號)、Zs (空格) 類別的萬國碼字元。詳情請參閱「一般類別」。

以下是有效資料表名稱的範例:table 01ग्राहक00_お客様étudiant-01

注意事項:

  • 根據預設,表格名稱會區分大小寫。mytableMyTable 可在同一資料集中共存,除非它們屬於已關閉大小寫敏感度的資料集
  • 我們已保留部分表格名稱和表格名稱前置字串,如果您收到錯誤訊息,指出表格名稱或前置字串已保留,請選取其他名稱,然後再試一次。
  • 如果序列中包含多個點運算子 (.),系統會隱含地移除重複的運算子。

    例如: project_name....dataset_name..table_name

    變成: project_name.dataset_name.table_name

所需權限

如要建立資料表,您必須具備下列 IAM 權限:

  • bigquery.tables.create
  • bigquery.tables.updateData
  • bigquery.jobs.create

此外,您可能需要 bigquery.tables.getData 權限,才能存取您寫入資料表的資料。

以下每個預先定義的 IAM 角色都包含建立資料表所需的權限:

  • roles/bigquery.dataEditor
  • roles/bigquery.dataOwner
  • roles/bigquery.admin (包含 bigquery.jobs.create 權限)
  • roles/bigquery.user (包含 bigquery.jobs.create 權限)
  • roles/bigquery.jobUser (包含 bigquery.jobs.create 權限)

此外,如果您具備 bigquery.datasets.create 權限,就可以在所建立的資料集中建立及更新資料表。

如要進一步瞭解 BigQuery 中的 IAM 角色和權限,請參閱「預先定義的角色與權限」一文。

使用結構定義建立空白叢集資料表

您在 BigQuery 中建立資料表時,應指定要叢集的欄位。資料表建立完成後,您可以修改叢集欄位。詳情請參閱「修改叢集規格」。

叢集資料欄必須是頂層的非重複資料欄,且屬於下列任一資料類型:

  • BIGNUMERIC
  • BOOL
  • DATE
  • DATETIME
  • GEOGRAPHY
  • INT64
  • NUMERIC
  • RANGE
  • STRING
  • TIMESTAMP

您最多可指定四個叢集資料欄,當您指定多個叢集資料欄時,資料欄的順序將決定資料的排序方式。舉例來說,如果資料表是依欄位 a、b、c 來進行叢集,則資料也會按照相同順序排序,即第一順位是欄位 a、第二順位是欄位 b、第三順位是欄位 c。按照最佳做法,最常用以進行資料篩選或匯總的資料欄應排在第一順位。

叢集資料欄順序亦會影響資料查詢的效能與定價。如要瞭解查詢叢集資料表的最佳做法,請參閱查詢叢集資料表一文。

如何使用結構定義建立空白叢集資料表:

主控台

  1. 前往 Google Cloud 控制台的「BigQuery」頁面。

    前往 BigQuery

  2. 在「Explorer」窗格中展開專案,然後選取資料集。
  3. 在「資料集資訊」部分,按一下 「建立資料表」
  4. 在「Create table」面板中,指定下列詳細資料:
    1. 在「Source」部分,選取「Create table from」清單中的「Empty table」
    2. 在「Destination」(目的地) 部分中,指定下列詳細資料:
      1. 在「Dataset」(資料集) 部分,選取要建立資料表的資料集。
      2. 在「Table」(資料表) 欄位中,輸入要建立的資料表名稱。
      3. 確認「Table type」欄位已設為「Native table」
    3. 在「Schema」(結構定義) 部分輸入結構定義。您可以使用下列任一方式,手動輸入結構定義資訊:
      • 選項 1:按一下「Edit as Text」(以文字形式編輯),然後以 JSON 陣列的形式貼上結構定義。如果您使用 JSON 陣列,可透過與建立 JSON 結構定義檔一樣的程序產生結構定義。您可以輸入下列指令,查看現有資料表的 JSON 格式結構定義:
            bq show --format=prettyjson dataset.table
            
      • 選項 2:按一下「新增欄位」,然後輸入表格結構定義。指定每個欄位的「Name」、「Type」 和「Mode」
    4. 針對「Clustering order」(分群順序),輸入一到四個以半形逗號分隔的欄位名稱。
    5. 選用步驟:如果您想使用客戶管理的加密金鑰,請在「Advanced options」(進階選項) 部分選取「Use a customer-managed encryption key (CMEK)」(使用客戶管理的加密金鑰 (CMEK)) 選項。根據預設,BigQuery 會使用 Google-owned and Google-managed encryption key加密靜態儲存的客戶內容
    6. 點選「建立資料表」。

SQL

使用 CREATE TABLE DDL 陳述式指令搭配 CLUSTER BY 選項。以下範例會在 mydataset 中建立名為 myclusteredtable 的叢集資料表:

  1. 前往 Google Cloud 控制台的「BigQuery」頁面。

    前往 BigQuery

  2. 在查詢編輯器中輸入以下陳述式:

    CREATE TABLE mydataset.myclusteredtable
    (
      customer_id STRING,
      transaction_amount NUMERIC
    )
    CLUSTER BY
      customer_id
      OPTIONS (
        description = 'a table clustered by customer_id');

  3. 按一下 「Run」

如要進一步瞭解如何執行查詢,請參閱「執行互動式查詢」一文。

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 \
    --clustering_fields CLUSTER_COLUMNS \
    --description "DESCRIPTION" \
    --label KEY:VALUE,KEY:VALUE \
    PROJECT_ID:DATASET.TABLE

更改下列內容:

  • INTEGER1:資料表的預設生命週期 (以秒為單位)。最小值是 3,600 秒 (1 小時)。到期時間為目前世界標準時間加整數值。如果您在建立資料表時設定了資料表到期時間,系統會忽略資料集的預設資料表到期時間設定。設定這個值會在指定時間到期後刪除資料表。
  • SCHEMA:格式為 COLUMN:DATA_TYPE,COLUMN:DATA_TYPE 的內嵌結構定義,或您本機機器上的 JSON 結構定義檔路徑。
  • CLUSTER_COLUMNS:以逗號分隔的清單,最多包含四個叢集資料欄。清單中不得有任何空格。
  • DESCRIPTION:置於括號中的資料表說明。
  • KEY:VALUE:代表標籤的鍵/值組合。您可以用逗號分隔的清單輸入多個標籤。
  • PROJECT_ID:您的專案 ID。
  • DATASET:專案中的資料集。
  • TABLE:您要建立的資料表名稱。

您在指令列中指定結構定義時,無法加入 RECORD (STRUCT) 類型和資料欄說明,也不能指定資料欄模式。所有模式均預設為 NULLABLE。如要加入說明、模式和 RECORD 類型,請改為提供 JSON 結構定義檔

範例:

輸入下列指令,在預設專案中的 mydataset 內建立名為 myclusteredtable 的叢集資料表,資料表到期時間設為 2,592,000 秒 (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' \
    --clustering_fields customer_id \
    --description "This is my clustered table" \
    --label org:dev \
    mydataset.myclusteredtable

輸入下列指令,在 myotherproject (而非預設專案) 中建立名為 myclusteredtable 的叢集資料表,說明設為 This is my clustered table,標籤則設為 organization:development。此指令使用 -t 捷徑,而非 --table。這個指令不會指定資料表到期時間。如果資料集有預設資料表到期時間,系統會直接套用這個時間。如果資料集沒有預設資料表到期時間,資料表就永遠不會過期。

結構定義在本機 JSON 檔案 /tmp/myschema.json 中指定。customer_id 欄位用於叢集資料表。

bq mk \
    -t \
    --expiration 2592000 \
    --schema /tmp/myschema.json \
    --clustering_fields=customer_id \
    --description "This is my clustered table" \
    --label org:dev \
    myotherproject:mydataset.myclusteredtable

建立資料表後,您可以更新資料表的說明標籤

Terraform

使用 google_bigquery_table 資源。

如要向 BigQuery 進行驗證,請設定應用程式預設憑證。詳情請參閱「設定用戶端程式庫的驗證機制」。

以下範例會建立名為 mytable 的資料表,並在 IDCreated 資料欄上進行叢集:

resource "google_bigquery_dataset" "default" {
  dataset_id                      = "mydataset"
  default_partition_expiration_ms = 2592000000  # 30 days
  default_table_expiration_ms     = 31536000000 # 365 days
  description                     = "dataset description"
  location                        = "US"
  max_time_travel_hours           = 96 # 4 days

  labels = {
    billing_group = "accounting",
    pii           = "sensitive"
  }
}

resource "google_bigquery_table" "default" {
  dataset_id          = google_bigquery_dataset.default.dataset_id
  table_id            = "mytable"
  deletion_protection = false # set to "true" in production

  clustering = ["ID", "Created"]

  schema = <<EOF
[
  {
    "name": "ID",
    "type": "INT64",
    "description": "Item ID"
  },
  {
    "name": "Item",
    "type": "STRING",
    "mode": "NULLABLE"
  },
 {
   "name": "Created",
   "type": "TIMESTAMP"
 }
]
EOF

}

如要在 Google Cloud 專案中套用 Terraform 設定,請完成下列各節中的步驟。

準備 Cloud Shell

  1. 啟動 Cloud Shell
  2. 設定要套用 Terraform 設定的預設 Google Cloud 專案。

    您只需為每個專案執行這個指令一次,而且可以在任何目錄中執行。

    export GOOGLE_CLOUD_PROJECT=PROJECT_ID

    如果您在 Terraform 設定檔中設定明確的值,系統就會覆寫環境變數。

準備目錄

每個 Terraform 設定檔都必須有自己的目錄 (也稱為根模組)。

  1. Cloud Shell 中建立目錄,並在該目錄中建立新檔案。檔案名稱必須包含 .tf 副檔名,例如 main.tf。在本教學課程中,檔案稱為 main.tf
    mkdir DIRECTORY && cd DIRECTORY && touch main.tf
  2. 如果您正在參考教學課程,可以複製各個章節或步驟中的程式碼範例。

    將範例程式碼複製到新建立的 main.tf 中。

    您可以視需要從 複製程式碼。如果 Terraform 程式碼片段是端對端解決方案的一部分,建議您採用這種做法。

  3. 查看並修改要套用至環境的範例參數。
  4. 儲存變更。
  5. 初始化 Terraform。這項操作只需對每個目錄執行一次。
    terraform init

    如要使用最新版的 Google 供應器,您可以選擇加入 -upgrade 選項:

    terraform init -upgrade

套用變更

  1. 檢查設定,確認 Terraform 要建立或更新的資源符合您的預期:
    terraform plan

    視需要修正設定。

  2. 執行下列指令,並在提示中輸入 yes,即可套用 Terraform 設定:
    terraform apply

    等待 Terraform 顯示「Apply complete!」(套用完成) 訊息。

  3. 開啟 Google Cloud 專案即可查看結果。在 Google Cloud 控制台中,前往 UI 中的資源,確認 Terraform 已建立或更新這些資源。

API

使用指定 clustering.fields 屬性和 schema 屬性的已定義資料表資源呼叫 tables.insert 方法。

Python

在嘗試這個範例之前,請先按照 BigQuery 快速入門:使用用戶端程式庫中的 Python 設定說明進行操作。詳情請參閱 BigQuery Python API 參考說明文件

如要向 BigQuery 進行驗證,請設定應用程式預設憑證。詳情請參閱「設定用戶端程式庫的驗證機制」。

from google.cloud import bigquery

# Construct a BigQuery client object.
client = bigquery.Client()

# TODO(developer): Set table_id to the ID of the table to create.
# table_id = "your-project.your_dataset.your_table_name"

schema = [
    bigquery.SchemaField("full_name", "STRING"),
    bigquery.SchemaField("city", "STRING"),
    bigquery.SchemaField("zipcode", "INTEGER"),
]

table = bigquery.Table(table_id, schema=schema)
table.clustering_fields = ["city", "zipcode"]
table = client.create_table(table)  # Make an API request.
print(
    "Created clustered table {}.{}.{}".format(
        table.project, table.dataset_id, table.table_id
    )
)

Go

在嘗試這個範例之前,請先按照 BigQuery 快速入門:使用用戶端程式庫中的 Go 設定說明進行操作。詳情請參閱 BigQuery Go API 參考說明文件

如要向 BigQuery 進行驗證,請設定應用程式預設憑證。詳情請參閱「設定用戶端程式庫的驗證機制」。

import (
	"context"
	"fmt"
	"time"

	"cloud.google.com/go/bigquery"
)

// createTableClustered demonstrates creating a BigQuery table with advanced properties like
// partitioning and clustering features.
func createTableClustered(projectID, datasetID, tableID string) error {
	// projectID := "my-project-id"
	// datasetID := "mydatasetid"
	// tableID := "mytableid"
	ctx := context.Background()

	client, err := bigquery.NewClient(ctx, projectID)
	if err != nil {
		return fmt.Errorf("bigquery.NewClient: %v", err)
	}
	defer client.Close()

	sampleSchema := bigquery.Schema{
		{Name: "timestamp", Type: bigquery.TimestampFieldType},
		{Name: "origin", Type: bigquery.StringFieldType},
		{Name: "destination", Type: bigquery.StringFieldType},
		{Name: "amount", Type: bigquery.NumericFieldType},
	}
	metaData := &bigquery.TableMetadata{
		Schema: sampleSchema,
		TimePartitioning: &bigquery.TimePartitioning{
			Field:      "timestamp",
			Expiration: 90 * 24 * time.Hour,
		},
		Clustering: &bigquery.Clustering{
			Fields: []string{"origin", "destination"},
		},
	}
	tableRef := client.Dataset(datasetID).Table(tableID)
	if err := tableRef.Create(ctx, metaData); err != nil {
		return err
	}
	return nil
}

Java

在嘗試這個範例之前,請先按照 BigQuery 快速入門:使用用戶端程式庫中的 Java 設定說明進行操作。詳情請參閱 BigQuery Java API 參考說明文件

如要向 BigQuery 進行驗證,請設定應用程式預設憑證。詳情請參閱「設定用戶端程式庫的驗證機制」。

import com.google.cloud.bigquery.BigQuery;
import com.google.cloud.bigquery.BigQueryException;
import com.google.cloud.bigquery.BigQueryOptions;
import com.google.cloud.bigquery.Clustering;
import com.google.cloud.bigquery.Field;
import com.google.cloud.bigquery.Schema;
import com.google.cloud.bigquery.StandardSQLTypeName;
import com.google.cloud.bigquery.StandardTableDefinition;
import com.google.cloud.bigquery.TableId;
import com.google.cloud.bigquery.TableInfo;
import com.google.cloud.bigquery.TimePartitioning;
import com.google.common.collect.ImmutableList;

public class CreateClusteredTable {
  public static void runCreateClusteredTable() {
    // TODO(developer): Replace these variables before running the sample.
    String datasetName = "MY_DATASET_NAME";
    String tableName = "MY_TABLE_NAME";
    createClusteredTable(datasetName, tableName);
  }

  public static void createClusteredTable(String datasetName, String tableName) {
    try {
      // Initialize client that will be used to send requests. This client only needs to be created
      // once, and can be reused for multiple requests.
      BigQuery bigquery = BigQueryOptions.getDefaultInstance().getService();

      TableId tableId = TableId.of(datasetName, tableName);

      TimePartitioning partitioning = TimePartitioning.of(TimePartitioning.Type.DAY);

      Schema schema =
          Schema.of(
              Field.of("name", StandardSQLTypeName.STRING),
              Field.of("post_abbr", StandardSQLTypeName.STRING),
              Field.of("date", StandardSQLTypeName.DATE));

      Clustering clustering =
          Clustering.newBuilder().setFields(ImmutableList.of("name", "post_abbr")).build();

      StandardTableDefinition tableDefinition =
          StandardTableDefinition.newBuilder()
              .setSchema(schema)
              .setTimePartitioning(partitioning)
              .setClustering(clustering)
              .build();
      TableInfo tableInfo = TableInfo.newBuilder(tableId, tableDefinition).build();

      bigquery.create(tableInfo);
      System.out.println("Clustered table created successfully");
    } catch (BigQueryException e) {
      System.out.println("Clustered table was not created. \n" + e.toString());
    }
  }
}

從查詢結果建立叢集資料表

從查詢結果建立叢集資料表的作法有兩種:

您可以藉由查詢分區資料表或非分區資料表的方式建立叢集資料表,但不能利用查詢結果將現有的資料表變更為叢集資料表。

當您從查詢結果建立叢集資料表時,必須要使用標準 SQL。目前,系統不支援使用舊版 SQL 查詢叢集資料表或將查詢結果寫入叢集資料表。

SQL

如要從查詢結果建立叢集資料表,請使用 CREATE TABLE DDL 陳述式搭配 CLUSTER BY 選項。以下範例會查詢現有的未叢集資料表,建立由 customer_id 叢集的新資料表:

  1. 前往 Google Cloud 控制台的「BigQuery」頁面。

    前往 BigQuery

  2. 在查詢編輯器中輸入以下陳述式:

    CREATE TABLE mydataset.clustered_table
    (
      customer_id STRING,
      transaction_amount NUMERIC
    )
    CLUSTER BY
      customer_id
    AS (
      SELECT * FROM mydataset.unclustered_table
    );

  3. 按一下 「Run」

如要進一步瞭解如何執行查詢,請參閱「執行互動式查詢」一文。

bq

輸入下列指令,從查詢結果中建立新的叢集目的地資料表:

bq --location=LOCATION query \
    --use_legacy_sql=false 'QUERY'

更改下列內容:

  • LOCATION:您所在位置的名稱。--location 是選用旗標。舉例來說,如果您在東京地區使用 BigQuery,就可以將旗標的值設為 asia-northeast1。您可以使用 .bigqueryrc 檔案設定位置的預設值。
  • QUERY:採用 GoogleSQL 語法的查詢。目前您無法使用舊版 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 的簡介

如要在定義載入工作時定義叢集,請進行以下操作:

SQL

使用 LOAD DATA 陳述式。以下範例會載入 AVRO 資料,建立由 transaction_date 欄分區,並以 customer_id 欄分群的資料表。並將分區設定為在三天後到期。

  1. 前往 Google Cloud 控制台的「BigQuery」頁面。

    前往 BigQuery

  2. 在查詢編輯器中輸入以下陳述式:

    LOAD DATA INTO mydataset.mytable
    PARTITION BY transaction_date
    CLUSTER BY customer_id
      OPTIONS (
        partition_expiration_days = 3)
    FROM FILES(
      format = 'AVRO',
      uris = ['gs://bucket/path/file.avro']);

  3. 按一下 「Run」

如要進一步瞭解如何執行查詢,請參閱「執行互動式查詢」一文。

API

如要在透過載入工作建立資料表時定義叢集設定,您可以填入資料表的 Clustering 屬性。

Go

在嘗試這個範例之前,請先按照 BigQuery 快速入門:使用用戶端程式庫中的 Go 設定說明進行操作。詳情請參閱 BigQuery Go API 參考說明文件

如要向 BigQuery 進行驗證,請設定應用程式預設憑證。詳情請參閱「設定用戶端程式庫的驗證機制」。

import (
	"context"
	"fmt"

	"cloud.google.com/go/bigquery"
)

// importClusteredTable demonstrates creating a table from a load job and defining partitioning and clustering
// properties.
func importClusteredTable(projectID, destDatasetID, destTableID string) error {
	// projectID := "my-project-id"
	// datasetID := "mydataset"
	// tableID := "mytable"
	ctx := context.Background()
	client, err := bigquery.NewClient(ctx, projectID)
	if err != nil {
		return fmt.Errorf("bigquery.NewClient: %v", err)
	}
	defer client.Close()

	gcsRef := bigquery.NewGCSReference("gs://cloud-samples-data/bigquery/sample-transactions/transactions.csv")
	gcsRef.SkipLeadingRows = 1
	gcsRef.Schema = bigquery.Schema{
		{Name: "timestamp", Type: bigquery.TimestampFieldType},
		{Name: "origin", Type: bigquery.StringFieldType},
		{Name: "destination", Type: bigquery.StringFieldType},
		{Name: "amount", Type: bigquery.NumericFieldType},
	}
	loader := client.Dataset(destDatasetID).Table(destTableID).LoaderFrom(gcsRef)
	loader.TimePartitioning = &bigquery.TimePartitioning{
		Field: "timestamp",
	}
	loader.Clustering = &bigquery.Clustering{
		Fields: []string{"origin", "destination"},
	}
	loader.WriteDisposition = bigquery.WriteEmpty

	job, err := loader.Run(ctx)
	if err != nil {
		return err
	}
	status, err := job.Wait(ctx)
	if err != nil {
		return err
	}

	if status.Err() != nil {
		return fmt.Errorf("job completed with error: %v", status.Err())
	}
	return nil
}

Java

在嘗試這個範例之前,請先按照 BigQuery 快速入門:使用用戶端程式庫中的 Java 設定說明進行操作。詳情請參閱 BigQuery Java API 參考說明文件

如要向 BigQuery 進行驗證,請設定應用程式預設憑證。詳情請參閱「設定用戶端程式庫的驗證機制」。

import com.google.cloud.bigquery.BigQuery;
import com.google.cloud.bigquery.BigQueryException;
import com.google.cloud.bigquery.BigQueryOptions;
import com.google.cloud.bigquery.Clustering;
import com.google.cloud.bigquery.Field;
import com.google.cloud.bigquery.FormatOptions;
import com.google.cloud.bigquery.Job;
import com.google.cloud.bigquery.JobInfo;
import com.google.cloud.bigquery.LoadJobConfiguration;
import com.google.cloud.bigquery.Schema;
import com.google.cloud.bigquery.StandardSQLTypeName;
import com.google.cloud.bigquery.TableId;
import com.google.cloud.bigquery.TimePartitioning;
import com.google.common.collect.ImmutableList;

public class LoadTableClustered {

  public static void runLoadTableClustered() throws Exception {
    // TODO(developer): Replace these variables before running the sample.
    String datasetName = "MY_DATASET_NAME";
    String tableName = "MY_TABLE_NAME";
    String sourceUri = "/path/to/file.csv";
    loadTableClustered(datasetName, tableName, sourceUri);
  }

  public static void loadTableClustered(String datasetName, String tableName, String sourceUri)
      throws Exception {
    try {
      // Initialize client that will be used to send requests. This client only needs to be created
      // once, and can be reused for multiple requests.
      BigQuery bigquery = BigQueryOptions.getDefaultInstance().getService();

      TableId tableId = TableId.of(datasetName, tableName);

      Schema schema =
          Schema.of(
              Field.of("name", StandardSQLTypeName.STRING),
              Field.of("post_abbr", StandardSQLTypeName.STRING),
              Field.of("date", StandardSQLTypeName.DATE));

      TimePartitioning partitioning = TimePartitioning.of(TimePartitioning.Type.DAY);

      Clustering clustering =
          Clustering.newBuilder().setFields(ImmutableList.of("name", "post_abbr")).build();

      LoadJobConfiguration loadJobConfig =
          LoadJobConfiguration.builder(tableId, sourceUri)
              .setFormatOptions(FormatOptions.csv())
              .setSchema(schema)
              .setTimePartitioning(partitioning)
              .setClustering(clustering)
              .build();

      Job loadJob = bigquery.create(JobInfo.newBuilder(loadJobConfig).build());

      // Load data from a GCS parquet file into the table
      // Blocks until this load table job completes its execution, either failing or succeeding.
      Job completedJob = loadJob.waitFor();

      // Check for errors
      if (completedJob == null) {
        throw new Exception("Job not executed since it no longer exists.");
      } else if (completedJob.getStatus().getError() != null) {
        // You can also look at queryJob.getStatus().getExecutionErrors() for all
        // errors, not just the latest one.
        throw new Exception(
            "BigQuery was unable to load into the table due to an error: \n"
                + loadJob.getStatus().getError());
      }
      System.out.println("Data successfully loaded into clustered table during load job");
    } catch (BigQueryException | InterruptedException e) {
      System.out.println("Data not loaded into clustered table during load job \n" + e.toString());
    }
  }
}

Python

在嘗試這個範例之前,請先按照 BigQuery 快速入門:使用用戶端程式庫中的 Python 設定說明進行操作。詳情請參閱 BigQuery Python API 參考說明文件

如要向 BigQuery 進行驗證,請設定應用程式預設憑證。詳情請參閱「設定用戶端程式庫的驗證機制」。

from google.cloud import bigquery

# Construct a BigQuery client object.
client = bigquery.Client()

# TODO(developer): Set table_id to the ID of the table to create.
# table_id = "your-project.your_dataset.your_table_name"

job_config = bigquery.LoadJobConfig(
    skip_leading_rows=1,
    source_format=bigquery.SourceFormat.CSV,
    schema=[
        bigquery.SchemaField("timestamp", bigquery.SqlTypeNames.TIMESTAMP),
        bigquery.SchemaField("origin", bigquery.SqlTypeNames.STRING),
        bigquery.SchemaField("destination", bigquery.SqlTypeNames.STRING),
        bigquery.SchemaField("amount", bigquery.SqlTypeNames.NUMERIC),
    ],
    time_partitioning=bigquery.TimePartitioning(field="timestamp"),
    clustering_fields=["origin", "destination"],
)

job = client.load_table_from_uri(
    ["gs://cloud-samples-data/bigquery/sample-transactions/transactions.csv"],
    table_id,
    job_config=job_config,
)

job.result()  # Waits for the job to complete.

table = client.get_table(table_id)  # Make an API request.
print(
    "Loaded {} rows and {} columns to {}".format(
        table.num_rows, len(table.schema), table_id
    )
)

控管叢集資料表的存取權

如要設定資料表和檢視表的存取權,您可以在下列層級為實體授予 IAM 角色,這些層級依允許的資源範圍排序 (由大到小):

  • Google Cloud 資源階層中的高層級,例如專案、資料夾或機構層級
  • 資料集層級
  • 資料表或檢視畫面層級

您也可以使用下列方法,限制資料表內的資料存取權:

任何受 IAM 保護的資源存取權都是疊加的。舉例來說,如果實體沒有專案等高層級的存取權,您可以授予實體資料集層級的存取權,這樣實體就能存取資料集中的資料表和檢視畫面。同樣地,如果實體沒有高層級或資料集層級的存取權,您可以在資料表或檢視表層級授予實體存取權。

Google Cloud資源階層中的較高層級 (例如專案、資料夾或機構層級) 授予 IAM 角色,可讓實體存取更多資源。舉例來說,在專案層級將特定角色授予實體,可讓該實體擁有適用於專案中所有資料集的權限。

在資料集層級授予角色,即可讓實體對特定資料集裡的資料表和檢視表執行指定作業,即使實體沒有更高層級的存取權也是如此。如要瞭解如何設定資料集層級的存取權控管設定,請參閱「控管資料集存取權」一文。

在資料表或檢視表層級授予角色,即可讓實體對特定資料表和檢視表執行指定作業,即使實體沒有較高層級的存取權也是如此。如要瞭解如何設定資料表層級存取權控管設定,請參閱「控管資料表和檢視表存取權」一文。

您也可以建立 IAM 自訂角色。建立自訂角色之後,您就能依據要讓實體執行的特定作業授予權限。

您無法對任何受 IAM 保護的資源設定「拒絕」權限。

如要進一步瞭解角色和權限,請參閱 IAM 說明文件中的「瞭解角色」一節,以及 BigQuery 的「IAM 角色和權限」一文。

使用叢集資料表

取得叢集資料表的相關資訊

您可以透過下列方式取得資料表的相關資訊:

  • 使用 Google Cloud 控制台。
  • 使用 bq 指令列工具的 bq show 指令。
  • 呼叫 tables.get API 方法
  • 查詢 INFORMATION_SCHEMA 檢視表。

所需權限

您至少要具備 bigquery.tables.get 權限,才能取得資料表相關資訊。以下是具有 bigquery.tables.get 權限的預先定義 IAM 角色:

  • bigquery.metadataViewer
  • bigquery.dataViewer
  • bigquery.dataOwner
  • bigquery.dataEditor
  • bigquery.admin

此外,當具備 bigquery.datasets.create 權限的使用者建立資料集時,會獲得該資料集的 bigquery.dataOwner 存取權。bigquery.dataOwner 存取權可讓使用者取得資料集裡的資料表相關資訊。

如要進一步瞭解 BigQuery 中的 IAM 角色和權限,請參閱「預先定義的角色與權限」一文。

取得叢集資料表資訊

如何查看叢集資料表的相關資訊:

主控台

  1. 在 Google Cloud 控制台中,前往「Resources」窗格。按一下資料集名稱,即可展開該資料集,然後點選您想要查看的資料表名稱。

  2. 按一下 [Details] (詳細資料)。這個頁面會顯示包含叢集資料欄的資料表詳細資料。

    資料表詳細資料。

SQL

對於叢集資料表,您可以在 INFORMATION_SCHEMA.COLUMNS 檢視畫面中查詢 CLUSTERING_ORDINAL_POSITION 資料欄,找出資料表叢集資料欄中資料欄的 1 索引偏移:

  1. 前往 Google Cloud 控制台的「BigQuery」頁面。

    前往 BigQuery

  2. 在查詢編輯器中輸入以下陳述式:

    CREATE TABLE mydataset.data (column1 INT64, column2 INT64)
    CLUSTER BY column1, column2;
    SELECT
      column_name, clustering_ordinal_position
    FROM
      mydataset.INFORMATION_SCHEMA.COLUMNS;

  3. 按一下 「Run」

如要進一步瞭解如何執行查詢,請參閱「執行互動式查詢」一文。

column1 的叢集序號位置為 1,column2 為 2。您可以透過 INFORMATION_SCHEMA 中的 TABLESTABLE_OPTIONSCOLUMNSCOLUMN_FIELD_PATH 檢視表,查看更多資料表中繼資料。

bq

發出 bq show 指令以顯示所有資料表資訊。使用 --schema 旗標可以只顯示資料表結構定義資訊。--format 旗標可用來控制輸出內容。

如果您要取得非預設專案中資料表的相關資訊,請使用下列格式將專案 ID 新增至資料集:project_id:dataset

bq show \
    --schema \
    --format=prettyjson \
    PROJECT_ID:DATASET.TABLE

更改下列內容:

  • PROJECT_ID:您的專案 ID
  • DATASET:資料集名稱
  • TABLE:資料表名稱

範例:

輸入下列指令,顯示 mydatasetmyclusteredtable 的所有相關資訊。mydataset 在您的預設專案中。

bq show --format=prettyjson mydataset.myclusteredtable

輸出應如下所示:

{
  "clustering": {
    "fields": [
      "customer_id"
    ]
  },
...
}

API

呼叫 bigquery.tables.get 方法,並提供所有相關參數。

列出資料集中的叢集資料表

您可以透過下列方式列出資料集中的叢集資料表:

  • 使用 Google Cloud 控制台。
  • 使用 bq 指令列工具的 bq ls 指令。
  • 呼叫 tables.list API 方法。
  • 使用用戶端程式庫。
  • INFORMATION_SCHEMA.COLUMNS 檢視畫面中查詢 CLUSTERING_ORDINAL_POSITION 欄。

列出叢集資料表所需具備的權限及步驟,與標準資料表相同。如要進一步瞭解如何列出資料表,請參閱「在資料集中列出資料表」一文。

修改分群規格

您可以變更或移除資料表的叢集規格,或是變更叢集資料表中的叢集資料欄組合。這種更新叢集欄組合的方法適用於使用持續串流插入功能的資料表,因為這些資料表無法輕易透過其他方法交換。

請按照下列步驟,將新的叢集規格套用至未分區或已分區的資料表。

  1. 在 bq 工具中,更新資料表的叢集規格,以符合新的叢集:

     bq update --clustering_fields=CLUSTER_COLUMN DATASET.ORIGINAL_TABLE 

    更改下列內容:

    • CLUSTER_COLUMN:您要進行叢集的資料欄,例如 mycolumn
    • DATASET:包含資料表的資料集名稱,例如 mydataset
    • ORIGINAL_TABLE:原始資料表的名稱,例如 mytable

    您也可以呼叫 tables.updatetables. API 方法,修改叢集規格

  2. 如要根據新的叢集規格將所有資料列分組,請執行下列 UPDATE 陳述式:

    UPDATE DATASET.ORIGINAL_TABLE SET CLUSTER_COLUMN=CLUSTER_COLUMN WHERE true

表格安全性

如要控管 BigQuery 中資料表的存取權,請參閱「使用 IAM 控管資源存取權」。

後續步驟