管理表

本文档介绍了如何管理 BigQuery 中的表。您可以通过以下方式管理 BigQuery 表:

  • 更新表的以下内容:
    • 到期时间
    • 说明
    • 架构定义
    • 标签
  • 重命名(复制)表
  • 复制表
  • 删除表
  • 恢复已删除的表

如需详细了解如何创建和使用表,包括获取表信息、列出表和控制对表数据的访问权限,请参阅创建和使用表

更新表属性

您可以更新表的以下内容:

所需权限

若要更新表,您必须至少具有 bigquery.tables.updatebigquery.tables.get 权限。以下预定义的 Cloud IAM 角色具有 bigquery.tables.updatebigquery.tables.get 权限:

  • bigquery.dataEditor
  • bigquery.dataOwner
  • bigquery.admin

此外,如果用户具有 bigquery.datasets.create 权限,则当该用户创建数据集时,系统会为其授予该数据集的 bigquery.dataOwner 访问权限。 具备 bigquery.dataOwner 访问权限的用户有权更新其创建的数据集中的表属性。

如需详细了解 BigQuery 中的 Cloud IAM 角色和权限,请参阅访问权限控制

更新表的说明

您可以通过以下方式更新表的说明:

  • 使用 GCP Console 或经典版 BigQuery 网页界面
  • 使用 DDL ALTER TABLE 语句
  • 使用 bq update CLI 命令
  • 调用 tables.patch API 方法
  • 使用客户端库

若要更新表的说明,请执行以下操作:

控制台

使用 GCP Console 创建表时,您无法添加说明。创建表后,您可以在详细信息页面上添加说明。

  1. 资源窗格中,选择表。

  2. 查询编辑器下方,点击详细信息

    修改表架构

  3. 说明部分,点击铅笔图标以修改说明。

    修改说明

  4. 在文本框中输入说明,然后点击更新进行保存。

DDL

借助数据定义语言 (DDL) 语句,您可以使用标准 SQL 查询语法创建和修改表和视图。

详细了解如何使用数据定义语言语句

要在 GCP Console 中使用 DDL 语句更新表的说明,请执行以下操作:

  1. 点击编写新查询

  2. 查询编辑器文本区域中,输入您的 DDL 语句。

     ALTER TABLE mydataset.mytable
     SET OPTIONS (
       description="Description of mytable"
     )
     

  3. 点击运行

经典版界面

  1. 在导航窗格中,选择表。

  2. Table Details 页面上,点击 Details

  3. Description 部分,点击 Describe this table 以打开说明框。

  4. 在该框中输入说明。在框外点击一下即可保存文本。

    表的说明

CLI

发出带 --description 标志的 bq update 命令。如果要更新非默认项目中的表,请使用以下格式将项目 ID 添加到数据集名称中:project_id:dataset

bq update \
--description "description" \
project_id:dataset.table

其中:

  • description 是表的文本说明(括在引号中)。
  • project_id 是项目 ID。
  • dataset 是含有您要更新表的数据集的名称。
  • table 是您要更新的表的名称。

示例:

输入以下命令可将 mydatasetmytable 的说明更改为“Description of mytable”。mydataset 在默认项目中。

bq update --description "Description of mytable" mydataset.mytable

输入以下命令可将 mydatasetmytable 的说明更改为“Description of mytable”。mydatasetmyotherproject 中,不在默认项目中。

bq update \
--description "Description of mytable" \
myotherproject:mydataset.mytable

API

调用 tables.patch 方法并使用表资源中的 description 属性来更新表的说明。由于 tables.update 方法会替换整个表资源,因此最好使用 tables.patch 方法。

Go

试用此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 Go 设置说明进行操作。如需了解详情,请参阅 BigQuery Go API 参考文档

// To run this sample, you will need to create (or reuse) a context and
// an instance of the bigquery client.  For example:
// import "cloud.google.com/go/bigquery"
// ctx := context.Background()
// client, err := bigquery.NewClient(ctx, "your-project-id")
tableRef := client.Dataset(datasetID).Table(tableID)
meta, err := tableRef.Metadata(ctx)
if err != nil {
	return err
}
update := bigquery.TableMetadataToUpdate{
	Description: "Updated description.",
}
if _, err = tableRef.Update(ctx, update, meta.ETag); err != nil {
	return err
}

Java

试用此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 Java 设置说明进行操作。如需了解详情,请参阅 BigQuery Java API 参考文档

// String datasetName = "my_dataset_name";
// String tableName = "my_table_name";
// String newDescription = "new_description";

Table beforeTable = bigquery.getTable(datasetName, tableName);
TableInfo tableInfo = beforeTable.toBuilder()
    .setDescription(newDescription)
    .build();
Table afterTable = bigquery.update(tableInfo);

Python

试用此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 Python 设置说明进行操作。如需了解详情,请参阅 BigQuery Python API 参考文档

配置 Table.description 属性并调用 Client.update_table() 向 API 发送更新。

# from google.cloud import bigquery
# client = bigquery.Client()
# table_ref = client.dataset('my_dataset').table('my_table')
# table = client.get_table(table_ref)  # API request

assert table.description == "Original description."
table.description = "Updated description."

table = client.update_table(table, ["description"])  # API request

