复合索引配置

Datastore 模式 Firestore 使用索引来处理应用执行的每个查询。 实体发生变化时,这些索引也会随之更新,因此应用执行查询时可快速返回结果。Datastore 模式会自动提供内置索引,但需要预先了解应用要用到哪些复合索引。您可在配置文件中指定应用所需的复合索引。Datastore 模拟器可以 在您测试 应用。您可以使用 gcloud 命令行工具,更新供 Datastore 模式生产数据库使用的索引。

系统要求

如需使用 gcloud CLI,您必须已安装 Google Cloud CLI

关于 index.yaml

应用执行的每个 Datastore 模式查询都需要相应的索引。 简单查询(例如对单个属性的查询)的索引是自动创建的。复杂查询的复合索引必须在名为 index.yaml 的配置文件中进行定义。此文件将随应用一起上传, Datastore 模式数据库中的复合索引。

在以下情况下,Datastore 模拟器会自动向该文件添加项: 应用尝试执行的查询需要的复合索引没有 相应的条目您可以调整复合索引或创建 手动创建新文件index.yaml 位于 <project-directory>/WEB-INF/ 文件夹中。包含 WEB-INF/appengine-generated/index.yaml 的数据目录默认为 ~/.config/gcloud/emulators/datastore/。如需了解详情,请参阅 Datastore 模拟器项目目录

下面是一个 index.yaml 文件示例:

indexes:

- kind: Task
  ancestor: no
  properties:
  - name: done
  - name: priority
    direction: desc

- kind: Task
  properties:
  - name: collaborators
    direction: asc
  - name: created
    direction: desc

- kind: TaskList
  ancestor: yes
  properties:
  - name: percent_complete
    direction: asc
  - name: type
    direction: asc

index.yaml 的语法采用 YAML 格式。如需详细了解此语法,请参阅 YAML 网站

复合索引定义

index.yaml 包含一个名为 indexes 的列表元素。列表中的每个元素表示一个应用复合索引。

索引元素可包含以下元素:

kind
查询的实体种类。此元素是必需的。
properties

一个要作为复合索引列包含在内的属性列表,按照排序顺序排列:先是等式过滤条件中使用的属性,然后是非等式过滤条件中使用的属性,最后是排序顺序及其方向。

该列表中的每个元素包含以下元素:

name
Datastore 模式下的属性名称。
direction
排序方向:asc 表示升序,desc 表示降序。仅查询的排序顺序中使用的属性需要该元素,且必须与查询使用的方向匹配。默认值为 asc
ancestor

如果查询具有祖先子句,则为 yes。默认值为 no

自动和手动复合索引

当 Datastore 模拟器将生成的复合索引定义添加到 index.yaml 文件中时,会加在下面这一行之后(需要时会插入此行):

# AUTOGENERATED

模拟器将该行以下的所有复合索引定义都视为 并且可能会将该行下面的现有定义更新为 应用进行查询。

该行以上的所有复合索引定义都被视为手动控制,模拟器不对其进行更新。模拟器仅会更改该行之后的内容,并且仅在完整的 index.yaml 文件未描述应用执行的某个查询时才进行更改。要控制自动复合索引定义,请将其移至上方 这一行。

更新复合索引

datastore indexes create 命令用于查看本地 Datastore 复合索引 配置(index.yaml 文件),而如果复合索引配置定义了 Datastore 模式生产数据库中尚不存在的复合索引 创建新的复合索引。请参阅使用 gcloud CLI 的开发工作流 查看有关如何使用 indexes create 的示例。

要创建复合索引,数据库必须设置复合索引,然后 使用现有数据回填复合索引。复合索引创建时间是设置时间和回填时间的总和:

  • 设置复合索引需要几分钟时间。复合索引的最短创建时间为几分钟,即使空数据库也是如此。

  • 回填时间取决于属于新复合索引的现有数据的数量。通过 属于复合索引的属性值越多, 回填复合索引。

如果应用执行的查询需要尚未完成的复合索引 则查询会引发异常。为避免此情况,在新复合索引构建完毕之前,请务必谨慎部署需要复合索引的应用的新版本。

您可以在索引页面中查看复合索引的状态 在 Google Cloud 控制台中查看。

删除未使用的复合索引

通过复合索引配置更改或移除复合索引时,原始复合索引不会自动从 Datastore 模式数据库中删除。这样,您便能够在构建新复合索引期间让应用的旧版本继续运行,或者在发现新版本存在问题时立即还原到旧版本。

如果您确定不再需要旧的复合索引,可以将其删除 datastore indexes cleanup 命令。此命令 删除未提及的 Datastore 模式生产实例的所有复合索引 (位于 index.yaml 本地版本中)。请参阅 使用 gcloud CLI 的开发工作流。 请使用 indexes cleanup

命令行参数

