简体   繁体   中英

pushing JSON document in subdocument inserts only ObjectId

I've created a Model in Mongoose:

var userWalletSchema = new Schema({
   userid: {type: Schema.ObjectId, ref: 'users'},
   Transactions: [{
         Datum: {Type: Date},
         CODE: {Type: String},
         aantal: {Type: Number},
         soortTransactie: {Type: String}, 
         bedrag: {Type:Number}
   }]
},
{collection:'userWallet'});

I insert the following document:

var newRecord = { Datum: '2017-12-21T00:00:00+01:00',
CODE: 'IE00B3VWN518',
aantal: 48,
soortTransactie: 'Aankoop',
bedrag: 478 };

With this code:

UserWallet.findOneAndUpdate(
   { userid: mongoose.Types.ObjectId(req.user.id)},
   { $push: {Transactions: newRecord}},
   { upsert: false },
   function (err, model) {
      console.log(err);
      console.log(model);
   });

I've tried several permutations and options, but all give the same result: a record is pushed to the Transactions array, but it always contains the value _id: ObjectId('5a490c3376dfb6630464f6e1') (Id changes of course), but never the document I intended to insert.

What goes wrong here? I'd expect that inserting a new subdocument would be easy.

Solution: I've found the problem. I typed "Type" with a capital T and the word should be all lowercase in JavaScript. So silly, took me 2 days to discover it.

You can try another approach. First find the object, add the new Transaction to the object, and save it.

UserWallet.findOneAndUpdate({ userid: mongoose.Types.ObjectId(req.user.id)}, function(err, userWallet) {
    userWallet.Transactions.push(newRecord);
    userWallet.save();
});

Your approach in terms of saving is okay. If you check your schema, what you are saving is an ObjectId and not necessarily an actual object.

If you want to save objects of type User instead, then you can put the actual User Model in your UserWallet scheme declaration.

However, the approach I would recommend for your situation is to keep things just the way they are and use population when retrieving userWallets.

Example:

UserWallet.find().populate('user_id').exec(function(err,userWallets){

});

Now the user_id field of UserWallet will have the actual user object that is being referenced with the ObjectId. You can read more about population in the documentation

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM