删除

本文档介绍了如何删除 Bigtable 表中存储的数据,讨论了每种方法的适用情形,并提供了示例。在阅读本页内容之前,您应该先熟悉 Bigtable 概览并了解架构设计中涉及的概念。

为保持一致性,本页面上的说明是指每种请求中使用的 API 方法。但是,我们强烈建议您始终使用其中一个 Bigtable 客户端库来访问 Bigtable API,而不是使用 REST 或 RPC。

本页面上的示例使用示例数据,这些数据类似于您可能存储在 Bigtable 中的数据。

如需了解您每天可以使用此页面中描述的操作的次数,请参阅配额和限制

Bigtable 如何删除数据

发送删除请求时,单元会标记为删除且无法读取。数据会在一周后的压缩过程中移除,此过程会持续优化表。发送删除请求后的几天,删除元数据可能会导致数据略微占用更多空间(每行几 KB),直到下一次压缩为止。

即使您的集群超出存储空间上限并且读写操作被阻止,您也可以始终发送删除请求。

删除一系列行

如果要删除存储在连续行中的大量数据,请使用 dropRowRange。此操作会删除由起始行和结束行或行键前缀标识的一系列行中的所有行。

您在删除一系列行时提供的行键值将被视为服务数据。如需了解服务数据的处理方式,请参阅 Google Cloud 隐私权声明

成功删除完成并收到响应后,您可以安全地将数据写入同一行范围。

dropRowRange 操作具有以下限制:

  • 您无法从已获授权的视图中删除某个范围内的行。
  • 您不能异步调用 dropRowRange 方法。如果您在其他请求正在进行时向表发送 dropRowRange 请求,Bigtable 会返回 UNAVAILABLE 错误并显示消息 A DropRowRange operation is already ongoing。如需解决此错误,请再次发送请求。
  • 请注意,对于使用了复制功能的实例,由于复制延迟时间增加和 CPU 使用率增加,Bigtable 可能需要很长时间才能完成操作。要从使用复制功能的实例中删除数据,请使用 Data API 读取并删除数据

以下代码示例展示了如何删除以行键前缀 phone#5c10102 开头的一系列行:

Java

如需了解如何安装和使用 Bigtable 客户端库,请参阅 Bigtable 客户端库

如需向 Bigtable 进行身份验证,请设置应用默认凭据。 如需了解详情,请参阅为客户端库设置身份验证

import com.google.cloud.bigtable.admin.v2.BigtableTableAdminClient;
import java.io.IOException;

public class DropRowRangeExample {
  public void dropRowRange(String projectId, String instanceId, String tableId) throws IOException {
    try (BigtableTableAdminClient tableAdminClient =
        BigtableTableAdminClient.create(projectId, instanceId)) {
      tableAdminClient.dropRowRange(tableId, "phone#4c410523");
    }
  }
}

Python

如需了解如何安装和使用 Bigtable 客户端库,请参阅 Bigtable 客户端库

如需向 Bigtable 进行身份验证,请设置应用默认凭据。 如需了解详情,请参阅为客户端库设置身份验证

def drop_row_range(project_id, instance_id, table_id):
    client = bigtable.Client(project=project_id, admin=True)
    instance = client.instance(instance_id)
    table = instance.table(table_id)
    row_key_prefix = "phone#4c410523"
    table.drop_by_prefix(row_key_prefix, timeout=200)

Node.js

如需了解如何安装和使用 Bigtable 客户端库,请参阅 Bigtable 客户端库

如需向 Bigtable 进行身份验证,请设置应用默认凭据。 如需了解详情,请参阅为客户端库设置身份验证

await table.deleteRows('phone#5c10102');
await printRows();

使用 Data API 方法删除数据

如果您需要删除少量不连续的数据,通常理想的选择是使用调用 Cloud Bigtable API (Data API) 的方法删除数据。如果您要在请求中删除 MB(而不是 GB)数据,请使用这些方法。使用 Data API 是从列(而不是列族)中删除数据的唯一方法。

Data API 方法使用以下三种变更类型之一调用 MutateRows

  • DeleteFromColumn
  • DeleteFromFamily
  • DeleteFromRow

使用 Data API 的删除请求是原子化请求:请求成功并且所有数据都会被删除,或者请求失败且未移除任何数据。

在大多数情况下,请避免使用 CheckAndMutate 方法删除数据。在极少数情况下,如果您需要强一致性,可能需要使用此方法,但请注意,这会占用大量资源,且性能可能会受到影响。

如需使用 MutateRows 删除数据,您需要发送带有过滤条件的 readRows 请求,以确定要删除的数据,然后发送删除请求。如需查看可用的过滤条件列表,请参阅过滤条件

本部分中的示例假设您已经确定要删除的数据

从列中删除

以下代码示例演示了如何删除一行中某列的所有单元:

Java

如需了解如何安装和使用 Bigtable 客户端库,请参阅 Bigtable 客户端库

