0

I am completely mystified (and supremely frustrated). How do I create this call using the mongoc library?

I have the following doc structure in the collection

{_id: myOID, 
  subsriptions: {
     newProducts: true, 
     newBlogPosts: true,
     pressReleases: true,
  }
}

I want to remove one of the subscriptions, for example, the user no longer wants to receive press releases from me.

This works in the mongo shell. Now I need to do it in C code

updateOne({_id: myOID}, [{'$unset': 'subscriptions.pressReleases'}], {})

Note how the update parameter in the Mongo shell is an anonymous array. I need to do that for the bson passed in as the update parameter in the mongoc_collection_update_one() API call.

The C code for updateOne is

 mongo_status = mongoc_collection_update_one (mongo_collection,
                                mongo_query,
                                mongo_update,
                                NULL, /* No Opts to pass in */
                                NULL, /* no reply wanted */
                                &mongo_error);

Also note that in the aggregate() API, this is done with

{"pipeline" : [{'$unset': 'elists.lunch' }] }

Neither the updateOne() shell function nor the mongoc_collection_update_one() API call accept that, they want just the array.

How do I create the bson to use as the second parameter for mongoc_collection_update_one() API call?

  • For that operation you shouldn't need a pipeline. Does it work if you passa bson object instead of an array? like `updateOne({_id: myOID},{'$unset':'subscriptions.pressReleases'})` – Joe Jul 06 '20 at 01:49
  • Oddly, it works as you show it for $set, but for $unset it wants the array. This is also true of the mongo shell. For the shell: updateOne({_id: myOID},{'$set': {'subscriptions.pressReleases' : true} }) – DB user10082797 Jul 06 '20 at 02:24
  • Oops, the `$unset` update operator takes an object, like: `updateOne({_id: myOID},{'$unset':{'subscriptions.pressReleases':1}})` – Joe Jul 06 '20 at 02:27
  • Yes, that is working. Thank you. So.... I still have a lingering question about creating an anonymous array. Any thoughts about that? – DB user10082797 Jul 06 '20 at 02:47
  • That should just be an ordinary array of type bson_t. – Joe Jul 06 '20 at 02:59

1 Answers1

0

Joe's answer works and I am able to accomplish what I need to do.

The $unset update operator takes an object, just like $set.

updateOne({_id: myOID},{'$unset':{'subscriptions.pressReleases': true}})

OR perhaps even better

updateOne({_id: myOID},{'$unset':{'subscriptions.pressReleases': {'$exists': true}}})

which will remove the subscription flag no matter what the value is for that field.

Doing it this way does not require an anonymous array (which I still don't know how to create).