0

I have written a query that looks like it should work but I can't figure out why it doesn't.

Firstly - I narrowed down a query to make sure it was actually working. the line with $expr in it proves that the fields are correct ( i.e. the same results show with or without it ) .

db.nzpostRecon.find(
    { $and: [
            {"eship.order.packages.0.tracking_number":"AB41045027010225"},
            {"ticketNumber":"AB41045027010225"},
            {$expr: { $eq: ["$this.eship.order.packages.0.tracking_number", "$this.ticketNumber"] }},
            {"eship.order.packages.0.tracking_number" : {$exists: true}}
            ]

However, when I remove the first 2 lines, the results don't make sense. When I run it I get some documents that have a value in the tracking_number field ( in the array ) - but the ticketNumber field is blank - so they are definitely not equal even though both fields exist. I'm baffled by this & think maybe my understanding of that part of the query is wrong.

db.nzpostRecon.find(
    { $and: [
            {$expr: { $eq: ["$this.eship.order.packages.0.tracking_number", "$this.ticketNumber"] }},
            {"eship.order.packages.0.tracking_number" : {$exists: true}}
            ]
3
  • $expr allows aggregation expression operators within the find query. Commented Apr 13, 2021 at 8:14
  • @prasad_ as explained in the question - it doesn't work as expected. Commented Apr 13, 2021 at 8:16
  • See this post with similar question: $expr query operator does not seem to work with array dot notation Commented Apr 13, 2021 at 8:16

1 Answer 1

0

There is no field named this so "$this.eship.order.packages.0.tracking_number" and "$this.ticketNumber" both evaluate to null or undefined and therefore match for every document, making that $expr always true.

The arrayfield.0.embeddedfield notation is part of the Mongo Query Language, and is not available in aggregation expressions.

If eship.order.packages is an array of objects, $eship.order.packages.tracking_number will be an array containing all of the tracking_number values from those objects, so you can use $arrayElemAt, like:

{$expr: { $eq: [{$arrayElemAt:["$eship.order.packages.tracking_number",0]}, "$ticketNumber"] }},
Sign up to request clarification or add additional context in comments.

1 Comment

Perfect. Thank you! I have spent hours on this and what you said makes perfect sense - works exactly as expected now.

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.