node.js - Mongoose:通过 findOneAndUpdate 查询使用对象数组的总和更新根数据属性不起作用
问题描述
我正在尝试使用 Node mongoose lib 更新 mongo 集合中的数组元素之一。这是我的 mongo 架构的样子:
{
"_id": ObjectId("5f8a94ccc8452643f1498419"),
"private": false,
"score": 2000,
"questions": [{
"_id": ObjectId("5f8a94e8c8452643f149841c"),
"order": 1,
"category": "TEXT",
"definition": "about us",
"score": 1,
}, {
"_id": ObjectId("5f8a94e8c8452643f149841d"),
"order": 2,
"category": "HTML",
"definition": "about us",
"score": 0.5
}]
}
我正在更新问题数组中的分数,要更新的根数组的分数属性是数组分数的总和,即
root score => question array1.score + array2.score
我使用了下面的猫鼬功能:
Model.findOneAndUpdate(
{
_id: id,
"questions._id": qid,
},
{
'$set': {
'questions.$.order': 1,
'questions.$.score': 1,
'questions.$.type': 'HTML',
'$sum': { 'score': 'questions.score' }
}
})
虽然所有其他属性都在更新,但根分数永远不会更新。
注意:$setoninsert不是一个选项,因为在这种情况下,upsert始终为false。
这是否有可能使用单个查询来执行这两个更新?
解决方案
从 MongoDB 4.2 开始,您可以将更新与聚合管道一起使用,
$set
更新 id 匹配的匹配问题qid
$set
questions
从数组的分数更新根分数
let id = mongoose.Types.ObjectId("5f8a94ccc8452643f1498419");
let qid = mongoose.Types.ObjectId("5f8a94e8c8452643f149841c");
let question = {
score: 1,
order: 1,
category: "TEXT"
};
Model.findOneAndUpdate(
{ _id: id },
[{
$set: {
questions: {
$map: {
input: "$questions",
in: {
$mergeObjects: [
"$$this",
{
$cond: [
{ $eq: ["$$this._id", qid] },
question, // add update fields in object
{}
]
}
]
}
}
}
}
},
{
$set: {
score: {
$reduce: {
input: "$questions",
initialValue: 0,
in: { $add: ["$$value", "$$this.score"] }
}
}
}
}]
)
推荐阅读
- c - Eclipse 将项目重构为可执行文件和库
- php - 未遵循PHP递归循环序列
- angular6 - 如何在 ng2-smart-table 的下拉列表中设置多项选择?
- moodle - MoodleCloud 是否公开了可供工具与之集成的 API?
- terminal - “令牌不存在”
- sql - 发货日期作业
- excel - VBA 文件目录链接到 Outlook
- python - 如何将图像保存为二进制压缩的 .tiff python?
- firefox - 在 Firefox Desktop 和 Firefox Android 之间传输/同步 WebExtension 数据
- forms - MS Access 表单无法在不同的显示器上正确居中