本文系统介绍 MongoDB Search 支持的索引类型、字段映射类型、分析器、检索操作符($search、$vectorSearch、$rankFusion)及参数细节,作为撰写检索查询和调优时的技术参考。
概述
MongoDB Search 功能通过在 MongoDB 实例中集成专用的搜索节点(mongot),提供与数据库无缝集成的全文检索和向量检索能力。无需管理外部搜索系统,即可使用 MongoDB 查询语言(MQL)完成多模态搜索任务,从而简化开发、降低运维负担。
关于 MongoDB Search 的适用范围、工作原理、开通和节点管理,请参见 MongoDB Search。本文聚焦索引定义和检索查询所需的算法参数与操作符。
Search 索引类型
全文检索索引
使用 createSearchIndex 方法创建,用于支持 $search 聚合阶段的全文检索查询。索引映射方式分为动态映射和静态映射。
动态映射(Dynamic Mapping)
dynamic: true 使 MongoDB 自动为集合中的所有字段建立索引,适合快速原型验证。
db.reviews.createSearchIndex({
name: "reviews_full_text_index",
definition: {
mappings: {
dynamic: true
}
}
});
静态映射(Static Mapping)
手动指定需要索引的字段及其类型,适合生产环境。通过精确控制索引范围减少存储开销。
db.movies.createSearchIndex({
name: "movies_custom_index",
definition: {
mappings: {
dynamic: false,
fields: {
title: { type: "string", analyzer: "lucene.standard" },
genre: { type: "stringFacet" },
year: { type: "number" },
rating: { type: "number" },
plot: { type: "string", analyzer: "lucene.standard" }
}
}
}
});
向量检索索引
使用三参数形式的 createSearchIndex 方法创建,类型为 "vectorSearch",用于支持 $vectorSearch 聚合阶段的相似性检索。
db.images.createSearchIndex(
"vector_index", // 索引名称
"vectorSearch", // 索引类型
{
fields: [
{
type: "vector",
path: "embedding", // 存储向量的字段
numDimensions: 1536, // 向量的维度
similarity: "dotProduct", // 相似度计算方法
quantization: "scalar" // 量化方式(可选)
}
]
}
);
字段映射类型
在静态映射索引的 fields 中,为每个字段指定类型:
|
type |
用途 |
关键子参数 |
|
|
全文检索(分词+倒排) |
|
|
|
不分词精确匹配(标签/枚举/ID) |
|
|
|
自动补全/前缀搜索 |
|
|
|
数值范围/排序/facet |
- |
|
|
日期范围/排序 |
- |
|
|
布尔过滤 |
- |
|
|
按 _id 或引用字段过滤 |
- |
|
|
UUID 字段过滤 |
- |
|
|
地理位置(geoWithin/geoNear) |
|
|
|
嵌套对象(点路径检索) |
|
|
|
数组对象整体匹配(同元素内多条件) |
|
|
|
向量检索($vectorSearch) |
|
|
|
旧版向量检索类型(兼容) |
|
|
|
自动 embedding |
|
|
|
字符串分面统计(可与 string 配合) |
- |
字段定义示例(各类型在 mappings.fields 中的写法):
mappings: {
dynamic: false,
fields: {
title: { type: "string", analyzer: "lucene.standard" }, // 全文检索
status: { type: "token" }, // 精确匹配(枚举)
price: { type: "number" }, // 数值范围/排序
created: { type: "date" }, // 日期范围
onSale: { type: "boolean" },
location:{ type: "geo" }, // 地理位置
tags: { type: "string", analyzer: "lucene.smartcn" },
embedding: { // 向量检索
type: "vector",
numDimensions: 1536,
similarity: "cosine"
},
// 数组对象:数组内每个元素独立匹配(同元素内多条件同时成立)
items: {
type: "embeddedDocuments",
dynamic: false,
fields: {
sku: { type: "token" },
color: { type: "string", analyzer: "lucene.standard" }
}
}
}
}
分析器
分析器决定文本如何被分词和标准化,在 string 类型字段中通过 analyzer 参数指定。
内置分析器
|
分析器 |
说明 |
分词示例 |
|
|
标准分析器,按 Unicode 文本分段规则分词并转小写 |
"The Quick Fox" → ["the", "quick", "fox"] |
|
|
按非字母字符分割并转小写 |
"hello-world 123" → ["hello", "world"] |
|
|
仅按空白字符分割,不转小写 |
"Hello World" → ["Hello", "World"] |
|
|
不分词,整个字段值作为一个 token |
"New York" → ["New York"] |
|
|
英文分析器,支持词干提取和停用词过滤 |
"running quickly" → ["run", "quick"] |
|
|
中文分析器(按字切分,粒度较粗) |
"全文搜索" → ["全", "文", "搜", "索"] |
|
|
中文智能分词(按词切分) |
"全文搜索" → ["全文", "搜索"] |
|
|
中日韩双字组合分词 |
"搜索引擎" → ["搜索", "索引", "引擎"] |
|
|
阿拉伯语分析器 |
- |
|
|
捷克语分析器 |
- |
|
|
德语分析器,含词干提取 |
"Bücher" → ["buch"] |
|
|
日文形态素分析(MeCab 词典) |
"東京都" → ["東京", "都"] |
|
|
波兰语词干分析器 |
- |
自定义分析器
可通过组合 tokenizer、tokenFilters 和 charFilters 创建自定义分析器:
db.collection.createSearchIndex({
name: "custom_analyzer_index",
definition: {
mappings: {
dynamic: false,
fields: {
content: {
type: "string",
analyzer: "myCustomAnalyzer"
}
}
},
analyzers: [
{
name: "myCustomAnalyzer",
charFilters: [{ type: "htmlStrip", ignoredTags: ["br", "hr"] }],
tokenizer: {
type: "standard"
},
tokenFilters: [
{ type: "lowercase" },
{ type: "stopword", tokens: ["the", "a", "an", "is"] }
]
}
]
}
});
Tokenizer 类型
|
Tokenizer |
说明 |
|
|
按 Unicode 文本分段规则分词 |
|
|
按空白字符分割 |
|
|
整体作为单个 token |
|
|
正则捕获组分词 |
|
|
正则分隔符分割 |
|
|
N-gram 分词 |
|
|
边缘 N-gram(前缀分词) |
|
|
识别并保留 URL 和 Email 地址 |
Token Filters
|
type |
说明 |
必填/关键参数 |
|
|
带变音符字符转 ASCII(café→cafe) |
- |
|
|
姓名语音编码(Daitch-Mokotoff) |
- |
|
|
边缘 N-gram(前缀分词) |
|
|
|
英文最小化词干(主要处理复数) |
- |
|
|
去英文所有格 's |
- |
|
|
展平 token 图(配合 graph 类过滤器) |
- |
|
|
ICU 折叠(大小写/变音/宽窄归一) |
- |
|
|
ICU Unicode 规范化 |
|
|
|
英文 Krovetz 词干(还原为真实词) |
- |
|
|
保留原词并复制一份供后续词干 |
- |
|
|
按 token 长度过滤 |
|
|
|
限制最大 token 数 |
|
|
|
转小写 |
- |
|
|
N-gram 分词 |
|
|
|
英文 Porter 词干 |
- |
|
|
正则替换 token |
|
|
|
去除重复 token |
- |
|
|
反转 token 字符 |
- |
|
|
生成相邻词组合(N-gram 短语) |
|
|
|
多语言 Snowball 词干 |
|
|
|
西班牙语复数词干 |
- |
|
|
波兰语词干 |
- |
|
|
移除停用词 |
|
|
|
去 token 首尾空白 |
- |
|
|
按大小写/数字/分隔符拆词 |
多个可选布尔项 |
Char Filters
Char Filters 在分词前对原始文本进行预处理,在自定义分析器中通过 charFilters 参数指定。
|
charFilter |
中文名 |
说明 |
子参数 |
|
|
HTML 剥离 |
去除 HTML 标签,只保留文本内容 |
|
|
|
ICU 规范化 |
基于 ICU 做 Unicode 规范化(连字/全半角/兼容字符归一) |
- |
|
|
字符映射 |
按自定义映射表做字符/字符串替换(如 & → and) |
|
|
|
波斯语字符处理 |
处理波斯语特有的零宽非连接符等字符 |
- |
Synonyms 同义词
synonyms 是 definition 下的顶层数组,与 mappings 平级,用于声明同义词映射规则。
definition: {
analyzers: [...],
mappings: {...},
synonyms: [...] // ← 定义synonyms
}
使用限制
-
同义词必须先在
definition.synonyms[]顶层声明。 -
同义词数据存放在独立 collection,必须与目标集合同库。
-
definition.synonyms[]每项必填三字段:name、source.collection、analyzer。 -
同义词集合文档需含
mappingType字段,取值为equivalent或explicit。
字段说明
|
字段 |
必填 |
说明 |
|
|
是 |
查询时 |
|
|
是 |
同库的同义词集合名 |
|
|
是 |
同义词条用什么分析器切分 |
mappingType 行为
|
mappingType |
行为 |
|
|
双向。搜任意一个都命中全部 |
|
|
单向。搜 input 里的词扩展到 synonyms,反过来不扩 |
完整示例
// ============ 1) 同义词集合(必须与目标集合同库,含 mappingType)============
db.synonyms_test.insertMany([
// equivalent(双向):搜任意一个都命中其他
{ mappingType: "equivalent", synonyms: ["支付", "付款", "缴费"] },
// explicit(单向):搜 input 才扩展到 synonyms,反向不成立
{ mappingType: "explicit", input: ["欠费"], synonyms: ["缴费", "付款"] }
]);
// ============ 2) 创建 Search Index(全程 lucene.smartcn)============
db.runCommand({
createSearchIndexes: "test_syn",
indexes: [{
name: "test_syn_idx",
definition: {
mappings: {
dynamic: false,
fields: {
content: { type: "string", analyzer: "lucene.smartcn" }
}
},
synonyms: [{
name: "mySynMapping",
source: { collection: "synonyms_test" },
analyzer: "lucene.smartcn" // ← 与字段 analyzer 一致,中文按词切
}]
}
}]
});
// ============ 3) 查询 ============
// equivalent 双向:搜"付款",期望命中 1(支付)/2(缴费)/3(付款)
db.test_syn.aggregate([
{ $search: {
index: "test_syn_idx",
text: { query: "付款", path: "content", synonyms: "mySynMapping" }
}},
{ $project: { content: 1, score: { $meta: "searchScore" } } }
]);
全文检索操作符($search)
通过 $search 聚合阶段执行全文检索查询,以下为支持的操作符。
text
基础全文检索,对查询文本进行分词后匹配目标字段。
db.reviews.aggregate([
{
$search: {
index: "reviews_full_text_index",
text: {
query: "good quality", // 查询关键词
path: "comment" // 在 comment 字段中检索
}
}
},
{ $limit: 5 },
{ $project: { _id: 0, comment: 1, score: { $meta: "searchScore" } } }
]);
参数说明:
-
query:检索关键词(字符串或字符串数组) -
path:检索字段(字符串或字符串数组) -
fuzzy:模糊匹配配置(可选) -
score:评分调整(可选) -
synonyms:同义词映射名称(可选)
compound
组合多个检索条件的复合查询,支持布尔逻辑组合。
db.movies.aggregate([
{
$search: {
index: "movies_custom_index",
compound: {
must: [
{ text: { query: "Drama", path: "genre" } }
],
mustNot: [
{ text: { query: "horror", path: "genre" } }
],
should: [
{ text: { query: "award", path: "plot" } }
],
filter: [
{ range: { path: "year", gte: 2000, lte: 2023 } }
]
}
}
},
{ $project: { title: 1, genre: 1, year: 1, _id: 0, score: { $meta: "searchScore" } } }
]);
子句说明:
|
子句 |
含义 |
是否影响评分 |
|
|
文档必须匹配所有条件 |
是 |
|
|
文档必须不匹配任何条件 |
否 |
|
|
匹配的文档获得更高评分 |
是 |
|
|
文档必须匹配,但不计算评分 |
否(性能更优) |
phrase
短语检索,要求词语按顺序出现。通过 slop 参数控制允许的词间距。
db.movies.aggregate([
{
$search: {
index: "default",
phrase: {
query: "organized crime",
path: "plot",
slop: 0 // 允许的词间距(默认 0,严格相邻)
}
}
},
{ $project: { title: 1, _id: 0, score: { $meta: "searchScore" } } }
]);
// 匹配 The Godfather(plot 中包含 "organized crime" 短语)
slop 值大于 0 时允许词语之间存在其他词:
// slop: 5 允许 "men" 和 "bond" 之间最多间隔 5 个词
{ phrase: { query: "men bond", path: "plot", slop: 5 } }
// 匹配 The Shawshank Redemption("men bond over a number of years")
range
数值或日期范围查询。
{
$search: {
range: {
path: "rating",
gte: 8.5,
lt: 10
}
}
}
支持的比较运算:gt(大于)、gte(大于等于)、lt(小于)、lte(小于等于)
fuzzy(模糊匹配)
在 text 操作符中通过 fuzzy 参数启用,容忍拼写错误。
db.movies.aggregate([
{
$search: {
index: "default",
text: {
query: "Godfater", // 拼写有误
path: "title",
fuzzy: {
maxEdits: 1, // 最大编辑距离(1 或 2)
prefixLength: 2, // 前缀不参与模糊匹配的字符数
maxExpansions: 50 // 最大扩展变体数
}
}
}
},
{ $project: { title: 1, _id: 0, score: { $meta: "searchScore" } } }
]);
// 匹配 "The Godfather"
wildcard(通配符)
使用 *(零个或多个字符)和 ?(单个字符)进行模式匹配。匹配发生在分词后的 token 级别。
db.movies.aggregate([
{
$search: {
index: "default",
wildcard: {
query: "inter*",
path: "title",
allowAnalyzedField: true
}
}
},
{ $project: { title: 1, _id: 0, score: { $meta: "searchScore" } } }
]);
// 匹配 Interstellar(token "interstellar" 匹配 "inter*")
参数说明:
-
query:包含通配符的模式(*匹配零或多个字符,?匹配单个字符) -
path:检索字段 -
allowAnalyzedField:对已分词字段使用时必须设为true
regex(正则表达式)
使用正则表达式进行模式匹配。基于 Lucene 正则引擎,匹配发生在分词后的 token 级别。
db.movies.aggregate([
{
$search: {
index: "default",
regex: {
query: ".*tion",
path: "plot",
allowAnalyzedField: true
}
}
},
{ $project: { title: 1, _id: 0, score: { $meta: "searchScore" } } },
{ $limit: 5 }
]);
// 匹配 plot 中包含以 "tion" 结尾的 token 的文档(如 redemption、fiction)
参数说明:
-
query:正则表达式模式(支持.、*、+、?、|、()、[ ]、{n,m}等语法) -
path:检索字段 -
allowAnalyzedField:对已分词字段使用时必须设为true
autocomplete(自动补全)
需配合 autocomplete 字段类型使用,支持前缀匹配和搜索建议。
// 索引定义:为 title 字段配置 autocomplete 类型
db.movies.createSearchIndex({
name: "ac_index",
definition: {
mappings: {
dynamic: false,
fields: {
title: [
{ type: "autocomplete" },
{ type: "string", analyzer: "lucene.standard" }
]
}
}
}
});
// 查询:输入 "inter" 自动补全
db.movies.aggregate([
{
$search: {
index: "ac_index",
autocomplete: {
query: "inter",
path: "title"
}
}
},
{ $project: { title: 1, _id: 0, score: { $meta: "searchScore" } } }
]);
// 匹配 Interstellar
exists(字段存在性检查)
检查文档中指定字段是否存在。
db.movies.aggregate([
{
$search: {
index: "default",
exists: {
path: "rating"
}
}
},
{ $project: { title: 1, rating: 1, _id: 0, score: { $meta: "searchScore" } } },
{ $limit: 3 }
]);
向量检索($vectorSearch)
相似度算法
在创建向量检索索引时,通过 similarity 参数指定相似度计算方法:
|
算法 |
说明 |
适用场景 |
|
|
欧氏距离,距离越小越相似 |
特征向量空间中的绝对距离度量 |
|
|
余弦相似度,值越大越相似 |
文本嵌入、语义检索(最常用) |
|
|
点积,值越大越相似 |
已归一化的向量,性能优于 cosine |
量化方式
通过 quantization 参数指定向量的量化压缩方式,可降低内存占用:
|
量化方式 |
说明 |
|
|
标量量化,将浮点值映射为整型,降低存储和内存开销 |
|
不指定 |
使用原始浮点精度 |
向量检索查询
// 假设 QUERY_EMBEDDING 是由 AI 模型生成的向量
const QUERY_EMBEDDING = [0.12, 0.45, -0.23, ...];
db.images.aggregate([
{
$vectorSearch: {
index: "vector_index",
path: "embedding",
queryVector: QUERY_EMBEDDING,
numCandidates: 150, // 候选集大小(性能与召回率的权衡参数)
limit: 10 // 返回结果数量
}
},
{
$project: {
_id: 0,
title: 1,
score: { $meta: "vectorSearchScore" } // 获取向量检索相关性得分
}
}
]);
参数说明:
|
参数 |
类型 |
说明 |
|
|
string |
向量检索索引名称 |
|
|
string |
向量字段路径 |
|
|
array |
查询向量,维度必须与索引定义一致 |
|
|
int |
候选集大小,增大可提高召回准确率但消耗更多资源 |
|
|
int |
返回的最近邻结果数量 |
|
|
string |
查询时使用的量化方式(可选) |
混合检索($rankFusion)
使用 $rankFusion 功能需在实例参数设置中将 setParameter.featureFlagRankFusionBasic 和 setParameter.featureFlagRankFusionFull 设置为 true,修改后实例会自动重启生效。
$rankFusion 聚合阶段用于将多个检索管道的结果通过 Reciprocal Rank Fusion(RRF)算法进行融合排序,适用于全文检索与向量检索的混合查询场景。
RRF 算法原理
RRF 算法根据文档在各子管道中的排名计算融合分数:
score = weight × (1 / (rank + 60))
其中 rank 为文档在子管道结果中的排名(从 1 开始),常数 60 为 RRF 平滑参数。当文档出现在多个子管道结果中时,最终分数为各子管道分数之和。
语法与参数
db.collection.aggregate([
{
$rankFusion: {
input: {
pipelines: {
"<pipeline_name_1>": [ /* 子管道 1 */ ],
"<pipeline_name_2>": [ /* 子管道 2 */ ]
}
},
combination: { // 可选
weights: {
"<pipeline_name_1>": number,
"<pipeline_name_2>": number
}
},
scoreDetails: boolean // 可选,默认 false
}
}
]);
参数说明:
|
参数 |
类型 |
必填 |
说明 |
|
|
object |
是 |
命名的子管道映射,每个子管道必须是"有序管道"(以 |
|
|
object |
否 |
各子管道的权重映射,未指定的管道权重默认为 1 |
|
|
boolean |
否 |
是否在结果中包含各子管道的详细评分信息,默认 |
使用示例
全文检索 + 向量检索的混合查询
db.products.aggregate([
{
$rankFusion: {
input: {
pipelines: {
fullTextSearch: [
{ $search: { index: "default", text: { query: "wireless headphones", path: "description" } } },
{ $limit: 20 }
],
vectorSearch: [
{ $vectorSearch: { index: "vector_index", path: "embedding", queryVector: QUERY_VECTOR, numCandidates: 100, limit: 20 } }
]
}
},
combination: {
weights: {
fullTextSearch: 0.3,
vectorSearch: 0.7
}
}
}
},
{ $limit: 10 },
{ $project: { title: 1, score: { $meta: "searchScore" } } }
]);
查看详细评分
db.products.aggregate([
{
$rankFusion: {
input: {
pipelines: {
textSearch: [
{ $search: { index: "default", text: { query: "laptop", path: "title" } } },
{ $limit: 10 }
],
ratingSort: [
{ $sort: { rating: -1 } },
{ $limit: 10 }
]
}
},
scoreDetails: true
}
},
{ $limit: 5 },
{ $project: { title: 1, score: { $meta: "searchScore" }, details: { $meta: "scoreDetails" } } }
]);
子管道要求
每个子管道必须是"有序管道",满足以下条件之一:
-
以
$search阶段开头 -
以
$vectorSearch阶段开头 -
包含
$sort阶段
使用注意事项
-
各子管道的结果数量建议通过
$limit控制,避免处理过多候选文档。 -
weights中未指定的管道默认权重为 1,所有权重值必须为正数。 -
scoreDetails: true会在结果中包含各子管道的排名和分数信息,便于调试和评估融合效果。
scoreDetails 输出格式
当 scoreDetails: true 时,通过 { $meta: "scoreDetails" } 获取的详细评分信息结构如下:
// scoreDetails 输出示例
{
value: 0.03252, // 最终 RRF 融合分数
description: "value output by reciprocal rank fusion algorithm, computed as sum of (weight * (1 / (60 + rank))) across input pipelines...",
details: [
{
inputPipelineName: "textSearch", // 子管道名称
rank: 1, // 该文档在此管道中的排名(从 1 开始)
weight: 1, // 该管道的权重
value: 0.6887, // 该管道原始评分
details: []
},
{
inputPipelineName: "vectorSearch",
rank: 2,
weight: 1,
value: 0.9999,
details: []
}
]
}
// 最终分数计算:1 × (1/(60+1)) + 1 × (1/(60+2)) = 0.01639 + 0.01613 = 0.03252
评分与结果处理
获取检索相关性得分
// 全文检索得分
{ $project: { score: { $meta: "searchScore" } } }
// 向量检索得分
{ $project: { score: { $meta: "vectorSearchScore" } } }
评分修改器
在全文检索操作符中,可通过 score 参数调整评分:
// boost:按倍数提升原始评分
{ text: { query: "crime", path: "genre", score: { boost: { value: 5 } } } }
// 原始评分 0.575 → 提升后 2.874
// constant:设置固定评分值
{ text: { query: "crime", path: "genre", score: { constant: { value: 10 } } } }
// 所有匹配文档评分均为 10
支持的评分修改方式:
-
boost:按倍数提升原始评分 -
constant:设置固定评分值 -
function:自定义函数评分(可引用字段值动态计算)
高亮(Highlight)
返回匹配文本的上下文片段,便于在搜索结果中展示命中关键词:
db.movies.aggregate([
{
$search: {
index: "default",
text: { query: "war", path: "plot" },
highlight: {
path: "plot",
maxCharsToExamine: 500,
maxNumPassages: 3
}
}
},
{
$project: {
title: 1,
_id: 0,
score: { $meta: "searchScore" },
highlights: { $meta: "searchHighlights" }
}
}
]);
storedSource
在索引中存储原始字段值,查询时可直接返回,避免回查集合从而降低延迟。
索引定义:
db.collection.createSearchIndex({
name: "stored_index",
definition: {
mappings: { dynamic: true },
storedSource: {
include: ["title", "genre"]
}
}
});
查询时使用 returnStoredSource:
db.movies.aggregate([
{
$search: {
index: "stored_index",
text: { query: "drama", path: "genre" },
returnStoredSource: true
}
},
{ $project: { title: 1, genre: 1, _id: 0, score: { $meta: "searchScore" } } },
{ $limit: 3 }
]);
Facet 聚合($searchMeta)
使用 $searchMeta 聚合阶段,按分类统计文档数量,常用于搜索结果的分面导航:
db.movies.aggregate([
{
$searchMeta: {
index: "movies_custom_index",
facet: {
operator: {
range: { path: "rating", gte: 8.0 }
},
facets: {
genreFacet: {
type: "string",
path: "genre",
numBuckets: 10
},
yearFacet: {
type: "number",
path: "year",
boundaries: [1990, 2000, 2010, 2020]
}
}
}
}
}
]);
说明:使用 $searchMeta 时,genre 字段需在索引中定义为 stringFacet 类型。
索引管理
|
操作 |
方法 |
|
创建全文检索索引 |
|
|
创建向量检索索引 |
|
|
查看索引列表 |
|
|
查看索引列表(简化) |
|
|
更新索引定义 |
|
|
删除索引 |
|
索引构建与状态
索引创建后,mongot 会在后台异步构建索引。索引的生命周期包含以下阶段:
-
索引定义注册:调用
createSearchIndex后,索引定义立即注册到mongot的索引目录中。此时通过$listSearchIndexes即可看到该索引(返回id、name、type、latestDefinition字段)。 -
初始同步(Initial Sync):
mongot从mongod同步全量数据并构建索引。对于大集合,此过程可能持续数分钟到数十分钟。 -
稳定状态(Steady State):初始同步完成后,索引进入稳定状态,此时索引可正常响应查询请求。
如何确认索引已就绪:
-
$listSearchIndexes和getSearchIndexes()在索引创建后立即返回索引信息,但这不代表索引已构建完成。当前版本的返回结果中不包含索引状态字段。 -
确认索引就绪的可靠方式是尝试执行
$search查询:若索引尚未就绪,查询将返回错误;若查询成功返回结果,则表明索引已可用。 -
也可通过 mongot 日志确认:当日志中出现
Transitioning from INITIAL_SYNC to STEADY_STATE消息时,表示该索引已完成构建并进入可查询状态。
索引更新
更新索引定义时,mongot 会在后台重建新索引,期间旧索引仍可支持查询。新索引构建完成后自动替换旧索引,整个过程对查询无感知。
注意事项
-
索引构建延迟:索引创建后需等待构建完成才能查询。通过
$listSearchIndexes能看到索引信息不代表索引已就绪,应通过实际执行$search查询或查看 mongot 日志来确认索引状态。 -
索引更新:更新索引定义时,
mongot会在后台重建新索引,旧索引仍可支持查询,新索引完成构建后自动替换。 -
数据同步延迟:数据写入后通常在秒级延迟内即可检索,延迟受实例写入负载和文档大小等因素影响。
-
静态映射推荐:生产环境建议使用静态映射控制索引范围,减少存储开销。
-
filter 性能优势:
compound查询中的filter子句不计算评分,性能优于must,适合精确过滤条件。 -
向量维度一致性:向量检索索引的
numDimensions必须与实际嵌入模型输出维度一致。 -
分析器命名格式:内置分析器使用
lucene.前缀格式(如lucene.standard)。 -
wildcard/regex 注意事项:在
string类型(已分词)字段上使用时必须设置allowAnalyzedField: true,且匹配发生在 token 级别而非原始文本级别。 -
备份恢复:通过备份恢复的新实例不包含 Search 索引,需在新实例上重新开通 Search 服务并重建索引。
-
数据迁移:使用 DTS 等工具迁移数据时,Search 索引不会被同步,需在目标实例手动创建。