0

I am using sub-documents in mongodb.

With one level of sub-documents, I can update documents with

Parent.findOneAndUpdate({ _id: parentId, 'children._id': childId }, {
  $set: {
    'children.$.name': name
  }
}, (err, doc) => {
  ...
});

but I have problems doing the same for another level of sub-documents, i.e.

Parent.findOneAndUpdate({ _id: parentId, 'children._id': childId, 'children.grandchildren._id': grandchildId }, {
  $set: {
    'children.$.grandchildren.$.name': name
  }
}, (err, doc) => {
  ...
});

Is the positional operator ($) limited to only 1 level of subdocuments?

Jamgreen
  • 10,329
  • 29
  • 113
  • 224

1 Answers1

0

Positional Operator ($) only supports one level and also the first matching element. As a workaround what you can do is this,

$set: { 'children.$.grandchildren.0.name': name }

I think this issue is more clearly explained here

Community
  • 1
  • 1
Ravindu Nirmal Fernando
  • 4,272
  • 4
  • 18
  • 29
  • Oh. Thanks. But won't your workaround just take the very first object in the grandchildren array instead of the one that matches with my `grandchildId`? – Jamgreen Sep 04 '16 at 15:09
  • Yes it would select the very first object as you have mentioned. But you can use the **foreach** function of the mongodb and update each grandchild's name which is matching the `grandchildId`. The link I provided with my answer also got one answer where you can refer. [Here is the link for that answer](http://stackoverflow.com/a/18721690/4334340) – Ravindu Nirmal Fernando Sep 04 '16 at 16:06
  • The feature has been implemented in 2017 https://jira.mongodb.org/browse/SERVER-831 – FooBar Jun 30 '21 at 18:44