首页 > 解决方案 > MongoDB 中的追随者/追随者结构

问题描述

我的网站有一个“关注”功能,用户可以互相关注。


理想情况下,user1 能够关注 user2,并且他们的 _id 存在于 user2.followers 中,并且 user2 应该存在于 user1.following 中。

我的第一个想法是简单地做类似的事情

/*
  UserSchema = new Schema({
    username: String,
    followers: [
      {
        type: Schema.Types.ObjectId,
        ref: 'user'
      }
    ],
    following: [
      {
        type: Schema.Types.ObjectId,
        ref: 'user'
      }
    ]
  })
*/

// POST /api/users/follow
let user = await User.findById(userId)
let follow = await User.findById(followId)

if (!user || !follow) {
  return errorHandle()
}

user.following.push(follow._id);
follow.followers.push(user._id);

user.save();
follow.save();

/*
  User.findById(userId)
  .populate('following', 'username')
  .then(user => console.log(user.following))
*/

但是这些将难以扩展和维护(以及其他问题)。

所以我想听听你,堆栈社区,处理这个系统的正确方法是什么,因为我是 MongoDB 和整个数据库的新手。

任何帮助表示赞赏

标签: node.jsdatabasemongodb

解决方案


嘿,我遇到了同样的问题,我想出了它是如何完成的。根据您的选择,我有两种编写代码的方式。

用户模式

  var UserSchema = new Schema({
    name:{
        type:String,
        required:true
    },
    email:{
        type:String,
        required:true
    },
    password:{
        type:String,
        required:true
    },
    following: [
    {

        user:{ 
            type: Schema.ObjectId, 
            ref: 'User' 
        },
    }

],
followers: [
    {

        user:{ 
            type: Schema.ObjectId, 
            ref: 'User' 
        },
    }
],
    date:{
        type:Date,
        default: Date.now
    },
});

第一种方法

用户.js

您可以使用 .then 和 .catch 方法

    router.post("/user/:user_id/follow-user", (req,res) => {

    // finding user by id (to whom user is going to follow)

    User.findById(req.params.user_id)
        .then(user => {

            //check if follow reqest by user2 is already exist in user1 followers

               if(user.followers.filter(follower => follower.user.toString()=== req.user._id).length > 0 ){
                return res.status(400).json({ alreadyLike : "User already like the post"})
            }

            // the requested user will push and save to followers of other user to whom request has made

            user.followers.push(req.user._id);
            var followedUser = user._id;
            user.save()

            // we will find current user by email you can find it by _id also

            User.findOne({ email: req.user.email })
                .then(user => {

                    // now push the user to following of its own and save the user

                    user.following.push(followedUser);
                    user.save().then(user => res.json(user))
                })
                .catch(err => console.log("error cant follow again you jave already followed the user"))
        })
})

第二种方法

回调的正常方法

    router.post("/user/:user_id/follow-user",  (req,res) => {

    // finding user by id (to whom user is going to follow)

    User.findById(req.params.user_id, function(err, user) {

        // the requested user will push and save to followers of other user to whom request has made

        user.followers.push(req.user._id);
        var followedUser = user._id;
        user.save(function(err){
            if(err){

                console.log(err)
            }
            else
            {

                // Secondly, find the user account for the logged in user

                User.findOne({ email: req.user.email }, function(err, user) {

                    user.following.push(followedUser);
                    user.save(function(err){
                        if(err){
                            console.log(err)
                        }
                        else{
                            //send success response
                            res.json(user)
                        }
                    });
                });
            }
        });
    });
});

推荐阅读