3

I have followers collection in mongodb like below:

[{
    user : <userId> ,
    followers : [
        {
            user : <userId>
            , createdOn : <Date>
            ,...
        }
        ,
        {
            user : <userId>
            , createdOn : <Date>
            ,...
        }
    ]
},
{
    user : <userId> ,
    followers : [
        {
            user : <userId>
            , createdOn : <Date>
            ,...
        }
        ,
        {
            user : <userId>
            , createdOn : <Date>
            ,...
        }
    ]
}]

When users requests to /api/users/<userId>/followers I am trying to provide all the followers of user <userId>. Additionally I am also trying to set a flag to denote if the particular follower of <userId> is followed by the loggedIn user or not. I am trying to output something like below :

{
    user : <userId>
    , followers : [
        {
            user : <userId>
            , isFollowing : <Boolean>
        }
        ,
        {
            user : <userId>
            , isFollowing : <Boolean>
        }
    ]
}

I give a try and my unsuccessful attempt looks like this :

app.get('/users/:userId/followers', function(req, res) {
    var userId = req.params.userId;
    var loginUser = req.user._id; // I am using passport for user authentication
    var Follower = mongoose.model('followers'); // I am using mongoose also
    var DocumentObjectId = mongoose.Types.ObjectId;

    Follower.aggregate([
         {$match : { user : DocumentObjectId(userId)}}
        , {$project : {"followers" : 1, "_id" : 0}}
        , {$unwind : "$followers"}
        , {$group : {
            _id : {"user : "$user"}
            , "followers" : {$push:{
                "user" : "$followers.user"
                , "isFollowing" : {$and : [{user: "$followers.user"}, {"followers.user" : loginUser}]}
            }}
        }}
    ])

})

But I am getting this error from mongodb : exception: dotted field names are only allowed at the top level

What should I do to know either particular follower is being followed by logged in user. So that I could display Follow or Unfollow button in UI when some user views another users followers.

1 Answer 1

1

You need to use the aggregation pipeline as below:

  • Match the user with the corresponding userId.
  • Unwind the followers array.
  • For each un-winded follower, project a field named isFollowing which conditionally states if he is the logged in user, implying he is a follower of the searched for user.
  • Group back the un-winded records based on the user, and compose an array of followers with the extra isFollowing field.

The Code:

var loginUser = 2;
var userId = 3; 
var documentObjectId = mongoose.Types.ObjectId;
Follower.aggregate(
{$match:{"user":documentObjectId(userId)}},
{$unwind:"$followers"},
{$project:{"user":1,"_id":0,
           "follower":"$followers.user",
           "isFollowing":{$cond:[{$eq:["$followers.user",loginUser]}
                         ,true,false]}}},
{$group:{"_id":"$user",
         "followers":{$push: {"user":"$follower",
                              "isFollowing":"$isFollowing"}}}},
function(err,resp){//handle response}
);

But I am getting this error from mongodb : exception: dotted field names are only allowed at the top level

You cant do {"followers.user" : loginUser} in a group by stage, this is a criteria statement which can be applied only in the $match stage. To see all the applicable group by operators refer:operators.

Sign up to request clarification or add additional context in comments.

Comments

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.