我正在尝试找出这段代码失败的原因:
db.restaurants.drop();
db.restaurants.insertMany( [
{ "_id" : 1, "borough" : "Manhattan"},
] );
db.restaurants.createIndex({
"borough": "text"
})
db.restaurants.aggregate([
{ $match: { $text: { $search: "a" } } },
{ $sort: {score: {"$meta": "textScore"}}},
{ $project: {"_id": true}},
])
错误输出:
uncaught exception: Error: command failed: {
"ok" : 0,
"errmsg" : "FieldPath field names may not start with '$'.",
"code" : 16410,
"codeName" : "Location16410"
} : aggregate failed :
_getErrorWithCode@src/mongo/shell/utils.js:25:13
doassert@src/mongo/shell/assert.js:18:14
_assertCommandWorked@src/mongo/shell/assert.js:639:17
assert.commandWorked@src/mongo/shell/assert.js:729:16
DB.prototype._runAggregate@src/mongo/shell/db.js:266:5
DBCollection.prototype.aggregate@src/mongo/shell/collection.js:1058:12
@(shell):1:1
我知道这与项目声明有关...
先谢谢你!
-丹尼尔
答案 0 :(得分:3)
您的问题几乎与此 Mongodb 4.4.0 FieldPath field names may not start with 相似,我有 answered 解决方案,唯一的区别是投影字段和一些用例!
经过大量研究,我在投影中的使用部分下找到了以下关于查找和聚合函数text-score-metadata-meta-textscore的一般说明,
<块引用>{ $meta: "textScore" }
表达式可以是投影文档的一部分,以包含文本分数元数据。
$meta
表达式可以出现在包含或排除投影中。
如果您将表达式设置为文档中已存在的字段名称,则投影的元数据值将覆盖现有值。
粗体句上方清除,如果您在 $project
阶段之后使用 $sort
阶段,score
或文本索引字段 borough
应包含或排除,
根据您尝试的解决方案:
db.restaurants.aggregate([
{ $match: { $text: { $search: "a" } } },
{ $sort: { score: { "$meta": "textScore" } } },
{
$project: {
"_id": true, // or _id: 1
"borough": false // or borough: 0
}
},
// or by default _id would be included
/*
{
$project: {
"borough": false // or borough: 0
}
},
*/
// or below will work but this will work as exclusion projection, so you need to specify your other fields to exclude,
/*
{
$project: {
"_id": true, // or _id: 1
"score": false, // or score: 0
}
}
*/
// or by default _id would be included
/*
{
$project: {
"score": false, // or score: 0
}
},
])
还有其他方式,我会推荐这种方式
$project
和 $sort
阶段,db.restaurants.aggregate([
{ $match: { $text: { $search: "a" } } },
{ $project: { "_id": true } },
{ $sort: { score: { "$meta": "textScore" } } }
])