assert table.description == "Updated description."

更新表的到期时间

您可以在数据集级层设置默认的表到期时间,也可以在创建表时设置表的到期时间。表的到期时间通常称为“存留时间”或 TTL。

如果在创建表时设置到期时间,则会忽略数据集的默认表到期时间。如果未在数据集级层设置默认的表到期时间,也未在创建表时设置表到期时间,则该表永不过期,您必须手动删除该表。

在创建表之后的任何时刻,您都可以通过以下方式更新表的到期时间:

  • 使用 GCP Console 或经典版 BigQuery 网页界面
  • 使用 DDL ALTER TABLE 语句
  • 使用 CLI 的 bq update 命令
  • 调用 tables.patch API 方法
  • 使用客户端库

要更新表的到期时间,请执行以下操作:

控制台

使用 GCP Console 创建表时,您无法添加到期时间。创建表后,您可以在表详细信息页面上添加或更新表到期时间。

  1. 资源窗格中,选择表。

  2. 查询编辑器下方,点击详细信息

  3. 点击表信息旁边的铅笔图标

  4. 表到期时间选择指定日期。然后使用下面的日历微件选择到期日期。

  5. 点击更新进行保存。已更新的到期时间会显示在表信息部分中。

DDL

借助数据定义语言 (DDL) 语句,您可以使用标准 SQL 查询语法创建和修改表和视图。

详细了解如何使用数据定义语言语句

要在 GCP Console 中使用 DDL 语句更新到期时间,请执行以下操作:

  1. 点击编写新查询

  2. 查询编辑器文本区域中,输入您的 DDL 语句。

     ALTER TABLE mydataset.mytable
     SET OPTIONS (
       -- Sets table expiration to timestamp 2025-02-03 12:34:56
       expiration_timestamp=TIMESTAMP "2025-02-03 12:34:56"
     )
     

  3. 点击运行

经典版界面

  1. 在导航窗格中,选择表。

  2. Table Details 页面上,点击 Details

  3. 对于 Expiration Time,点击 Edit

  4. Update Expiration 对话框中,点击 In,输入以天为单位的到期时间。

  5. 点击 OK。已更新的到期时间会显示在 Details 页面上。

    表到期时间

CLI

发出带 --expiration 标志的 bq update 命令。如果要更新非默认项目中的表,请使用以下格式将项目 ID 添加到数据集名称中:project_id:dataset

bq update \
--expiration integer \
project_id:dataset.table

其中:

  • integer 是表的默认生命周期(以秒为单位)。最小值为 3600 秒(一小时)。到期时间以当前时间加上这个整数值为准。如果您指定 0,表到期时间将被移除,且表永不过期。您必须手动删除未设定到期时间的表。
  • project_id 是项目 ID。
  • dataset 是含有您要更新表的数据集的名称。
  • table 是要更新的表的名称。

示例:

输入以下命令可将 mydatasetmytable 的到期时间更新为 5 天(432000 秒)。mydataset 在默认项目中。

bq update --expiration 432000 mydataset.mytable

输入以下命令可将 mydatasetmytable 的到期时间更新为 5 天(432000 秒)。mydatasetmyotherproject 中,不在默认项目中。

bq update --expiration 432000 myotherproject:mydataset.mytable

API

调用 tables.patch 方法并使用表资源中的 expirationTime 属性来更新表的到期时间(以毫秒为单位)。由于 tables.update 方法会替换整个表资源,因此最好使用 tables.patch 方法。

Go

试用此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 Go 设置说明进行操作。如需了解详情,请参阅 BigQuery Go API 参考文档

// To run this sample, you will need to create (or reuse) a context and
// an instance of the bigquery client.  For example:
// import "cloud.google.com/go/bigquery"
// ctx := context.Background()
// client, err := bigquery.NewClient(ctx, "your-project-id")
tableRef := client.Dataset(datasetID).Table(tableID)
meta, err := tableRef.Metadata(ctx)
if err != nil {
	return err
}
update := bigquery.TableMetadataToUpdate{
	ExpirationTime: time.Now().Add(time.Duration(5*24) * time.Hour), // table expiration in 5 days.
}
if _, err = tableRef.Update(ctx, update, meta.ETag); err != nil {
	return err
}

Java

试用此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 Java 设置说明进行操作。如需了解详情,请参阅 BigQuery Java API 参考文档

Table beforeTable = bigquery.getTable(datasetName, tableName);

// Set table to expire 5 days from now.
long expirationMillis = DateTime.now().plusDays(5).getMillis();
TableInfo tableInfo = beforeTable.toBuilder()
        .setExpirationTime(expirationMillis)
        .build();
Table afterTable = bigquery.update(tableInfo);

Python

试用此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 Python 设置说明进行操作。如需了解详情,请参阅 BigQuery Python API 参考文档

配置 Table.expires 属性并调用 Client.update_table() 向 API 发送更新。

import datetime
import pytz

# from google.cloud import bigquery
# client = bigquery.Client()
# table_ref = client.dataset('my_dataset').table('my_table')
# table = client.get_table(table_ref)  # API request

assert table.expires is None

# set table to expire 5 days from now
expiration = datetime.datetime.now(pytz.utc) + datetime.timedelta(days=5)
table.expires = expiration
table = client.update_table(table, ["expires"])  # API request

