文档首页
X DevAPI 用户指南
下载本手册
PDF (US Ltr) - 1.4Mb
PDF (A4) - 1.4Mb


X DevAPI 用户指南  /  使用集合  /  为集合创建索引

4.4 为集合创建索引

为了更有效地导航大型文档集合,您可以根据集合中文档中的一个或多个字段创建索引。本节介绍如何为集合创建索引。

创建索引

集合索引是虚拟列上的普通 MySQL 索引,这些虚拟列从集合中的文档中提取数据。因为 MySQL 无法直接索引 JSON 值,所以要启用集合索引,您需要提供一个 JSON 文档,该文档指定索引要使用的文档字段。您将定义索引的 JSON 文档作为 IndexDefinition 参数传递给 Collection.createIndex(name, IndexDefinition) 方法。这个通用示例(实际语法可能因编程语言而异)展示了如何根据 count 字段创建一个强制的整型索引

myCollection.createIndex("count", {fields:[{"field": "$.count", "type":"INT", required:true}]});

此示例展示了如何根据文本字段创建索引:在本例中为邮政编码。对于文本字段,您必须指定索引的前缀长度,这是 MySQL 服务器的要求

myCollection.createIndex("zip", {fields: [{field: "$.zip", type: "TEXT(10)"}]})

有关 IndexDefinition 的格式以及支持索引的字段类型的更多信息,请参阅 定义索引

如果已存在同名索引或索引定义格式不正确,则 Collection.createIndex() 方法将失败并报错。名称参数是必需的,并且必须是 SQL 语句 CREATE INDEX 接受的有效索引名称。

要删除现有索引,请使用 collection.dropIndex(string name) 方法。这将删除具有传递名称的索引,如果命名的索引不存在,则操作将静默成功。

集合的索引存储为虚拟列。要验证创建的索引,请使用 SHOW INDEX 语句。例如,要从 MySQL Shell 使用此 SQL

session.runSql('SHOW INDEX FROM mySchema.myCollection');

定义索引

要根据集合中的文档创建索引,您需要创建一个 IndexDefinition JSON 文档。本节介绍了您可以在此类 JSON 文档中使用的有效字段来定义索引。

要定义用于索引集合的文档字段,该字段的类型必须在整个集合中保持一致。换句话说,类型必须一致。用于定义索引的 JSON 文档,例如 {fields: [{field: '$.username', type: 'TEXT'}]},可以包含以下内容

  • fields:至少包含一个 IndexField 对象的数组,每个对象描述要包含在索引中的 JSON 文档字段。

    单个 IndexField 描述由以下字段组成

    • field:一个字符串,包含要索引的文档成员或字段的完整文档路径

    • type:用于将字段映射到的支持列类型之一的字符串(请参阅 字段数据类型)。对于数字类型,可以跟随可选的 UNSIGNED 关键字。对于 TEXT 类型,您必须定义要考虑用于索引的长度(前缀长度)。

    • required:如果字段需要存在于文档中,则应设置为 true 的可选布尔值。对于除 GEOJSON 之外的所有类型,默认值为 false,而 GEOJSON 的默认值为 true

    • options:解码 GEOJSON 数据时用作特殊选项标志的可选整数(有关详细信息,请参阅 ST_GeomFromGeoJSON() 的说明)。

    • srid:解码 GEOJSON 数据时用作 srid 值的可选整数(有关详细信息,请参阅 ST_GeomFromGeoJSON() 的说明)。

    • array:如果该字段包含数组,则设置为 true 的可选布尔值。默认值为 false。有关详细信息,请参阅 索引数组字段

      重要

      对于 MySQL 8.0.16 及更早版本,索引不支持 JSON 数组字段;指定包含数组数据的字段不会从服务器生成错误,但索引无法正常工作。

  • type:定义索引类型的可选字符串。值为 INDEXSPATIAL 之一。默认值为 INDEX,可以省略。

IndexDefinitionIndexField JSON 文档中包含上面未描述的任何其他字段会导致 collection.createIndex() 失败并报错。

如果未指定索引类型或设置为 INDEX,则创建的索引与通过发出 CREATE INDEX 创建的索引相同。如果索引类型设置为 SPATIAL,则创建的索引与通过发出带有 SPATIAL 关键字的 CREATE INDEX 创建的索引相同,请参阅 空间索引优化创建空间索引。例如

myCollection.createIndex('myIndex', //
{fields: [{field: '$.myGeoJsonField', type: 'GEOJSON', required: true}], type:'SPATIAL'})
重要

使用 SPATIAL 类型的索引时,不能在 IndexField 条目中将 required 字段设置为 false

这是一个基于多个字段创建索引的示例

myCollection.createIndex('myIndex', {fields: [{field: '$.myField', type: 'TEXT'}, //
{field: '$.myField2', type: 'TEXT(10)'}, {field: '$.myField3', type: 'INT'}]})

索引字段的值使用标准 MySQL 类型转换从 JSON 转换为 IndexField 描述中指定的类型(请参阅 表达式求值中的类型转换),但 GEOJSON 类型除外,它使用 ST_GeomFromGeoJSON() 函数进行转换。这意味着在 IndexField 描述中使用数字类型时,非数字的实际字段值将转换为 0。

IndexField 中的 optionssrid 字段只有在 type 设置为 GEOJSON 时才会出现。如果存在,则在将 GEOJSON 数据转换为 MySQL 原生 GEOMETRY 值时,它们将用作 ST_GeomFromGeoJSON() 的参数。

字段数据类型

文档字段支持以下数据类型。在 type 字段中使用时,类型名称不区分大小写。

索引数组字段

X DevAPI 支持基于数组字段创建索引,方法是将 IndexField 描述中的布尔值字段 array 设置为 true。例如,要为 emails 数组字段创建索引:

collection.createIndex("emails_idx", //
    {fields: [{"field": "$.emails", "type":"CHAR(128)", "array": true}]});

以下限制适用于基于数组创建索引:

  • 对于每个索引,只有一个索引字段可以是 array

  • 可以为其创建数组索引的数据类型: