I am trying to do the following questions.
-
Find the ISBN and title of books that was published in 2022.
-
Find the ISBN, title of book and publisher of books that have at least two authors and at most three authors.
For Question 1, I’ve tried:
I wanted to try to use $eq
but I’m not so sure how to so I tried using $elemMatch
but it seems like I have no idea how it works too.
db.Subject.aggregate( [
{"$unwind":"$subject.book"},
{"$match":{"subject.book":{"$elemMatch":{"subject.yearPub":2022}} }},
{"$project":{"subject.book.ISBN":1,"subject.book.bookTitle":1 }}
] )
For Question 2, I’ve tried:
This works so far it gives me books with 3 authors. But for some reason it misses the books with 2 authors.
db.Subject.aggregate([{"$match": {"$or": [{'subject.book.author.3': {"$exists": true}},
{'book.author.2': {"$exists": true}}]}},
{"$project": {"subject.book.ISBN": 1,"subject.book.bookTitle": 1,"subject.book.publisher": 1,"_id":0}}
]).pretty()
3
Answers
Q1: Filter with dot notation: "subject.book.yearPub"
Demo Q1 @ Mongo Playground
Updated: To filter the document in the array
Demo Q1.1 @ Mongo Playground
Q2: I suspect that you observe the result incorrectly.
subject.book.author.3
will return you the fourth element from thesubject.book.author
array as the index starts from 0.For your current query, it will return the document with the third and fourth elements in the
subject.book.author
array which means that as long the array contains more than 2 elements, the document will be returned.Instead, you need the
$size
operator to get the size of the array. While there are documents that don’t have thebook
property, so use$ifNull
to return the empty array to prevent an error when using$size
.Demo Q2 @ Mongo Playground
Updated: To filter the document in the array
Demo Q2.1 @ Mongo Playground
Note: You attach too many questions into one. Please remember to split it into different questions (posts) when you ask a new question in the future.
Instead of
$unwind
you can also use$filter
:Mongo Playground
For Question 2, since Yong Shun mentioned array starts at 0, I’ve edited the code to fit accordingly. As well as if you want to collect each books as an individual record you will need to unwind them to the book level.
I hope this answers your question.
I’m new to MongoDB as well so let me know if it is not working as intended.
Click Q2 MongoDB Playground