# expiration is stored in milliseconds
margin = datetime.timedelta(microseconds=1000)
assert expiration - margin <= table.expires <= expiration + margin

更新表的架构定义

如需了解更新表的架构定义的说明,请参阅修改表架构

重命名表

当前无法更改现有表的名称。如果需要更改表名称,请按照复制表的步骤进行操作。在复制操作中指定目标表时,请使用新的表名称。

复制表

您可以通过以下方式复制表:

  • 使用 GCP Console 或经典版 BigQuery 网页界面
  • 使用命令行工具的 bq cp 命令
  • 调用 jobs.insert API 方法并配置一个 copy 作业
  • 使用客户端库

所需权限

若要复制表和分区,您必须至少具有以下权限。

对于源数据集

  • bigquery.tables.get
  • bigquery.tables.getData

对于目标数据集

  • bigquery.tables.create:用于在目标数据集中创建表或分区的副本

以下预定义的 Cloud IAM 角色具有 bigquery.tables.createbigquery.tables.getbigquery.tables.getData 权限:

  • bigquery.dataEditor
  • bigquery.dataOwner
  • bigquery.admin

此外,若要运行复制作业,您必须具有 bigquery.jobs.create 权限。

以下预定义的 Cloud IAM 角色具有 bigquery.jobs.create 权限:

  • bigquery.user
  • bigquery.jobUser
  • bigquery.admin

此外,如果用户具有 bigquery.datasets.create 权限,则当该用户创建数据集时,系统会为其授予该数据集的 bigquery.dataOwner 访问权限。 具备 bigquery.dataOwner 访问权限的用户有权复制该数据集中的表和分区,但如果目标数据集并非由该用户创建,则用户还需要具备对目标数据集的访问权限。

如需详细了解 BigQuery 中的 Cloud IAM 角色和权限,请参阅访问权限控制

复制表的限制

表的复制作业受到以下限制:

  • 复制表时,目标表的名称必须遵循与创建表时相同的命名惯例。
  • 表的副本需遵循 BigQuery 的有关复制作业的配额政策
  • 使用 GCP Console 或经典版 BigQuery 网页界面复制表时,不能覆盖目标数据集中的现有表。该表必须在目标数据集中具有唯一名称。
  • 复制表时,目标数据集与包含所要复制表的源数据集必须位于同一位置。例如,您无法从欧盟的数据集复制表并将其写入美国境内的数据集。
  • GCP Console 或经典版 BigQuery 网页界面不支持将多个源表复制到目标表。
  • 使用 CLI 或 API 将多个源表复制到目标表时,所有源表必须具有相同架构。

复制单个源表

您可以通过以下方式复制单个表:

  • 使用 GCP Console 或经典版 BigQuery 网页界面
  • 使用命令行工具的 bq cp 命令
  • 调用 jobs.insert API 方法,配置一个 copy 作业并指定 sourceTable 属性
  • 使用客户端库

在 GCP Console 和经典版 BigQuery 网页界面,仅支持一个复制作业中有一个源表和一个目标表。要将多个源文件复制到目标表,必须使用命令行工具或 API。

要复制单个源表,请执行以下操作:

控制台

  1. 资源窗格中选择要复制的表。

  2. 查询编辑器下方,点击复制表

  3. 复制表对话框的目标下:

    • 项目名称部分,选择将存储复制表的项目。
    • 数据集名称部分,选择要存储复制表的数据集。源数据集和目标数据集必须在同一位置
    • 表名部分,输入新表的名称。该名称在目标数据集中必须唯一。表名称不得超过 1024 个字符,并且只能包含 a-z、A-Z、0-9 或 _(下划线字符)。您无法使用 GCP Console 覆盖目标数据集中的现有表。
  4. 点击复制以开始复制作业。

经典版界面

  1. 点击要复制的表旁边的 向下箭头 显示菜单图标,然后点击 Copy Table

  2. Copy Table 对话框中执行以下操作:

    • 对于 Destination project,选择将存储复制表的项目。
    • 对于 Destination dataset,选择要存储复制表的数据集。源数据集和目标数据集必须在同一位置。
    • 对于 Destination table,输入新表的名称。该名称在目标数据集中必须唯一。表名称不得超过 1024 个字符,并且只能包含 a-z、A-Z、0-9 或 _(下划线字符)。您不能使用经典版 BigQuery 网页界面覆盖目标数据集中的现有表。

      表的复制

  3. 点击 OK 以开始复制作业。

CLI

发出 bq cp 命令。可使用以下可选标志控制目标表的写入处置方式:

  • -a--append_table 用于将源表中的数据附加到目标数据集中的现有表。
  • -f--force 用于覆盖目标数据集中的现有表,并且不会提示您进行确认。
  • -n--no_clobber 会在目标数据集中已存在同名表时返回以下错误消息:Table 'project_id:dataset.table' already exists, skipping.。如果未指定 -n,则默认行为是提示您选择是否替换目标表。
  • --destination_kms_key 是客户管理的 Cloud KMS 密钥,用于加密目标表。

此处未演示 --destination_kms_key。如需了解详情,请参阅使用 Cloud Key Management Service 密钥保护数据