如需详细了解用于创建和清除复合索引的命令行参数,请分别参阅 datastore indexes createdatastore indexes cleanup 命令的相关信息。如需详细了解 gcloud CLI 的命令行参数,请参阅 gcloud CLI 参考文档

管理长时间运行的操作

复合索引构建是“长时间运行的操作”,可能需要大量时间才能完成。

您启动复合索引构建后,Datastore 模式会为操作分配唯一名称。操作名称的前缀为 projects/[PROJECT_ID]/databases/(default)/operations/,例如:

projects/project-id/databases/(default)/operations/ASA1MTAwNDQxNAgadGx1YWZlZAcSeWx0aGdpbi1zYm9qLW5pbWRhEgopEg

不过,您可以在指定 describe 命令的操作名称时省略前缀。

列出所有长时间运行的操作

如需列出长时间运行的操作,请使用 gcloud datastore operations list 命令。此命令会列出正在进行和最近完成的操作。最近几天内完成的操作都会列出:

gcloud

gcloud datastore operations list

rest

在使用任何请求数据之前,请先进行以下替换:

  • project-id:您的项目 ID

HTTP 方法和网址:

GET https://datastore.googleapis.com/v1/projects/project-id/operations

如需发送您的请求,请展开以下选项之一:

请参阅下方有关响应的信息。

例如,最近完成的复合索引构建会显示以下信息:

{
  "operations": [
  {
    "name": "projects/project-id/operations/S01vcFVpSmdBQ0lDDCoDIGRiNTdiZDQNmE4YS0yMTVmNWUzZSQadGx1YWZlZAcSMXRzYWVzdS1yZXhlZG5pLW5pbWRhFQpWEg",
    "done": true,
    "metadata": {
      "@type": "type.googleapis.com/google.datastore.admin.v1.IndexOperationMetadata",
      "common": {
        "endTime": "2020-06-23T16:55:29.923562Z",
        "operationType": "CREATE_INDEX",
        "startTime": "2020-06-23T16:55:10Z",
        "state": "SUCCESSFUL"
      },
      "indexId": "CICAJiUpoMK",
      "progressEntities": {
        "workCompleted": "2193027",
        "workEstimated": "2198182"
      }
    },
    "response": {
      "@type": "type.googleapis.com/google.datastore.admin.v1.Index",
      "ancestor": "NONE",
      "indexId": "CICAJiUpoMK",
      "kind": "Task",
      "projectId": "project-id",
           "properties": [
        {
          "direction": "ASCENDING",
          "name": "priority"
        },
        {
          "direction": "ASCENDING",
          "name": "done"
        },
        {
          "direction": "DESCENDING",
          "name": "created"
        }
      ],
      "state": "READY"
    }
  },
  ]
}

描述单个操作

您可以列出单个长时间运行的操作的详细信息,而不是列出所有长时间运行的操作:

gcloud

使用 operations describe 命令显示状态 使用复合索引

gcloud datastore operations describe operation-name

rest

在使用任何请求数据之前,请先进行以下替换:

  • project-id:您的项目 ID

HTTP 方法和网址:

GET https://datastore.googleapis.com/v1/projects/project-id/operations

如需发送您的请求,请展开以下选项之一:

请参阅下方有关响应的信息。

估计完成时间

操作运行时,查看 state 字段的值可了解操作的总体状态。

用于获取长时间运行的操作的状态的请求也会返回指标 workEstimatedworkCompleted。这些返回的指标包含实体数量。workEstimated 基于数据库统计信息估算操作将处理的实体总数。workCompleted 显示到目前为止已处理的实体数。操作完成后,workCompleted 会反映实际处理的实体总数,可能与 workEstimated 的值不同。

workCompleted 除以 workEstimated 可得出粗略的进度估算值。该估计可能不准确,因为它取决于统计信息收集是否存在延迟。

例如,以下是一个复合索引构建的进度状态:

{
  "operations": [
    {
      "name": "projects/project-id/operations/AyAyMDBiM2U5NTgwZDAtZGIyYi0zYjc0LTIzYWEtZjg1ZGdWFmZWQHEjF0c2Flc3UtcmV4ZWRuaS1uaW1kYRUKSBI",
      "metadata": {
        "@type": "type.googleapis.com/google.datastore.admin.v1.IndexOperationMetadata",
        "common": {
          "operationType": "CREATE_INDEX",
          "startTime": "2020-06-23T16:52:25.697539Z",
          "state": "PROCESSING"
        },
        "progressEntities": {
          "workCompleted": "219327",
          "workEstimated": "2198182"
        }
       },
    },
    ...

操作完成后,操作说明将包含 "done": true。查看 state 字段的值,了解操作的结果。如果没有在响应中设置 done 字段,则其值为 false。对于进行中的操作,不要依赖 done 值的存在。