Mongo DB insert into a sub document if sub documen

2019-05-04 05:36发布

问题:

I'm very new to mongodb and i'm a little lost.

I have mongo db collection that looks like this :

  ({
    _id:id ,
    createdAt: new Date(),
    name:name,
    friends : [{name:1,children:[{name:sarah,age:12}]}],
    dogs : [{}]
  });

I would like to be able to insert a new element in the friends array if the name doesnt exist and a children element to that new array.

Pseudo code would be

If Directory.find id.friends.name = true

update and add a new children document {name:"sarah",age:5}

else

make a new friend element with a new children subdocument

After alot of research it seems that people are recommending the use of $exist but i can't find a way to use it in a sub document'

I've come up with this but it's not really working and i'm wondering how could i use that for my if else stament:

db.Directory.find({_id:id},{friends.name:"foo", {"$exists": True}})

For the actual query

db.Directory.update(
    { _id: id, 'friends.name': "foo" },
    {$push: {'friends.$.children':  {name:"x",age:"yy"}}}
)

And if it doesn't exist :

db.Directory.insert(
    { _id: id, 'friends.name': "foo" },
    {$push: {'friends.$.children':  {name:"x",age:"yy"}}}
)

But it's not really working , i'm not sure if there is something wrong in my formulas as it's a lot of trials and errors from research. I also don't really know if that the proper way to do it as i couldn't find anything on a value existing on sub documents and was planning on trying to do a Find() search store the value and then test for true or false on the result in JS to make either of the update/insert calls.

Hope someone can help

Edit : Let's say i want to add {name:john,age:15} to that friend name:1

friends : [{name:1,children:[{name:sarah,age:12}]}]

I'd like the output to be

friends : [{name:1,children:[{name:sarah,age:12},{name:john,age:15}]}]

or if name 1 doesnt exist

friends : []

make it so that it output

friends : [{name:1,children:[{name:john,age:15}]}]

Updated example :

case one :

friends : []

i add a new friend name "josh" with one child sarah , age 12 i get:

friends : [{name:"josh",children:[{name:sarah,age:12}]}]

This is perfect.

Now i add a new friend name 2 with children tom 15.

Nothing happens.

after , I want to add a new child to josh , timmy age 15

I get :

friends : [{name:"josh",children:[{name:timmy,age:12}]}]

And sarah disapeared.

回答1:

Please try to do it through Bulk operation, add one new friend through $addToSet operator and update friend through $set operator, update it after you making your question more clearly.

var bulk = db.Directory.initializeOrderedBulkOp();

// if `friends` is `[]`, push the empty children firstly through addToSet
bulk.find({_id: id, 'friends.name': {$exists: false}}).updateOne(
     {$addToSet: {friends: {name: 1, children: []}});

// if we find the match friend, update this one through `$set`
bulk.find({_id: id, 'friends.children.name': 'john'}).updateOne(
    {$set: {'friends.$.children': {name: 'john', age: 22}}});

// if we cannot find match friend, insert the new one through `$addToSet`
bulk.find({_id: id, 'friends.children.name': {$ne: "john"}}).updateOne( 
    {$addToSet: {'friends.0.children': {name: 'john', age: 12}}});

bulk.execute();