如需向 Bigtable 进行身份验证,请设置应用默认凭据。 如需了解详情,请参阅为客户端库设置身份验证

import com.google.cloud.bigtable.data.v2.BigtableDataClient;
import com.google.cloud.bigtable.data.v2.models.Mutation;
import com.google.cloud.bigtable.data.v2.models.RowMutation;
import com.google.cloud.bigtable.data.v2.models.TableId;
import java.io.IOException;

public class DeleteFromColumnExample {
  public void deleteFromColumnCells(String projectId, String instanceId, String tableId)
      throws IOException {
    try (BigtableDataClient dataClient = BigtableDataClient.create(projectId, instanceId)) {
      Mutation mutation = Mutation.create().deleteCells("cell_plan", "data_plan_01gb");
      dataClient.mutateRow(
          RowMutation.create(TableId.of(tableId), "phone#4c410523#20190501", mutation));
    }
  }
}

Python

如需了解如何安装和使用 Bigtable 客户端库,请参阅 Bigtable 客户端库

如需向 Bigtable 进行身份验证,请设置应用默认凭据。 如需了解详情,请参阅为客户端库设置身份验证

def delete_from_column(project_id, instance_id, table_id):
    client = bigtable.Client(project=project_id, admin=True)
    instance = client.instance(instance_id)
    table = instance.table(table_id)
    row = table.row("phone#4c410523#20190501")
    row.delete_cell(column_family_id="cell_plan", column="data_plan_01gb")
    row.commit()

Node.js

如需了解如何安装和使用 Bigtable 客户端库,请参阅 Bigtable 客户端库

如需向 Bigtable 进行身份验证,请设置应用默认凭据。 如需了解详情,请参阅为客户端库设置身份验证

await table.mutate({
  key: 'phone#4c410523#20190501',
  method: 'delete',
  data: {
    column: 'cell_plan:data_plan_05gb',
  },
});
await printRows();

从列族中删除

以下代码示例演示了如何删除行中的列族中的单元:

Java

如需了解如何安装和使用 Bigtable 客户端库,请参阅 Bigtable 客户端库

如需向 Bigtable 进行身份验证,请设置应用默认凭据。 如需了解详情,请参阅为客户端库设置身份验证

import com.google.cloud.bigtable.data.v2.BigtableDataClient;
import com.google.cloud.bigtable.data.v2.models.RowMutation;
import com.google.cloud.bigtable.data.v2.models.TableId;
import java.io.IOException;

public class DeleteFromColumnFamilyExample {
  public void deleteFromColumnFamily(String projectId, String instanceId, String tableId)
      throws IOException {
    try (BigtableDataClient dataClient = BigtableDataClient.create(projectId, instanceId)) {
      dataClient.mutateRow(
          RowMutation.create(TableId.of(tableId), "phone#5c10102#20190501")
              .deleteFamily("stats_summary"));
    }
  }
}

Python

如需了解如何安装和使用 Bigtable 客户端库,请参阅 Bigtable 客户端库

如需向 Bigtable 进行身份验证,请设置应用默认凭据。 如需了解详情,请参阅为客户端库设置身份验证

def delete_from_column_family(project_id, instance_id, table_id):
    client = bigtable.Client(project=project_id, admin=True)
    instance = client.instance(instance_id)
    table = instance.table(table_id)
    row = table.row("phone#4c410523#20190501")
    row.delete_cells(column_family_id="cell_plan", columns=row.ALL_COLUMNS)
    row.commit()

Node.js

如需了解如何安装和使用 Bigtable 客户端库,请参阅 Bigtable 客户端库

如需向 Bigtable 进行身份验证,请设置应用默认凭据。 如需了解详情,请参阅为客户端库设置身份验证

await table.mutate({
  key: 'phone#4c410523#20190501',
  method: 'delete',
  data: {
    column: 'cell_plan',
  },
});
await printRows();

从行中删除

以下代码段演示了如何删除一行中的所有单元格:

Java

如需了解如何安装和使用 Bigtable 客户端库,请参阅 Bigtable 客户端库

如需向 Bigtable 进行身份验证,请设置应用默认凭据。 如需了解详情,请参阅为客户端库设置身份验证

import com.google.cloud.bigtable.data.v2.BigtableDataClient;
import com.google.cloud.bigtable.data.v2.models.Mutation;
import com.google.cloud.bigtable.data.v2.models.RowMutation;
import com.google.cloud.bigtable.data.v2.models.TableId;
import java.io.IOException;

public class DeleteFromRowExample {
  public void deleteFromRow(String projectId, String instanceId, String tableId)
      throws IOException {
    try (BigtableDataClient dataClient = BigtableDataClient.create(projectId, instanceId)) {
      Mutation mutation = Mutation.create().deleteRow();
      dataClient.mutateRow(
          RowMutation.create(TableId.of(tableId), "phone#4c410523#20190501", mutation));
    }
  }
}

