Accessing "dynamic" object property in aggregation stage

In an aggregation stage is it possible to get the value of an object property when the name is in another variable?

I’m looking for something like $arrayElemAt but for objects:

{ $objectProp: [ <expr that evaluates to an object>, <expr that evaluates to object key> ] }

So for example this { $objectProp: [ { foo: 11, bar: 22 }, "foo" ] } would evaluate to 11.

I guess it’s possible to do with $objectToArray & $filter & $first & $let (to get the value), but that’s pretty cumbersome (10 lines of code?). Is there an easier way that I’m missing?

Hello

I think you are asking this


Lets say you are in pipeline and you have this

  $$mydoc   = one document
  $$mykey   = one key
  
How to do 

  get("$$mydoc","$$mykey")
  contains?("$$mydoc","$$mykey")
  put("$$mydoc","$$mykey","randomValue")
  remove("$$mydoc","$$mykey")
  ....
  (and all those basic operation on maps that programming languages offer)
  

I had the same problems before sometime,in mongodb for now seems that the key can’t be in a variable.
The problem is not just the 10 lines,but object to array and back to object,is so slow to be done multiple times(for example hen reducing a array to a document).
I didn’t got any solution yet,i dont think its possible.
I managed to implement fast only put,and only if the key is new.

But if the you keep the documents with known fields (known schema),you can use unwind/group/project
etc , and if you want to do those for an embeded data,you can use facet,and do those.
Javascript is also possible with $function stage ,but its slower.

If you know where to send this either to be answered or to ask to be added on mongoDB ,would be nice.

1 Like

Yeah this is exactly what I’m wondering. Too bad that there doesn’t seem to be a (better) way. :-/

In my case the fields are not known in advance, but there are not too many of them (1-100), so I hope the approach I wrote using $objectToArray and back will be fast enough when the number of fields is at the upper limit.

Hello

If the fields are known use facet and project or addFields.
I think its easier solution,maybe test it.
Facet allows the use of stage operators,even if the object is embeded,if you replace the root
inside the facet with that object,and then use the stage operators.
https://docs.mongodb.com/manual/reference/operator/aggregation/replaceRoot/

If the fields are know then you can use $let.

This topic was automatically closed 5 days after the last reply. New replies are no longer allowed.