MERN栈中如何用MongoDB操作移除用户数据中匹配帖子的评论
问题:移除User数据中与指定Post评论ID匹配的评论项
我是MERN栈新手,想移除User数据里ID和指定Post数据中评论ID相同的评论项。下面是Post数据、User数据示例,以及我尝试的代码,但没实现需求,求帮助。
Post 数据示例
{ _id: new ObjectId('66985b5774dd3a87fd1be9d4'), title: 'adadasd', description: 'adasda', category: 'Web Development', user: new ObjectId('6692abbc21ab34ea540b3755'), role: 'Blogger', bio: 'Lorem ipsum dolor, sit amet consectetur adipisicing elit.', comments: [ { _id: new ObjectId('66985b6074dd3a87fd1be9dc'), user: new ObjectId('6692abbc21ab34ea540b3755'), message: 'adad', post: new ObjectId('66985b5774dd3a87fd1be9d4'), createdAt: 2024-07-18T00:01:36.508Z, updatedAt: 2024-07-18T00:01:36.508Z, __v: 0 }, { _id: new ObjectId('66985b6374dd3a87fd1be9e4'), user: new ObjectId('6692abbc21ab34ea540b3755'), message: 'dada', post: new ObjectId('66985b5774dd3a87fd1be9d4'), createdAt: 2024-07-18T00:01:39.457Z, updatedAt: 2024-07-18T00:01:39.457Z, __v: 0 } ], }
User 数据示例
{ _id: ObjectId('66985b5774dd3a87fd1be9d4'), title: 'adadasd', description: 'adasda', category: 'Web Development', image: 'https://res.cloudinary.com/dgmfnfvf9/image/upload/v1721260913/blog-app-v3/ty1qyrqyodklxqwmf7us.jpg', user: ObjectId('6692abbc21ab34ea540b3755'), role: 'Blogger', bio: 'Lorem ipsum dolor, sit amet consectetur adipisicing elit.', comments: [ ObjectId('66985b6074dd3a87fd1be9dc'), ObjectId('66985b6374dd3a87fd1be9e4'), ObjectId('66985f4746d06f903adef17f'), ObjectId('66986298273a46211122814c') ], createdAt: ISODate('2024-07-18T00:01:27.733Z'), updatedAt: ISODate('2024-07-18T00:32:24.142Z'), __v: 0 }
尝试的代码
app.post('/remove', async (req, res, next)=>{ try { const post = await Post.findById(req.params.id,{ comments: 1, _id: 0 }); //if post is deleted then remove post id from user post await User.updateOne({ post: req.params.id },{ $pullAll: { comment: { $in: post.comments } }, }); } catch (error) { return res.render("posts/postDetails",{ error: error.message, post: "" }); } });
解决方法
你的代码存在3个关键问题,修正后即可实现需求:
- 字段名拼写错误:User数据里的评论字段是
comments,但你写的是comment,少了末尾的s; - 查询条件错误:从数据示例看,User模型中关联的是用户ID字段
user,而非post,所以查询时要匹配user字段; $pullAll用法错误:$pullAll需要传入明确的值数组,不能搭配$in表达式,需先从Post的comments中提取所有_id组成数组。
修正后的代码:
app.post('/remove', async (req, res, next) => { try { // 获取指定Post的评论ID列表 const post = await Post.findById(req.params.id, { 'comments._id': 1, _id: 0 }); // 提取评论ID组成数组 const commentIds = post.comments.map(item => item._id); // 更新User,移除匹配的评论ID await User.updateOne( { user: post.user }, // 匹配该Post对应的用户 { $pullAll: { comments: commentIds } } // 移除comments数组中匹配的ID ); res.redirect('/posts'); // 操作成功后跳转,可根据需求调整 } catch (error) { return res.render("posts/postDetails", { error: error.message, post: "" }); } });
补充说明
- 如果你的User模型中确实用
post字段关联帖子,可将查询条件改为{ post: req.params.id }; - 也可以用
$pull实现相同效果,写法为{ $pull: { comments: { $in: commentIds } } },两种方式均可,$pullAll在已知明确值数组时效率更高。
内容的提问来源于stack exchange,提问作者GAMING WARRIOR
相关产品推荐
相关产品推荐

