如何使用MongoDB / Mongoose中的先前值更新字段

时间:2017-05-03 21:20:44

标签: node.js mongodb mongoose

例如,我有一些看起来像这样的文件:

{
    id: 1
    name: "foo"
}

我想将另一个string附加到当前name字段值。

我使用Mongoose尝试了以下操作,但它没有工作:

Model.findOneAndUpdate({ id: 1 }, { $set: { name: +"bar" } }, ...);

2 个答案:

答案 0 :(得分:2)

您无法引用要更新的文档的值,因此您需要一个查询来检索文档,另一个查询需要更新它。自2016年以来OPEN州的情况似乎有feature request

如果您的文档集如下:

{ "_id" : ObjectId("590a4aa8ff1809c94801ecd0"), "name" : "bar" }

使用MongoDB shell,你可以这样做:

db.test.find({ name: "bar" }).snapshot().forEach((doc) => {
    doc.name = "foo-" + doc.name;

    db.test.save(doc);
});

该文件将按预期更新:

{ "_id" : ObjectId("590a4aa8ff1809c94801ecd0"), "name": "foo-bar" }

请注意.snapshot()来电。  这可以确保查询不会多次返回文档,因为由于文档大小的增加,插入的写操作会移动它。

将其应用于您的Mongoose示例,如this official example

中所述
Cat.findById(1, (err, cat) => {
    if (err) return handleError(err);

    cat.name = cat.name + "bar";

    cat.save((err, updatedCat) => {
        if (err) return handleError(err);

        ...
    });
});

值得一提的是聚合框架中有一个$concat运算符,但遗憾的是你不能在update查询中使用它。

无论如何,根据您的需要,您可以将其与$out运算符一起使用,以将聚合结果保存到新集合中。

使用相同的示例,您将执行以下操作:

db.test.aggregate([{
    $match: { name: "bar" }
}, {
    $project: { name: { $concat: ["foo", "-", "$name"] }}
}, {
    $out: "prefixedTest"
}]);

将创建一个新的集合prefixedTest,其中包含以下文档:

{ "_id" : ObjectId("XXX"), "name": "foo-bar" }

作为参考,还有一个关于同一主题的另一个有趣的问题,其中有几个答案值得一读:Update MongoDB field using value of another field

答案 1 :(得分:0)

如果这仍然有意义,那么我有针对MongoDB 4.2的解决方案。

我遇到了同样的问题,我的"projectDeadline"文档的"project"字段是Array类型(["2020","12","1"]

使用Robo3T,我通过SRV链接连接到了MongoDB Atlas数据库。然后执行以下代码,它对我有用。

初始文档:

{
  _id             : 'kjnolqnw.KANSasdasd',
  someKey         : 'someValue',
  projectDeadline : ['2020','12','1']
}

CLI命令:

db
.getCollection('mainData')
.find({projectDeadline: {$not: {$eq: "noDeadline"}}})
.forEach((doc) => {

    var deadline = doc.projectDeadline;
    var deadlineDate = new Date(deadline);

    db
    .mainData
    .updateOne({
        _id: doc._id}, 
        {"$set": 
            {"projectDeadline": deadlineDate}
        }
    )}
);

结果文档:

{
  _id             : 'kjnolqnw.KANSasdasd',
  someKey         : 'someValue',
  projectDeadline : '2020-12-01 21:00:00.000Z'
}