MongoDB, add a new {field: value} to an existing embedded document with multilevel bitmap?

What I'm trying to do is add a new {field: value} for the blog post. For example, if I wanted to start tracking impressions on .blog_posts.url: "http://www.example.com/01.html" sites, how do I add this impression attribute for this blog post?

My current document structure:

{ email_address: ' webmaster@example.com ', password: 'random_password', first_name: 'John', last_name: 'Doe', user_type: 'WEBMASTER', newsletter: 'NO', websites: [{ main_title: 'My Blog Website', main_url: 'http://www.example.com', blog_posts: [{ url: 'http://www.example.com/01.html', title:'My first blog post', description: 'My first description.' }, { url: 'http://www.example.com/02.html', title: 'My second blog post', description: 'My second description.' }, { url: 'http://www.example.com/03.html', title: 'My third blog post', description: 'My third description.' }, { url: 'http://www.example.com/04.html', title: 'My fourth blog post', description: 'My fourth description.' }] }] } 

Here is what I thought would work using updating and creating upsert TRUE.

db.my_collection.update ({'websites.blog_posts.url': 'http://www.example.com/01.html'}, {'$ set': {'websites.blog_posts.impressions': 549}} , true)

The error I received: * cannot attach to the array using the string field name [blog_posts] *

Maybe the "$ set" is wrong for this, or maybe I can't reference this depth using dot notation? I just started using MongoDB yesterday, any help would be great.

Thanks!

+6
source share
1 answer

What you are trying to do is not possible given your pattern. Dot notation can be multi-level, but if there is more than one level, which is an array, it can no longer be considered using the positioning operator "$".

eg. you will need to do:

 db.my_collection.update( {'websites.blog_posts.url': 'http://www.example.com/01.html' }, {'$set': {'websites.$.blog_posts.$.impressions': 549}}, true ); 

But the presence of two position operators in the update is not possible, since MongoDB can determine the position of an element in the first array.

Your only option is to reverse engineer your scheme to have a dedicated collection of user websites (which is better for other reasons in this case too).

+5
source

Source: https://habr.com/ru/post/900201/


All Articles