问题描述
我正在尝试创建一个mongo find查询,该查询使用一个字符串输入来搜索mongo文档,但是我找不到能够满足我所有三个要求的语法:
仅在以下情况下才应找到该文档
:-
输入字符串包含在(或等于)字段值之内。
-
忽略大小写(如果仅字母大小写不同则匹配)
-
变音符号敏感(输入与不同变音符号的字母不匹配,即对待o与ö不同)
假设我的收藏夹中有以下文件:
[
{
_id: <some object id>,title: 'home',},{
_id: <some other object id>,title: 'HoMe',title: 'AllTheWayHome.',title: 'höme',}
]
对于我的项目,正确的实现应返回除以外的所有文档作为最后一个文档(因为变音符号使之不匹配)。
这是我尝试过的...
1)使用“ RegExp”
当创建一个新的“ RegExp”对象并将其用作查询对象时,我可以进行“包含”搜索,最后的“ i”使其不区分大小写。
const query = { title: new RegExp(`.*${searchText}*.`,'i') }
return collection.find(query).toArray();
^这种方法的问题在于,我还没有找到使它变音符号敏感的方法。
2。使用“正则表达式文字”
有趣的是,如果我尝试这样做,它将永远不会匹配任何文档(我希望它的工作方式与“新RegExp”相同)。
const query = { title: /.*${searchText}*./i }
return collection.find(query).toArray();
^这个正则表达式似乎可以匹配任何内容,并为searchText的每个可能值返回所有文档。
3。使用“ $ text”和“ $ search”
浏览Mongo文档后,我发现可以使用这种方便的“ $ text”语法,因此我尝试了如下查询:
const query = {
$text: {
$search: searchText,$caseSensitive: false,$diacriticSensitive: true
}
}
return collection.find(query).toArray();
^但是,这似乎并没有执行我要查找的“包含”搜索。 (例如,“ home”与“ AllTheWayHome”不匹配。)
在阅读了有关该问题的一些答案之后,我发现了一条有趣的评论,上面有很多反对意见,说这种“ $ text,$ search”语法不能“包含”句点。 (这仍然是真的吗?)
注意:我已在“标题”字段上添加了文本索引,但仍得到完全相同的结果(仅完全匹配字符串匹配,忽略变音符号)。
否,实际文本运算符不允许执行“包含”,因此它 将仅返回完全匹配的单词,这是当前3.0版中唯一的选项 是使用正则表达式,即db.users.find({username:/ son / i}) 查找包含“儿子”(不区分大小写)的每个用户
因此,总而言之,我感到非常困惑,并且希望获得有关如何实现我在此目标的任何建议。 ?
谢谢!
解决方法
我尝试了第三种方法,它对我有用。
我认为您可能错过的唯一事情可能是在text index
字段上添加title
。
从mongo文档中:-
$ text对用文本索引索引的字段的内容执行文本搜索。
使用以下命令添加索引,然后尝试运行查询。
db.collection.createIndex( { title: "text" } )
编辑:-
- 这些是我尝试过的文件。
- 出于测试目的,我在
student
集合中插入了记录。这里是此收藏集上indexes
的屏幕截图。
- 这是查询和结果集。它包括
All the way home
和排除的höme
。