这对我的同事MongoDB和NodeJs Devs来说是一个挑战
我有一个搜索表单,用户可以在其中输入以下内容:
225/65R16 71T K715 Hankook
至于我的mongodb,我有一个包含以下文档的集合:
1- { _id: SomeId, Description: 225/65R16 71T K715, Brand: Hankook, Ref: 123455 }
2- { _id: SomeId, Description: 225/65R16 71T K715, Brand: Continental, Ref: 123456 }
3- { _id: SomeId, Description: 225/65R16 94T Energy, Brand: Hankook, Ref: 123457 }
我该怎么做才能在搜索下面的任何组合时获得上述文档1和3的结果?
组合清单:
Hankook
225/65R16
225/65R16 Hankook
225 Hankook
225 Han
答案 0 :(得分:1)
您可以尝试创建索引:
db.yourollection.createIndex({"Description":1,"Brand":1})
然后通过搜索值,例如:
mongoosemodel.find({$text:{$search: 225/65R16 Hankook}},{Description:1,Brand:1})
而且,如果您获得的结果超出预期,则可以使用Javascript进行过滤。
答案 1 :(得分:1)
您可以使用regular expressions匹配字段的开头,然后使用OR operator。
假设以下文件。
{ "Description" : "225/65R16 71T K715", "Brand" : "Hankook", "Ref" : 123455 }
{ "Description" : "225/65R16 71T K715", "Brand" : "Continental", "Ref" : 123455 }
{ "Description" : "225/65R16 94T", "Brand" : "Hankook", "Ref" : 123455 }
以下查询会返回预期结果。
> db.test.find({$or: [{Description: {$regex: '^225/65R16'}, Brand: {$regex: '^Hankook'}}]})
{ "Description" : "225/65R16 71T K715", "Brand" : "Hankook", "Ref" : 123455 }
{"Description" : "225/65R16 94T", "Brand" : "Hankook", "Ref" : 123455 }
> db.test.find({$or: [{Description: {$regex: '^225'}, Brand: {$regex: '^Han'}}]})
{ "Description" : "225/65R16 71T K715", "Brand" : "Hankook", "Ref" : 123455 }
{ "Description" : "225/65R16 94T", "Brand" : "Hankook", "Ref" : 123455 }
对于225/65R16
,虽然无法避免匹配文档编号2,但查询不包含足够的消歧信息。
答案 2 :(得分:1)
这是一个基于node.js,javascript和猫鼬的示例
您可以在集合的多个字段中查找“搜索词”或“搜索词”,如下所示:
var searchTerm = 'Hankook'; // put your search term here
YourMongooseModel.find({
$or: [
// in this example we want to search at two fields 'Description' and 'Brand'
// however you can put any fields as you desire
{"Description": {$regex: searchTerm, $options: "i"}},
{"Brand": {$regex: searchTerm, $options: "i"}}
]
}, function (err, docs) {
if(docs) {
// handle retreived docs here
}
});
希望这会有所帮助。谢谢
答案 3 :(得分:0)
使用聚合来连接搜索字段,然后只使用正则表达式:
// Build a regex from your string,
// Example : containing exactly all word, no order
enter code here
var a = "225/65R16 71T K715 Hankook"
var ar = a.split(new RegExp("\\s")); // [ '225/65R16', '71T', 'K715', 'Hankook' ]
var estr = ""
ar.forEach(function(e){ estr += "(?=.*\b"+e+"\b)";});
var re = new RegExp("^.*"+estr+".*$"); // /^.*(?=.*\b225\/65R16\b)(?=.*\b71T\b)(?=.*\bK715\b)(?=.*\bHankook\b).*$/
enter code here
db.a.aggregate([
{
$project:{
st: {$concat:["$Brand"," ", "$Description"]},
_id:1,
Description:1,
Brand:1,
Ref:1
}
},
{
$match:{
st: /^(?=.*\b225\/65R16\b)(?=.*\b71T\b)(?=.*\bK715\b)(?=.*\bHankook\b).*$/
}
}
])
// output { "_id" : ObjectId("582f009da52585177f054ddc"), "Description" : "225/65R16 71T K715", "Brand" : "Hankook", "Ref" : "123455", "st" : "Hankook 225/65R16 71T K715" }