Parse Server, MongoDB - get the "liked" state of an object

I am using Parse Server which runs on MongoDB.

Say I have a User and Comment collection and a user connection table and comment. The user may like the comment that creates a new entry in the connection table.

In particular, in Parse Server, a connection table can be defined using the 'relation' field in the collection.

Now that I want to get all the comments, I also need to know if each of them will be pleasant to the current user. How can I do this without additional requests?

You could say that I can create a likers array likers in the Comment table and use $elemMatch , but that doesn't seem like a good idea, because there could potentially be thousands of comments on the comment.

My idea, but I hope there may be a better solution:

I could create someLikers array field, join table allLikers field and allLikers number field in Comment table. Then put the first 100 characters in someLikers and allLikers and add extra characters only in allLikers . I would always increase likesCount .

Then when requesting a list of comments, I would make a call using $elemMatch , which will tell me if the current user is inside someLikers . When I get the comments, I would check if some of the comments likesCount > 100 AND $elemMatch null. If so, I will have to run another query in the connection table, looking for these comments and checking (asking) if the current user will like them.

Is there a better option?

Thanks!

+5
source share
3 answers

I would suggest getting direct access to MongoDB again if you absolutely don't need to; after all, the way you create collections and relationships is part of Parse's implementation, and could theoretically change in the future by breaking your code.

Despite the fact that you want to avoid multiple requests, I suggest doing just that (depending on your platform, you can even run two Parse requests in parallel):

  • The first is a Comment request to get all the comments you want to display; if you have any Post for which comments can be written, the query will find all comments that link to the current post.
  • The second query is used again for Comment , but this time
    • limited to comments received in the first request, for example: containedIn("objectID", arrayOfCommentIDs)
    • and limited to comments that have the current user in their relation to likers , for example: equalTo("likers", currentUser)
+2
source

Well, assembling connections is not really noSQL thinking ;-) I don't know ParseServer, so below is only based on pure MongoDB.

What would I do, the Comment document uses an ObjectId array for each user who likes the comment.

Document Location Example

 { "_id" : ObjectId(""), "name" : "Comment X", "liked" : [ ObjectId(""), .... ] } 

Then use aggregation to get the data. I assume you have the _id of the comment and you know the _id of the user.

The following aggregation returns a comment with a similar counter and a logical one, which indicates that the user liked the comment.

 db.Comment.aggregate( [ { $match: { _id : ObjectId("your commentId") } }, { $project: { _id : 1, name :1, number_of_likes : {$size : "$liked"}, user_liked: { $gt: [{ $size: { $filter: { input: "$liked", as: "like", cond: { $eq: ["$$like", ObjectId("your userId")] } } } }, 0] }, } }, ] ); 

it returns

 { "_id" : ObjectId(""), "name" : "Comment X", "number_of_likes" : NumberInt(7), "user_liked" : true 

}

Hope this is what you are after.

+2
source

Not a user of the parsing server.

Adding an answer as it may be relevant for future mongodb users.

You can do this as follows, based on what you need.

You can make the server $lookup from the comments table to the connections table and check if it contains the user ID, the same as the current user.

Get all comments with favorite flag for current user

You can add the $addFields script to check whether each comment is liked or not by comparing the user ID with the current user.

db.commentcol.aggregate([ {"$lookup" : { "from" : "relationcol", "localField" : "_id", "foreignField" : "commentid", "as" : "commentusers" }}, {"$unwind":"$commentusers"}, {"$addFields":{liked:{$eq:["$commentusers.userid", user id]}}} ])

You should use the preserveNullAndEmptyArrays option when you $unwind save comments that no one likes, since the "commentators" from $ lookup will be empty in these cases

Get all comments liked by current user

Sort of

db.commentcol.aggregate({$lookup : {from : "relationcol", localField : "_id", foreignField : "commentid", as : "commentusers"}}, {$unwind:"$commentusers"}, {$match:{"commentusers.userid":current user id}}) .

$lookup + $unwind + $match optimized to use the index when there is one

Get all comments that the current user liked for a specific post

You can request a post with an identifier, then $lookup in the comments to get all the comments for this post, and then the above search to check if the current user likes the comments or not.

db.postcol.aggregate([{"$match":{_id:postid}}, {"$lookup" : { "from" : "commentcol", "localField" : "_id", "foreignField" : "postid", "as" : "comments" }},{"$unwind":"$comments"}, , {"$lookup" : { "from" : "relationcol", "localField" : "comments._id", "foreignField" : "commentid", "as" : "commentusers" }},{"$unwind":"$commentusers"} {"$addFields":{liked:{$eq:["$commentusers.userid", user id]}}}])

0
source

Source: https://habr.com/ru/post/1274690/


All Articles