如果源数据集或目标数据集不在默认项目中,请使用以下格式将项目 ID 添加到数据集名称中:project_id:dataset

(可选)添加 --location 标志并将值设置为您的位置

bq --location=location cp \
-a -f -n \
project_id:dataset.source_table \
project_id:dataset.destination_table

其中:

  • [location] 是位置的名称。--location 是可选标志。例如,如果您在东京区域使用 BigQuery,可将该标志的值设置为 asia-northeast1。您可以使用 .bigqueryrc 文件设置位置的默认值。
  • project_id 是项目 ID。
  • dataset 是源数据集或目标数据集的名称。
  • source_table 是要复制的表。
  • destination_table 是目标数据集中表的名称。

示例:

输入以下命令可将 mydataset.mytable 复制到 mydataset2.mytable2。两个数据集都在默认项目中。

bq cp mydataset.mytable mydataset2.mytable2

输入以下命令可复制 mydataset.mytable 并覆盖具有相同名称的目标表。源数据集在默认项目中。目标数据集在 myotherproject 中。-f 快捷键用于在无提示的情况下覆盖目标表。

bq cp -f \
mydataset.mytable \
myotherproject:myotherdataset.mytable

输入以下命令可复制 mydataset.mytable 并会在目标数据集中包含同名表时返回错误。源数据集在默认项目中。目标数据集在 myotherproject 中。-n 快捷键用于防止覆盖具有相同名称的表。

bq cp -n \
mydataset.mytable \
myotherproject:myotherdataset.mytable

输入以下命令可复制 mydataset.mytable 并向具有相同名称的目标表附加数据。源数据集在默认项目中。目标数据集在 myotherproject 中。- a 快捷键用于附加到目标表。

bq cp -a mydataset.mytable myotherproject:myotherdataset.mytable

API

若要通过 API 复制现有的表,您可以调用 bigquery.jobs.insert 方法并配置一个 copy 作业。在作业资源jobReference 部分的 location 属性中,指定您的位置。

您必须在作业配置中指定以下值:

"copy": {
      "sourceTable": {       // Required
        "projectId": string, // Required
        "datasetId": string, // Required
        "tableId": string    // Required
      },
      "destinationTable": {  // Required
        "projectId": string, // Required
        "datasetId": string, // Required
        "tableId": string    // Required
      },
      "createDisposition": string,  // Optional
      "writeDisposition": string,   // Optional
    },

其中,sourceTable 提供要复制的表的相关信息,destinationTable 提供新表的相关信息,createDisposition 指定是否在表不存在时创建表,writeDisposition 指定是覆盖还是附加到现有的表。

C#

试用此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 C# 设置说明进行操作。如需了解详情,请参阅 BigQuery C# API 参考文档


using Google.Apis.Bigquery.v2.Data;
using Google.Cloud.BigQuery.V2;
using System;

public class BigQueryCopyTable
{
    public void CopyTable(
        string projectId = "your-project-id",
        string destinationDatasetId = "your_dataset_id"
    )
    {
        BigQueryClient client = BigQueryClient.Create(projectId);
        TableReference sourceTableRef = new TableReference()
        {
            TableId = "shakespeare",
            DatasetId = "samples",
            ProjectId = "bigquery-public-data"
        };
        TableReference destinationTableRef = client.GetTableReference(
            destinationDatasetId, "destination_table");
        BigQueryJob job = client.CreateCopyJob(
            sourceTableRef, destinationTableRef)
            .PollUntilCompleted();  // Wait for the job to complete.
        // Retrieve destination table
        BigQueryTable destinationTable = client.GetTable(destinationTableRef);
        Console.WriteLine(
            $"Copied {destinationTable.Resource.NumRows} rows from table "
            + $"{sourceTableRef.DatasetId}.{sourceTableRef.TableId} "
            + $"to {destinationTable.FullyQualifiedId}."
        );
    }
}

Go

试用此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 Go 设置说明进行操作。如需了解详情,请参阅 BigQuery Go API 参考文档

// To run this sample, you will need to create (or reuse) a context and
// an instance of the bigquery client.  For example:
// import "cloud.google.com/go/bigquery"
// ctx := context.Background()
// client, err := bigquery.NewClient(ctx, "your-project-id")
dataset := client.Dataset(datasetID)
copier := dataset.Table(dstID).CopierFrom(dataset.Table(srcID))
copier.WriteDisposition = bigquery.WriteTruncate
job, err := copier.Run(ctx)
if err != nil {
	return err
}
status, err := job.Wait(ctx)
if err != nil {
	return err
}
if err := status.Err(); err != nil {
	return err
}

Java

试用此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 Java 设置说明进行操作。如需了解详情,请参阅 BigQuery Java API 参考文档

TableId destinationId = TableId.of(dataset, tableName);
JobOption options = JobOption.fields(JobField.STATUS, JobField.USER_EMAIL);
Job job = table.copy(destinationId, options);
// Wait for the job to complete.
try {
  Job completedJob =
      job.waitFor(
          RetryOption.initialRetryDelay(Duration.ofSeconds(1)),
          RetryOption.totalTimeout(Duration.ofMinutes(3)));
  if (completedJob != null && completedJob.getStatus().getError() == null) {
    // Job completed successfully.
  } else {
    // Handle error case.
  }
} catch (InterruptedException e) {
  // Handle interrupted wait
}

