Reputation: 21
The $match expression on mongodb's stitch application does not work properly.
I am trying to set up a simple update trigger that will only work on one field in a collection.
The trigger setup provides a $match aggregation which seems simple enough to set up.
For example if I want the trigger to only fire when the field "online" in a specified collection gets set to "true" I would do:
{"updateDescription.updatedFields":{"online":"true"}}
which for a stitch trigger is the same as:
{$match:{{updateDescription.updatedFields:{online:"true"}}}
The problem is when i try to match an update on a field that is an object.(for example hours:{online:40,offline:120}
For some reason $exists or $in does not work So doing:
{"updateDescription.updatedFields":{"hours":{"$exists":true}}
does not work,neither does something like:
{"updateDescription.updatedFields":{"hours.online":{"$exists":true}}
The $match for the trigger is supposed to work exactly like a normal mongo $match. They just provide one example :
{
"updateDescription.updatedFields": {
"status": "blocked"
}
}
The example is from here: https://docs.mongodb.com/stitch/triggers/database-triggers/
I tried 100's of variations but i can't seem to get it
The trigger is working fine if the match is a specific value like:
{"updateDescription.updatedFields":{"hours.online":{"$numberInt\":"20"}}
and then i set the hours.online to 20 in the database.
Upvotes: 2
Views: 1176
Reputation: 1
Here's a slightly different case as FYI for anyone who might stumble on this thread:
My scenario was I needed the trigger to only run if a nested field was not present in the updated fields.
The solution provided by MongoDB's Community Forum only works if the field you're looking for is the first one in the updated
array. Here's a slight modification to look for it on any position:
{
"$expr": {
"$not": {
"$let": {
"vars": {
"updated": {
"$map": {
"input": { "$objectToArray": "$updateDescription.updatedFields" },
"as": "ups",
"in": "$$ups.k"
}
}
},
"in": { "$in": [ "example.subdocument.nested_field", "$$updated" ] }
}
}
}
}
Upvotes: 0
Reputation: 46
I struggled with this myself, trying to get a trigger to fire when a certain nested field was updated to any value (rather than just one specific one).
The issue appears to have to do with how change streams report updated fields.
With credit and thanks to MongoDB support, I can finally offer this as a potential solution, at least for simpler cases:
{
"$expr": {
"$not": {
"$cmp": [{
"$let": {
"vars": { "updated": { "$objectToArray": "$updateDescription.updatedFields" } },
"in": { "$arrayElemAt": [ "$$updated.k", 0 ] }
}},
"example.subdocument.nested_field"
]
}
}
}
Of course replace example.subdocument.nested_field
with your own dot-notation field path.
Upvotes: 2
Reputation: 239
I was able to have it match items by using an explicit $expr
operator or declare it as a single field not an embedded object. ie. "updateDescription.updatedFields.statue": "blocked"
Upvotes: 2