【问题标题】:How to update all nested documents of an array in a selected document in mongoose?如何在猫鼬的选定文档中更新数组的所有嵌套文档?
【发布时间】:2019-06-03 21:47:16
【问题描述】:

在某种情况下,我需要更新嵌套在 Mongoose 模型中的数组中的所有文档的字段。

我将上传图像的新嵌套文档添加到用户集合中,我需要将所有先前文档的“is_available”设置为 false,并且只有新插入文档的“is_available”字段为 true。

我搜索并发现的只是更新具有特定 ID 或过滤器的嵌套文档。但我没有找到更新模型中数组的所有嵌套文档的特定字段的方法。

我的模特:

var mongoose = require("mongoose");
var Schema = mongoose.Schema;

var UsersSchema = new Schema({
  name: { type: String, default: "" },
  lastname: { type: String, default: "" },
  images: [{
    dir: { type: String },
    is_available: { type: Boolean }
  }]
});

var Users = mongoose.model("Users", UsersSchema, "users");
module.exports = Users;

实际结果:


{ 
    "_id" : ObjectId("5ce950aa4sw435ty503ab83b"), 
    "name" : "Sina", 
    "image" : [
        {
            "_id" : ObjectId("5cf4dd3da6b4gb6bcf9c6dc1"), 
            "dir" : "profiledirectory/804eafeaf8acc40a3d6.jpg", 
            "is_available" : true
        }, 
        {
            "_id" : ObjectId("5cf4fffs2419316bddffgg82"), 
            "dir" : "profiledirectory/d85b01ac40fa6b1a7c1.jpg", 
            "is_available" : true
        }, 
        {
            "_id" : ObjectId("5cf4ff334fhd316bef2fdt40"), 
            "dir" : "profiledirectory/512d9d19da7a4322b37.jpg", 
            "is_available" : true
        }
    ]
}

预期结果:


{ 
    "_id" : ObjectId("5ce950aa4sw435ty503ab83b"), 
    "name" : "Sina", 
    "image" : [
        {
            "_id" : ObjectId("5cf4dd3da6b4gb6bcf9c6dc1"), 
            "dir" : "profiledirectory/804eafeaf8acc40a3d6.jpg", 
            "is_available" : false
        }, 
        {
            "_id" : ObjectId("5cf4fffs2419316bddffgg82"), 
            "dir" : "profiledirectory/d85b01ac40fa6b1a7c1.jpg", 
            "is_available" : false
        }, 
        {
            "_id" : ObjectId("5cf4ff334fhd316bef2fdt40"), 
            "dir" : "profiledirectory/512d9d19da7a4322b37.jpg", 
            "is_available" : true
        }
    ]
}
Code Snippet:

let updateQuery = {
  $set: { 'image.$.is_available': false },
  $push: {
    image: [
      {
        dir: "profiledirectory/558bb6938ecd54bde556af122a4.jpg",
        is_available: true
      }
    ]
  }
}


let findQuery = { _id: req.body.user_id }

Users.findOneAndUpdate(findQuery,
  updateQuery, function (err, doc) {
    if (err) {
      res.send(err.message)
    } else {
      res.send('successful')
    }
  })

【问题讨论】:

  • 你试过什么查询?
  • 我更新了我的问题并添加了代码 sn-p
  • 我的答案有效吗?
  • @SaurabhMistry 我将您的答案与@mourya venkat aswer 结合起来。 user.save((err,updated)… 对我不起作用,我使用 eventObject.findOneAndUpdate(... 来处理那部分。谢谢

标签: javascript node.js mongoose


【解决方案1】:

根据您提到的,您不断将对象添加到图像字段中,并且每次添加新对象时,都应使用 is_available:false

覆盖现有对象
    eventObject.find(query).lean().exec(function (err, response) {
        if (err) {
            logger.error(err);
            return reject(err.message)
        }
        // Assuming there will be only one record based on the query you make
        if(response.length>0){
            response[0].images = response.images.map((image)=>{
                image.is_available = false
                return image
            })

            // Now append your new image to the modified response
            response[0].images.push(newimage)// this should be the newImage object
            // Now use findOneAndUpdate to update the existing doc by querying with id or according to your usecase

            eventObject.findOneAndUpdate(query, response[0], { upsert: true }, (err, data) => {
            if (err) {
                return reject(err)
            }
            logger.info(data);
            return resolve(newData);
        })
        }
    })

所以基本的方法是,

  1. 从数据库中获取文档
  2. 更新文档内容
  3. 添加新数据
  4. 使用更新的数据更新记录。

【讨论】:

    【解决方案2】:

    上传文件后,你必须找到用户

      // after upload image 
    
      User.findOne({_id:req.user._id}).lean().exec((err,user)=>{
            if(!err && user){
                  // setting all previous images to false 
                  user.image.forEach(image=>{
                        image.is_available=false;
                  });
                  // now pushing new uploded item to image array
            let newImage={"dir" : "path of uploaded item here"  , "is_available" : true};
    
                  user.image.push(newImage);
                  user.save((err,updated)=>{
                       if(!err && updated){ 
                         return res.status(200).json({status:"success",message:"User updated"});
                       }
                  });
            }
      });
    

    【讨论】:

      猜你喜欢
      • 2019-09-30
      • 1970-01-01
      • 2012-02-15
      • 2015-04-21
      • 1970-01-01
      • 1970-01-01
      • 2011-10-25
      • 2020-03-01
      相关资源
      最近更新 更多