Node.js

试用此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 Node.js 设置说明进行操作。如需了解详情,请参阅 BigQuery Node.js API 参考文档

// Import the Google Cloud client library and create a client
const {BigQuery} = require('@google-cloud/bigquery');
const bigquery = new BigQuery();

async function copyTable() {
  // Copies src_dataset:src_table to dest_dataset:dest_table.

  /**
   * TODO(developer): Uncomment the following lines before running the sample
   */
  // const srcDatasetId = "my_src_dataset";
  // const srcTableId = "my_src_table";
  // const destDatasetId = "my_dest_dataset";
  // const destTableId = "my_dest_table";

  // Copy the table contents into another table
  const [job] = await bigquery
    .dataset(srcDatasetId)
    .table(srcTableId)
    .copy(bigquery.dataset(destDatasetId).table(destTableId));

  console.log(`Job ${job.id} completed.`);

  // Check the job's status for errors
  const errors = job.status.errors;
  if (errors && errors.length > 0) {
    throw errors;
  }
}

PHP

试用此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 PHP 设置说明进行操作。如需了解详情,请参阅 BigQuery PHP API 参考文档

use Google\Cloud\BigQuery\BigQueryClient;
use Google\Cloud\Core\ExponentialBackoff;

/** Uncomment and populate these variables in your code */
// $projectId = 'The Google project ID';
// $datasetId = 'The BigQuery dataset ID';
// $sourceTableId   = 'The BigQuery table ID to copy from';
// $destinationTableId = 'The BigQuery table ID to copy to';

$bigQuery = new BigQueryClient([
    'projectId' => $projectId,
]);
$dataset = $bigQuery->dataset($datasetId);
$sourceTable = $dataset->table($sourceTableId);
$destinationTable = $dataset->table($destinationTableId);
$copyConfig = $sourceTable->copy($destinationTable);
$job = $sourceTable->runJob($copyConfig);

// poll the job until it is complete
$backoff = new ExponentialBackoff(10);
$backoff->execute(function () use ($job) {
    print('Waiting for job to complete' . PHP_EOL);
    $job->reload();
    if (!$job->isComplete()) {
        throw new Exception('Job has not yet completed', 500);
    }
});
// check if the job has errors
if (isset($job->info()['status']['errorResult'])) {
    $error = $job->info()['status']['errorResult']['message'];
    printf('Error running job: %s' . PHP_EOL, $error);
} else {
    print('Table copied successfully' . PHP_EOL);
}

Python

试用此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 Python 设置说明进行操作。如需了解详情,请参阅 BigQuery Python API 参考文档

# from google.cloud import bigquery
# client = bigquery.Client()

source_dataset = client.dataset("samples", project="bigquery-public-data")
source_table_ref = source_dataset.table("shakespeare")

# dataset_id = 'my_dataset'
dest_table_ref = client.dataset(dataset_id).table("destination_table")

job = client.copy_table(
    source_table_ref,
    dest_table_ref,
    # Location must match that of the source and destination tables.
    location="US",
)  # API request

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

assert job.state == "DONE"
dest_table = client.get_table(dest_table_ref)  # API request
assert dest_table.num_rows > 0

复制多个源表

您可以通过以下方式将多个源表复制到一个目标表:

  • 使用命令行工具的 bq cp 命令
  • 调用 jobs.insert 方法,配置一个 copy 作业并指定 sourceTables 属性
  • 使用客户端库

所有源表必须具有相同架构,并且只能有一个目标表。

在指定源表时,您必须采用以英文逗号分隔的列表的形式。在复制多个源表时,您不能使用通配符。

要复制多个源表,请执行以下操作:

控制台

目前,GCP Console 不支持复制多个表。

经典版界面

目前,经典版 BigQuery 网页界面不支持复制多个表。

CLI

发出 bq cp 命令并包含多个源表,中间用英文逗号分隔。可使用以下可选标志控制目标表的写入处置方式:

  • -a--append_table 用于将源表中的数据附加到目标数据集中的现有表。
  • -f--force 用于覆盖目标数据集中的现有目标表,并且不会提示您进行确认。
  • -n--no_clobber 会在目标数据集中已存在同名表时返回以下错误消息:Table 'project_id:dataset.table' already exists, skipping.。 如果未指定 -n,则默认行为是提示您选择是否替换目标表。
  • --destination_kms_key 是客户管理的 Cloud Key Management Service 密钥,用于加密目标表。

此处未演示 --destination_kms_key。如需了解详情,请参阅使用 Cloud Key Management Service 密钥保护数据

如果源数据集或目标数据集不在默认项目中,请使用以下格式将项目 ID 添加到数据集名称中:project_id:dataset

(可选)添加 --location 标志并将值设置为您的位置

bq --location=location cp \
-a -f -n \
project_id:dataset.source_table,project_id:dataset.source_table \
project_id:dataset.destination_table

其中:

  • [location] 是位置的名称。--location 是可选标志。例如,如果您在东京区域使用 BigQuery,可将该标志的值设置为 asia-northeast1。您可以使用 .bigqueryrc 文件设置位置的默认值。
  • project_id 是项目 ID。
  • dataset 是源数据集或目标数据集的名称。
  • source_table 是要复制的表。
  • destination_table 是目标数据集中表的名称。