Python

如需了解如何安装和使用 Bigtable 客户端库,请参阅 Bigtable 客户端库

如需向 Bigtable 进行身份验证,请设置应用默认凭据。 如需了解详情,请参阅为客户端库设置身份验证

def delete_from_row(project_id, instance_id, table_id):
    client = bigtable.Client(project=project_id, admin=True)
    instance = client.instance(instance_id)
    table = instance.table(table_id)
    row = table.row("phone#4c410523#20190501")
    row.delete()
    row.commit()

Node.js

如需了解如何安装和使用 Bigtable 客户端库,请参阅 Bigtable 客户端库

如需向 Bigtable 进行身份验证,请设置应用默认凭据。 如需了解详情,请参阅为客户端库设置身份验证

const row = table.row('phone#4c410523#20190501');
await row.delete();
await printRows();

通过流式处理和批量删除

流式处理和批量删除请求通常是删除大量数据的最佳方式。如果您拥有比垃圾回收政策更精细的数据保留要求,则此策略非常有用。

以下代码段启动数据流(读取行),批量处理这些行,然后完成批量处理并删除 cell_plan 列族中 data_plan_01gb1 列中的所有单元格:

Java

如需了解如何安装和使用 Bigtable 客户端库,请参阅 Bigtable 客户端库

如需向 Bigtable 进行身份验证,请设置应用默认凭据。 如需了解详情,请参阅为客户端库设置身份验证

import com.google.api.gax.batching.Batcher;
import com.google.api.gax.rpc.ServerStream;
import com.google.cloud.bigtable.data.v2.BigtableDataClient;
import com.google.cloud.bigtable.data.v2.models.Query;
import com.google.cloud.bigtable.data.v2.models.Row;
import com.google.cloud.bigtable.data.v2.models.RowMutationEntry;
import com.google.cloud.bigtable.data.v2.models.TableId;
import java.io.IOException;

public class BatchDeleteExample {
  public void batchDelete(String projectId, String instanceId, String tableId)
      throws InterruptedException, IOException {
    try (BigtableDataClient dataClient = BigtableDataClient.create(projectId, instanceId)) {
      try (Batcher<RowMutationEntry, Void> batcher =
          dataClient.newBulkMutationBatcher(TableId.of(tableId))) {
        ServerStream<Row> rows = dataClient.readRows(Query.create(TableId.of(tableId)));
        for (Row row : rows) {
          batcher.add(
              RowMutationEntry.create(row.getKey()).deleteCells("cell_plan", "data_plan_05gb"));
        }
        // Blocks until mutations are applied on all submitted row entries.
        batcher.flush();
      }
    }
  }
}

Python

如需了解如何安装和使用 Bigtable 客户端库,请参阅 Bigtable 客户端库

如需向 Bigtable 进行身份验证,请设置应用默认凭据。 如需了解详情,请参阅为客户端库设置身份验证

def streaming_and_batching(project_id, instance_id, table_id):
    client = bigtable.Client(project=project_id, admin=True)
    instance = client.instance(instance_id)
    table = instance.table(table_id)
    batcher = table.mutations_batcher(flush_count=2)
    rows = table.read_rows()
    for row in rows:
        row = table.row(row.row_key)
        row.delete_cell(column_family_id="cell_plan", column="data_plan_01gb")

    batcher.mutate_rows(rows)

Node.js

如需了解如何安装和使用 Bigtable 客户端库,请参阅 Bigtable 客户端库

如需向 Bigtable 进行身份验证,请设置应用默认凭据。 如需了解详情,请参阅为客户端库设置身份验证

const rows = (await table.getRows({limit: 2}))[0];
const entries = rows.map(row => {
  return {
    key: row.id,
    method: 'delete',
    data: {
      column: 'cell_plan:data_plan_05gb',
    },
  };
});
await table.mutate(entries);
await printRows();

删除已获授权的视图中的数据

如需删除表数据,您可以向已获授权的视图发送删除请求。您必须使用以下其中一项:

  • gcloud CLI
  • Java 版 Bigtable 客户端

当您从已获授权的视图中删除数据时,除了表 ID 之外,还需要提供已获授权的视图 ID。

您可以从已获授权的视图中删除的数据受到已获授权的视图定义的限制。您只能删除已获授权的视图中包含的数据。如果您尝试删除的数据不在已获授权的视图定义范围内或受以下规则的约束,系统会返回 PERMISSION_DENIED 错误:

  • 不支持在 Admin API 中使用 DropRowRange 从已获授权的视图中删除一系列行。
  • 不支持从行中删除。
  • 只要是在授权视图中的行,系统支持从列中将其删除。
  • 只有当指定的列族配置为允许在授权视图中使用所有列限定符前缀 (qualifier_prefixes="") 时,才允许从列族中删除内容。

例如,如果您尝试从指定行中删除,并且该行包含底层表中不在已获授权的视图中的列,则请求将失败。

后续步骤