如何对对象和文档数组中的字段进行索引
在此页面上
注意
Atlas Search embeddedDocuments 类型、 embeddedDocument操作符和 embedded
评分选项均处于预览状态。当副本集或单个MongoDB分片上的分片 Atlas Search索引达到2 、100 、000 、000 索引对象时, Atlas Search会将索引转换为过时的可查询状态。如果您希望Atlas Search将来支持超过2 、100 、000 、000 的索引对象,请在MongoDB反馈引擎中为此请求投票。
您可以使用 Atlas Search embeddedDocuments
类型来对文档中的字段和作为数组元素的对象编制索引。Atlas Search 可为嵌入式文档编制独立于其父文档的索引。每个索引文档只包含嵌入式文档数组元素的字段。您只能使用 EmbeddedDocument 操作符来查询索引为 embeddedDocuments
类型的字段。
注意
使用 embeddedDocuments
类型为文档数组中的字段编制索引,以便您可以单独查询每个嵌套文档。如果只需要查询嵌套文档与父文档的关系,请使用“如何索引对象和文档中的字段”类型。
Atlas Search 不会动态地对 embeddedDocument
类型的字段进行索引。您必须 使用静态映射对 embeddedDocument
字段进行索引。您可以使用 Atlas 用户界面中的可视化编辑器或 JSON 编辑器对 embeddedDocument
类型的字段进行索引。
查看 embeddedDocuments
类型限制
在创建使用 embeddedDocuments
类型的索引之前,请查看 2,100,000,000 索引对象限制和其他 Atlas Search 限制。
2,100,000,000 个索引对象限制
Atlas Search 将停止在副本集或单个分片上复制大于 2,100,000,000 个索引对象的索引的更改,其中每个已索引的嵌入式文档都算作单个对象。使用 embeddedDocuments
字段类型可能会导致索引对象超过此限制,从而导致索引转换为 Stale
可查询状态,并可能导致结果过时。
索引对象的确切数量可能会因文档更改和删除的速率而异。搜索 Lucene Docs 最大数量指标提供了每个副本集或分片中所有索引的当前索引对象数量的上限。您可以通过执行以下操作来估算单个索引中索引对象的预期数量:
计算每个文档的索引对象数量。对于每一级嵌套,每个嵌入式文档都算作一个单独的索引对象。
total number of index objects = 1 + number of nested embedded documents 将每个文档的索引对象数量乘以集合中的文档总数
total number of index objects x total number of documents in collection
请注意,此近似值是一个下限。
例子
考虑此教程中描述的名为 schools
的集合,假设该集合包含与以下内容类似的 1000 个文档:
{ "_id": 0, "name": "Springfield High", "mascot": "Pumas", "teachers": [ { "first": "Jane", "last": "Smith", "classes": [ { "subject": "art of science", "grade": "12th" }, ... // 2 more embedded documents ] }, ... // 1 more embedded document ], "clubs": { "stem": [ { "club_name": "chess", "description": "provides students opportunity to play the board game of chess informally and competitively in tournaments." }, ... // 1 more embedded document ], ... // 1 more embedded document } }
现在,请考虑 schools
集合中以下字段的索引定义:
名为 teachers
的文档数组被索引为 embeddedDocuments
类型,并启用了动态映射。但是,classes
字段未进行索引。使用以下方法计算索引对象:
计算每个文档的索引对象数量。
Number of ``teachers`` embedded documents = up to 2 Total number of index objects per document = 1 + 2 = 3 乘以集合中的文档总数。
Number of documents in the collection = 1000 Number of index objects per document = 3 Total number of index objects for collection = 1000 x 3 = 3000
名为 teachers
和 teachers.classes
的文档数组被索引为 embeddedDocuments
类型,并启用了动态映射。使用以下方法计算索引对象:
计算每个文档的索引对象数量:
Number of documents = 1 Number of ``teachers`` embedded documents = up to 2 Number of ``classes`` embedded documents = up to 3 Number of index objects per document = 1 + ( 2 x 3 ) = 7 乘以集合中的文档总数。
Number of documents in the collection = 1000 Number of index objects per document = 7 Total number of index objects: 1000 x 7 = 7000
如果您的集合包含可能产生 2,100,000,000 个索引对象的较大数组,则必须对任何包含 embeddedDocuments
类型索引的集群进行分片。
Atlas Search 限制
适用以下限制:
您只能在嵌套级别最多为
5
个的字段上使用embeddedDocuments
。一个embeddedDocuments
字段不能具有超过4
个embeddedDocuments
父字段。您不能将
embeddedDocuments
类型内部的字段定义为已弃用的 knnVector 类型。您无法将索引为
embeddedDocuments
类型的字段的子字段作为词元类型进行索引。只有将嵌入式文档子字段的父项作为文档类型索引时,才能执行以下操作:
对嵌入式文档中的 string 字段进行分面搜索。您还必须将要分面的字段索引为 stringFacet 类型。
注意
当您在嵌入式文档中对字符串字段进行分面时,Atlas Search 只返回与父文档数量匹配的分面计数。
您无法对嵌入式文档中的数字和日期字段进行分面。
突出显示嵌入文档中的字段。有关示例,请参阅如何针对数组中的对象运行 Atlas 搜索查询教程。
按嵌入式文档字段的父项排序。您还必须使用 string 值作为词元类型对嵌入式文档字段进行索引。对于具有数字和日期值的子字段,启用动态映射以自动为这些字段编制索引。有关示例,请参阅排序示例。
为 embeddedDocument
类型定义索引
要定义 embeddedDocument
类型的索引,请在 Atlas UI 中选择您的首选配置方法,然后选择数据库和集合。
单击 Refine Your Index 配置索引。
在 Field Mappings 部分中,单击 Add Field 打开 Add Field Mapping 窗口。
单击 Customized Configuration(连接)。
从 Field Name 下拉菜单中选择要索引的字段。
注意
您无法对字段名称开头包含美元 (
$
) 符号的字段创建索引。单击 Data Type(添加数据)下拉列表并选择 EmbeddedDocument(插入文档)。
切换 Enable Dynamic Mapping 设置以启用或禁用文档中所有动态可索引字段的动态索引。要了解更多信息,请参阅配置
document
字段属性。单击 Add(连接)。
如果禁用了动态映射,请单击 EmbeddedDocument 类型字段的 Add Embedded Field,以定义文档中字段的字段映射。
以下是 embeddedDocument
类型的 JSON 语法。将默认索引定义替换为以下内容。要了解有关字段的更多信息,请参阅字段属性。
1 { 2 "mappings": { 3 "dynamic": true|false, 4 "fields": { 5 "<field-name>": { 6 "type": "embeddedDocuments", 7 "dynamic": true|false, 8 "fields": { 9 "<field-name>": { 10 <field-mapping-definition> 11 } 12 } 13 } 14 } 15 } 16 }
配置 embeddedDocument
字段属性
Atlas Search embeddedDocuments
类型采用以下参数:
字段 | 类型 | 必要性 | 说明 | 默认 |
---|---|---|---|---|
type | 字符串 | 必需 | 标识字段类型的人类可读标签。值必须是 embeddedDocuments 。 | |
dynamic | 布尔 | Optional | 该标记指定是否对文档中的每个可动态索引的字段进行索引。值可以是以下值之一:
| false |
fields | 文档 | Optional | 要进行索引的字段。 如果 如果 Atlas Search 不支持将分面字段作为 | {} |
尝试 embeddedDocument
类型的示例
下面的索引定义示例使用了 sample_supplies.sales 集合。如果您的集群上已经加载了 示例数据,则可以使用 Atlas 用户界面中的可视化编辑器或 JSON 编辑器来配置索引。选择首选配置方法后,选择数据库和集合并优化索引以添加字段映射。
以下索引定义对 items
字段中的对象数组编制索引。它还将 Atlas Search 配置为自动为 items
数组中对象内的所有动态可索引字段编制索引。
在 Add Field Mapping 窗口中,从 Field Name 下拉列表中选择 items。
单击 Data Type(添加数据)下拉列表并选择 EmbeddedDocuments(插入文档)。
如果需要,请切换 Enable Dynamic Mapping 以启用动态映射。
单击 Add(连接)。
将默认索引定义替换为以下索引定义。
1 { 2 "mappings": { 3 "fields": { 4 "items": { 5 "type": "embeddedDocuments", 6 "dynamic": true 7 } 8 } 9 } 10 }
注意
要为嵌入式文档中的所有字段(包括 Atlas Search 未动态索引的字段)建立索引,请在索引定义中定义这些字段。对于字符串分面,Atlas Search 会对结果集中的每个文档计数一次字符串分面。
例如,以下索引定义将 Atlas Search 配置为自动为 items
数组中的对象内的所有动态可索引字段编制索引。它还将对象数组内的 purchaseMethod
字段配置为作为 stringFacet 进行索引(Atlas Search 不会动态索引该字段),以支持针对该字段的 Atlas Search 分面查询:
单击 Field Mappings 部分的 Add Field,并在 Add Field Mapping 窗口配置各字段的设置后,单击 Add 添加以下字段。
Field Name | Data Type |
---|---|
items | 单击下拉菜单并选择 EmbeddedDocuments 。 |
purchaseMethod | 单击下拉菜单并选择 StringFacet 。 |
1 { 2 "mappings": { 3 "dynamic": true, 4 "fields": { 5 "items": { 6 "dynamic": true, 7 "type": "embeddedDocuments" 8 }, 9 "purchaseMethod": { 10 "type": "stringFacet" 11 } 12 } 13 } 14 }
以下索引定义将 Atlas Search 配置为仅将 name
和 tags
字段索引为 items
对象数组中的 Atlas Search string
类型。
在 Add Field Mapping 窗口中,从 Field Name 下拉列表中选择 items。
单击 Data Type(添加数据)下拉列表并选择 EmbeddedDocuments(插入文档)。
禁用 Enable Dynamic Mapping。
单击 Add(连接)。
单击 Add Embedded Field 以选择 Field Mappings 表中的 items 字段,并在 Add Embedded Field Mapping 窗口配置各字段的设置后,单击 Add 添加以下字段。
Field NameData Typeitems.name单击 Data Type(添加数据)下拉列表并选择 String(插入文档)。items.tags单击 Data Type(添加数据)下拉列表并选择 String(插入文档)。
将默认索引定义替换为以下索引定义。
1 { 2 "mappings": { 3 "fields": { 4 "items": { 5 "type": "embeddedDocuments", 6 "dynamic": false, 7 "fields": { 8 "name": { 9 "type": "string" 10 }, 11 "tags": { 12 "type": "string" 13 } 14 } 15 } 16 } 17 } 18 }