示例:

输入以下命令可将 mydataset.mytablemydataset.mytable2 复制到 mydataset2.tablecopy。两个数据集都在默认项目中。

bq cp \
mydataset.mytable,mydataset.mytable2 \
mydataset2.tablecopy

输入以下命令可将 mydataset.mytablemydataset.mytable2 复制到 myotherdataset.mytable,并覆盖具有相同名称的目标表。目标数据集在 myotherproject 中,不在默认项目中。-f 快捷键用于在无提示的情况下覆盖目标表。

bq cp -f \
mydataset.mytable,mydataset.mytable2 \
myotherproject:myotherdataset.mytable

输入以下命令可复制 myproject:mydataset.mytablemyproject:mydataset.mytable2 并会在目标数据集中包含同名表时返回错误。目标数据集在 myotherproject 中。-n 快捷键用于防止覆盖具有相同名称的表。

bq cp -n \
myproject:mydataset.mytable,myproject:mydataset.mytable2 \
myotherproject:myotherdataset.mytable

输入以下命令可复制 mydataset.mytablemydataset.mytable2 并向具有相同名称的目标表附加数据。源数据集在默认项目中。目标数据集在 myotherproject 中。-a 快捷键用于附加到目标表。

bq cp -a \
mydataset.mytable,mydataset.mytable2 \
myotherproject:myotherdataset.mytable

API

若要使用 API 复制多个表,请调用 jobs.insert 方法,配置一个表 copy 作业,并指定 sourceTables 属性。

作业资源jobReference 部分的 location 属性中,指定您的区域。

Go

试用此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 Go 设置说明进行操作。如需了解详情,请参阅 BigQuery Go API 参考文档

// To run this sample, you will need to create (or reuse) a context and
// an instance of the bigquery client.  For example:
// import "cloud.google.com/go/bigquery"
// ctx := context.Background()
// client, err := bigquery.NewClient(ctx, "your-project-id")
dataset := client.Dataset(datasetID)

srcTableIDs := []string{"table1", "table2"}
var tableRefs []*bigquery.Table
for _, v := range srcTableIDs {
	tableRefs = append(tableRefs, dataset.Table(v))
}
copier := dataset.Table(dstTableID).CopierFrom(tableRefs...)
copier.WriteDisposition = bigquery.WriteTruncate
job, err := copier.Run(ctx)
if err != nil {
	return err
}
status, err := job.Wait(ctx)
if err != nil {
	return err
}
if err := status.Err(); err != nil {
	return err
}

Java

试用此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 Java 设置说明进行操作。如需了解详情,请参阅 BigQuery Java API 参考文档

TableId destinationTable = TableId.of(datasetId, destinationTableId);
CopyJobConfiguration configuration =
    CopyJobConfiguration.newBuilder(
        destinationTable,
        Arrays.asList(
            TableId.of(datasetId, "table1"),
            TableId.of(datasetId, "table2")))
    .build();

// Copy the tables.
Job job = bigquery.create(JobInfo.of(configuration));
job = job.waitFor();

// Check the table
StandardTableDefinition table = bigquery.getTable(destinationTable).getDefinition();
System.out.println("State: " + job.getStatus().getState());
System.out.printf("Copied %d rows.\n", table.getNumRows());

Python

试用此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 Python 设置说明进行操作。如需了解详情,请参阅 BigQuery Python API 参考文档

# from google.cloud import bigquery
# client = bigquery.Client()
# source_dataset_id = 'my_source_dataset'
# dest_dataset_id = 'my_destination_dataset'

table1_ref = client.dataset(source_dataset_id).table("table1")
table2_ref = client.dataset(source_dataset_id).table("table2")
dest_table_ref = client.dataset(dest_dataset_id).table("destination_table")

job = client.copy_table(
    [table1_ref, table2_ref],
    dest_table_ref,
    # Location must match that of the source and destination tables.
    location="US",
)  # API request
job.result()  # Waits for job to complete.

assert job.state == "DONE"
dest_table = client.get_table(dest_table_ref)  # API request
assert dest_table.num_rows > 0

删除表

您可以通过以下方式删除表:

  • 使用 GCP Console 或经典版 BigQuery 网页界面
  • 使用命令行工具的 bq rm 命令
  • 调用 tables.delete API 方法
  • 使用客户端库

目前,您每次只能删除一个表。

删除表时,该表中的所有数据也将一并删除。若要在指定的时间段后自动删除表,请设置数据集的默认表到期时间,或在创建表时设置到期时间。

所需权限

若要删除表,您必须至少具有 bigquery.tables.deletebigquery.tables.get 权限。以下预定义的 Cloud IAM 角色具有 bigquery.tables.deletebigquery.tables.get 权限:

  • bigquery.dataOwner
  • bigquery.dataEditor
  • bigquery.admin

此外,如果用户具有 bigquery.datasets.create 权限,则当该用户创建数据集时,系统会为其授予该数据集的 bigquery.dataOwner 访问权限。 具备 bigquery.dataOwner 访问权限的用户有权在数据集中删除表。

如需详细了解 BigQuery 中的 Cloud IAM 角色和权限,请参阅访问权限控制

