0

I have following structure of my document:

{
    "daily": [
        {
            "general": [
                {
                    "status": false,
                    "_id": "5e728265f4796c0017203662",
                    "title": "Sport"
                },...
            ]
        }
    ]
}

I would like to pull the the document inside the "general" Array by it's "_id".

I tried several things but nothing seems to work for me.

Every help will be appreciate :)

4
  • Can you post your code which you have tried so far? Commented Mar 19, 2020 at 6:30
  • what should be the response ? Commented Mar 19, 2020 at 6:31
  • Generate ObjectId first then it will be easy to update Commented Mar 19, 2020 at 6:38
  • I don't want to have a repsonse. I just want to remove the embedded document inside of the "general" array @Kun Commented Mar 19, 2020 at 7:26

2 Answers 2

2

The update query to pull the sub-document from the nested array field general using the _id:

ID = "5e728265f4796c0017203662"

db.collection.update(
 { "daily.general._id": ID },
 { $pull: { "daily.$.general": { _id: ID } } }
)
Sign up to request clarification or add additional context in comments.

1 Comment

Field _id is typically an ObjectId, so I assume it should be rather ID = ObjectId("5e728265f4796c0017203662")
0

This can only be done in Mongo 4.2+, where they introduced pipeline'd updates.

Now we can use aggregation expressions to update documents:

db.collection.updateOne(
    {},
    [
        {
            $set: {
                "daily": {
                    $map: {
                        input: "$daily",
                        as: "item",
                        in: {
                            "general": {
                                $filter: {
                                    input: "$$item.general",
                                    as: "datum",
                                    cond: {$ne: ["$$datum._id", "5e728265f4796c0017203662"]}
                                }
                            }
                        }
                    }
                }
            }
        }
    ]);

Or if objects in daily have more than just the general field you can do it like this:

db.collection.updateOne(
    {},
    [
        {
            $set: {
                "daily": {
                    $map: {
                        input: "$daily",
                        as: "item",
                        in: {
                            $mergeObjects: [
                                "$$item",
                                {
                                    "general": {
                                        $filter: {
                                            input: "$$item.general",
                                            as: "datum",
                                            cond: {$ne: ["$$datum._id", "5e728265f4796c0017203662"]}
                                        }
                                    }
                                }
                            ]
                        }
                    }
                }
            }
        }
    ]);

Unfortunately for any other Mongo version this is not possible, you'll have to restructure your data or do it in code.

3 Comments

It is possible without aggregation expression, see answer above (which is even much shorter).
No it's not, since when is the length of an answer an indicator if its correct or not? feel free to use the "short" answer. i have a feeling it won't work.
The code from prasad_ is much shorter. Your code is working correctly but your statement "This can only be done in Mongo 4.2+, where they introduced pipeline'd updates." is wrong. $[<identifier>] was introduced in Mongo 3.6

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.