索引投影是技能组定义的一个组件,用于定义辅助索引的形状。支持一对多索引模式,其中,来自扩充管道的内容可以针对多个索引。
索引投影利用由扩充管道生成的经 AI 加强的内容,并将其编入您的搜索服务中的辅助索引(不同于索引器默认目标的索引)。 通过使用索引投影,您还可以在编制索引之前重塑数据。这样,您可以将富数据项的数组拆分为目标索引中的多个搜索文档,这种方法也被称为“一对多”索引。 “一对多”索引对于数据分块场景非常有用,其中你可能希望有一个用于未分块内容的主索引,和一个用于已分块内容的辅助索引。
如果你过去使用过认知技能,便知道技能集创建丰富的内容。 技能集通过一系列调用原子转换的增强功能(例如识别实体或翻译文本)对文档进行处理。 默认情况下,在技能组中处理的一个文档会映射到搜索索引中的单个文档。 这意味着,如果对输入文本执行分块,然后在每个区块上执行扩充,则通过 outputFieldMappings 映射时索引中的结果是生成的扩充的数组。 借助索引映射,可以定义一个上下文,将丰富数据的每个区块映射到其各自的搜索文档。 这样,你就可以将文档的扩展数据进行一对多映射,并应用到搜索索引中。
索引投影定义
索引投影是在技能组定义中定义的,主要定义为选择器数组,其中每个选择器对应于搜索服务上的一个不同的目标索引。 每个选择器需要以下参数作为其定义的一部分:
-
targetIndexName:搜索服务上用于对索引投影数据进行编制的索引名称。 -
parentKeyFieldName:包含父文档的键值的目标索引中的字段的名称。 -
sourceContext:定义将数据映射到各个搜索文档的粒度的扩充注释。 有关详细信息,请参阅技能上下文和输入注释语言。 -
mappings:将增强的数据映射到搜索索引字段的数组。 每个映射都包含:-
name:搜索索引中用于编制数据索引的字段名称。 -
source:用于数据提取的富化注释路径。
-
每个 mapping 还可以递归方式使用可选的 sourceContext 和 inputs 字段定义数据,类似于知识存储或整形程序技能。 使用这些参数,可以将数据调整为适合在搜索索引中类型为 Edm.ComplexType 的字段中编制索引的格式。
targetIndexName 参数中定义的索引具有以下要求:
- 在创建包含索引投影定义的技能组之前必须已在搜索服务上创建。
- 必须包含具有
parentKeyFieldName参数中定义的名称的字段。 此字段必须是Edm.String类型的,不能是键字段,并且必须将“可筛选”设置为 true。 - 键字段必须将“可搜索”设置为 true,且使用
keyword分析器定义。 - 必须为
name中定义的每个mappings定义字段,其中所有字段都不能是键字段。
下面是一个用于索引映射定义的示例有效负载,可将单个页面的输出映射为其在搜索索引中的独立文档。
"indexProjections": {
"selectors": [
{
"targetIndexName": "myTargetIndex",
"parentKeyFieldName": "ParentKey",
"sourceContext": "/document/pages/*",
"mappings": [
{
"name": "chunk",
"source": "/document/pages/*"
}
]
}
]
}
处理父文档
由于索引投影能够有效地为通过技能组处理的每个“父”文档生成相应的“子”文档,因此您还可以选择以下方式来处理“父”文档的索引。
若要将父文档和子文档置于不同的索引中,只需确保索引器定义的
targetIndexName与索引投影选择器中定义的targetIndexName不同。若要在同一索引中对父文档和子文档编制索引,需要确保目标索引的架构同时适用于索引器定义中定义的
fieldMappings和outputFieldMappings,以及索引投影选择器中定义的mappings。 然后,只需为索引器定义和索引投影选择器提供相同的targetIndexName。若要忽略父文档并仅对子文档编制索引,仍然需要在索引器定义中提供
targetIndexName(只需提供与为索引投影选择器提供的相同名称)。 然后定义parameters定义旁边的单独的selectors对象,并将projectionMode键设置为skipIndexingParentDocuments,如下所示:"indexProjections": { "selectors": [ ... ], "parameters": { "projectionMode": "skipIndexingParentDocuments" } }
索引投影通常可用。 建议使用最新的稳定 API。
内容生命周期
如果索引器数据源支持更改跟踪和删除检测,索引过程可以同步主索引和辅助索引以选取这些更改。
每次运行索引器和技能组时,如果技能组或基础源数据已更改,索引投影就会更新。 索引器选取的任何更改都将通过扩充过程传播到索引中的投影,从而确保投影数据是原始数据源中内容的当前表示形式。
注意
虽然可以使用索引推送 API 手动编辑投影文档中的数据,但如果源数据中的文档被更新,任何编辑都会在下次管道调用时被覆盖。
投影的键值
每个索引投影文档都包含索引器生成的唯一标识键,以确保唯一性,让更改和删除跟踪可以正常运行。 该键包含以下各段:
- 用于保证唯一性的随机哈希。 如果在索引器运行之间更新父文档,则此哈希会更改。
- 父文档的键。
- 标识从中生成文档的上下文的扩充注释路径。
例如,如果将具有键值“123”的父文档拆分为四页,然后通过索引投影将其中每个页面投影为其自己的文档,则第三页文本的键将类似于“01f07abfe7ed_123_pages_2”。 如果父文档随后更新以添加第五页,那么第三页的新键可能是“9d800bdacc0e_123_pages_2”,这是因为在索引器运行期间,随机哈希值发生了变化,即使其他投影数据没有改变。
更改或添加
如果更改了父文档,使得投影索引文档中的数据发生变化(例如,如果在特定页面更改了一个单词但没有添加新的页面),则目标索引中与该投影对应的数据将会更新以反映该更改。
如果更改了父文档,使得出现了之前不存在的新投影子文档(例如,如果向文档添加了一页或多页的文本),那么这些新的子文档将在下次运行索引器时添加。
在这两种情况下,所有预期的文档都会更新其键的新哈希值,无论其具体内容是否发生了更改。
删除
如果更改了父文档,使得由索引投影生成的子文档不再存在(例如,如果文本缩短,导致区块比之前少),则会删除搜索索引中的相应子文档。 其余子文档的键也会更新以包含新的哈希值,即使它们的内容没有发生其他变化也是如此。
如果父文档从数据源中完全删除,则仅当数据源定义上定义的 dataDeletionDetectionPolicy 检测到删除时,才会删除相应的子文档。 如果未配置 dataDeletionDetectionPolicy,但需要从数据源中删除父文档,应在不再需要它时手动删除子文档。