删除表

要删除表,请执行以下操作:

控制台

  1. 资源窗格中选择表。在查询编辑器下方,点击删除表

  2. 在对话框中键入表的名称,然后点击删除进行确认。

经典版界面

  1. 在导航栏中,点击表名称旁边的向下箭头图标 向下箭头图标,然后点击 Delete table

  2. 出现提示时,点击 OK 以确认删除。

CLI

使用带有 --table 标志(或 -t 快捷键)的 bq rm 命令删除表。使用 CLI 移除表时,必须确认该操作。您可以使用 --force 标志(或 -f 快捷方式)跳过确认。

如果该表不在默认项目的数据集中,请使用以下格式将项目 ID 添加到数据集名称中:project_id:dataset

bq rm \
-f \
-t \
project_id:dataset.table

其中:

  • project_id 是项目 ID。
  • dataset 是包含该表的数据集的名称。
  • table 是要删除的表的名称。

示例:

输入以下命令可从 mydataset 删除 mytablemydataset 在默认项目中。

bq rm -t mydataset.mytable

输入以下命令可从 mydataset 删除 mytablemydatasetmyotherproject 中,不在默认项目中。

bq rm -t myotherproject:mydataset.mytable

输入以下命令可从 mydataset 删除 mytablemydataset 在默认项目中。该命令使用 -f 快捷键绕过确认。

bq rm -f -t mydataset.mytable

API

调用 tables.delete API 方法并使用 tableId 参数指定要删除的表。

C#

试用此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 C# 设置说明进行操作。如需了解详情,请参阅 BigQuery C# API 参考文档


using Google.Cloud.BigQuery.V2;
using System;

public class BigQueryDeleteTable
{
    public void DeleteTable(
        string projectId = "your-project-id",
        string datasetId = "your_dataset_id",
        string tableId = "your_table_id"
    )
    {
        BigQueryClient client = BigQueryClient.Create(projectId);
        client.DeleteTable(datasetId, tableId);
        Console.WriteLine($"Table {tableId} deleted.");
    }
}

Go

试用此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 Go 设置说明进行操作。如需了解详情,请参阅 BigQuery Go API 参考文档

// To run this sample, you will need to create (or reuse) a context and
// an instance of the bigquery client.  For example:
// import "cloud.google.com/go/bigquery"
// ctx := context.Background()
// client, err := bigquery.NewClient(ctx, "your-project-id")
table := client.Dataset(datasetID).Table(tableID)
if err := table.Delete(ctx); err != nil {
	return err
}

Java

试用此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 Java 设置说明进行操作。如需了解详情,请参阅 BigQuery Java API 参考文档

TableId tableId = TableId.of(projectId, datasetName, tableName);
boolean deleted = bigquery.delete(tableId);
if (deleted) {
  // the table was deleted
} else {
  // the table was not found
}

Node.js

试用此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 Node.js 设置说明进行操作。如需了解详情,请参阅 BigQuery Node.js API 参考文档

// Import the Google Cloud client library
const {BigQuery} = require('@google-cloud/bigquery');
const bigquery = new BigQuery();

async function deleteTable() {
  // Deletes "my_table" from "my_dataset".

  /**
   * TODO(developer): Uncomment the following lines before running the sample.
   */
  // const datasetId = "my_dataset";
  // const tableId = "my_table";

  // Delete the table
  await bigquery
    .dataset(datasetId)
    .table(tableId)
    .delete();

  console.log(`Table ${tableId} deleted.`);
}

PHP

试用此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 PHP 设置说明进行操作。如需了解详情,请参阅 BigQuery PHP API 参考文档

use Google\Cloud\BigQuery\BigQueryClient;

/** Uncomment and populate these variables in your code */
// $projectId = 'The Google project ID';
// $datasetId = 'The BigQuery dataset ID';
// $tableId = 'The BigQuery table ID';

$bigQuery = new BigQueryClient([
    'projectId' => $projectId,
]);
$dataset = $bigQuery->dataset($datasetId);
$table = $dataset->table($tableId);
$table->delete();
printf('Deleted table %s.%s' . PHP_EOL, $datasetId, $tableId);

Python

试用此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 Python 设置说明进行操作。如需了解详情,请参阅 BigQuery Python API 参考文档

from google.cloud import bigquery

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

# TODO(developer): Set table_id to the ID of the table to fetch.
# table_id = 'your-project.your_dataset.your_table'

# If the table does not exist, delete_table raises
# google.api_core.exceptions.NotFound unless not_found_ok is True
client.delete_table(table_id, not_found_ok=True)
print("Deleted table '{}'.".format(table_id))

Ruby

试用此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 Ruby 设置说明进行操作。如需了解详情,请参阅 BigQuery Ruby API 参考文档

require "google/cloud/bigquery"

def delete_table dataset_id = "my_dataset_id", table_id = "my_table_id"
  bigquery = Google::Cloud::Bigquery.new
  dataset  = bigquery.dataset dataset_id
  table    = dataset.table table_id

  table.delete

  puts "Table #{table_id} deleted."
end

恢复已删除的表

