Reputation: 753
I'm trying to create a watch list where users can watch items. I was trying to create it by adding a watchlist field to my users collection. The watchlist would be an array of IDs corresponding to other items.
Users Collection:
The question I have is related to querying this structure. I want to be able to write a query where I pass in a user id and an array of ~20 IDs and check which of those IDs the user watches (i.e. which of them exists in the watchlist field for that user).
I tried this initially:
db.users.find({
_id: 507c35dd8fada716c89d0013,
watchlist: { $in: [342, 999, 8745, etc...] }
});
But this gives me the list of users that contain any of those watchlist items, which is not what I want. What I actually want is a response containing an array like this:
{
id: 342,
exists: true
},
{
id: 999,
exists: false
},
{
id: 8745,
exists: true
}
I'd even be ok just getting an array of items that match:
{
_id: 507c35dd8fada716c89d0013,
watching: [342, 8745]
}
Is this doable, or would I be better off moving the watchlist to a separate collection with users as an array? (My concern with the latter approach is that a user will only watch a few hundred items, but tens of thousands of users could potentially watch the same item.)
Upvotes: 0
Views: 72
Reputation: 75964
You can easily achieve the second output using $setIntersection operator.
db.users.aggregate(
[ {$match:{"_id": 507c35dd8fada716c89d0013}},
{ $project: { "watching": { $setIntersection: [ "$watchlist", [ 342, 999, 8745 ] ] } } }
]
)
Upvotes: 0