表在删除后的 2 天内可恢复。利用快照修饰器功能,您可以引用删除事件发生之前的表,然后复制这个表。注意事项:

  • 一旦您在同一数据集中创建同名新表,便无法再引用已删除的表。

  • 如果您将已删除表所在的数据集也一并删除,并且创建了同名的新数据集,则无法再引用已删除的表。

恢复已删除的表

您可以通过以下方式恢复已删除的表:

  • 在 CLI 中使用 @<time> 快照修饰器
  • 使用客户端库

控制台

您无法使用 GCP Console 恢复删除的表。

经典版界面

您无法使用经典版网页界面恢复删除的表。

CLI

要使用旧版 SQL 恢复删除的表,请使用 @<time> 快照修饰器。首先,确定指明表存在时间的 UNIX 时间戳(以毫秒为单位)。然后,将该时间戳的表复制到新表。新表不得采用已删除表的名称。

(可选)添加 --location 标志并将值设置为您的位置

例如,输入以下命令可将时间为 1418864998000mydataset.mytable 复制到新表 mydataset.newtable

bq cp mydataset.mytable@1418864998000 mydataset.newtable

如需了解详情,请参阅旧版 SQL 中的表修饰器

Go

// To run this sample, you will need to create (or reuse) a context and
// an instance of the bigquery client.  For example:
// import "cloud.google.com/go/bigquery"
// ctx := context.Background()
// client, err := bigquery.NewClient(ctx, "your-project-id")

ds := client.Dataset(datasetID)
if _, err := ds.Table(tableID).Metadata(ctx); err != nil {
	return err
}
// Record the current time.  We'll use this as the snapshot time
// for recovering the table.
snapTime := time.Now()

// "Accidentally" delete the table.
if err := client.Dataset(datasetID).Table(tableID).Delete(ctx); err != nil {
	return err
}

// Construct the restore-from tableID using a snapshot decorator.
snapshotTableID := fmt.Sprintf("%s@%d", tableID, snapTime.UnixNano()/1e6)
// Choose a new table ID for the recovered table data.
recoverTableID := fmt.Sprintf("%s_recovered", tableID)

// Construct and run a copy job.
copier := ds.Table(recoverTableID).CopierFrom(ds.Table(snapshotTableID))
copier.WriteDisposition = bigquery.WriteTruncate
job, err := copier.Run(ctx)
if err != nil {
	return err
}
status, err := job.Wait(ctx)
if err != nil {
	return err
}
if err := status.Err(); err != nil {
	return err
}

Java

试用此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 Java 设置说明进行操作。如需了解详情,请参阅 BigQuery Java API 参考文档

// String datasetId = "my_dataset";
String tableId = "oops_undelete_me";

// Record the current time.  We'll use this as the snapshot time
// for recovering the table.
long snapTime = Instant.now().getMillis();

// "Accidentally" delete the table.
bigquery.delete(TableId.of(datasetId, tableId));

// Construct the restore-from tableID using a snapshot decorator.
String snapshotTableId = String.format("%s@%d", tableId, snapTime);
// Choose a new table ID for the recovered table data.
String recoverTableId = String.format("%s_recovered", tableId);

// Construct and run a copy job.
CopyJobConfiguration configuration =
    CopyJobConfiguration.newBuilder(
        TableId.of(datasetId, recoverTableId),
        TableId.of(datasetId, snapshotTableId))
    .build();
Job job = bigquery.create(JobInfo.of(configuration));
job = job.waitFor();

// Check the table
StandardTableDefinition table = bigquery.getTable(
        TableId.of(datasetId, recoverTableId)).getDefinition();
System.out.println("State: " + job.getStatus().getState());
System.out.printf("Recovered %d rows.\n", table.getNumRows());

Python

试用此示例之前,请按照《BigQuery 快速入门:使用客户端库》中的 Python 设置说明进行操作。如需了解详情,请参阅 BigQuery Python API 参考文档

# TODO(developer): Uncomment the lines below and replace with your values.
# import time
# from google.cloud import bigquery
# client = bigquery.Client()
# dataset_id = 'my_dataset'  # Replace with your dataset ID.
# table_id = 'my_table'      # Replace with your table ID.

table_ref = client.dataset(dataset_id).table(table_id)

# TODO(developer): Choose an appropriate snapshot point as epoch
# milliseconds. For this example, we choose the current time as we're about
# to delete the table immediately afterwards.
snapshot_epoch = int(time.time() * 1000)

# "Accidentally" delete the table.
client.delete_table(table_ref)  # API request

# Construct the restore-from table ID using a snapshot decorator.
snapshot_table_id = "{}@{}".format(table_id, snapshot_epoch)
source_table_ref = client.dataset(dataset_id).table(snapshot_table_id)

# Choose a new table ID for the recovered table data.
recovered_table_id = "{}_recovered".format(table_id)
dest_table_ref = client.dataset(dataset_id).table(recovered_table_id)

# Construct and run a copy job.
job = client.copy_table(
    source_table_ref,
    dest_table_ref,
    # Location must match that of the source and destination tables.
    location="US",
)  # API request

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

print(
    "Copied data from deleted table {} to {}".format(table_id, recovered_table_id)
)

后续步骤

此页内容是否有用?请给出您的反馈和评价:

发送以下问题的反馈:

此网页
需要帮助?请访问我们的支持页面