Node.js Express:mongodb mongoose链接实体
我正在开发一个简单的web应用程序,公司向其员工发送一个问题,请求反馈。还在学习mongodb。这一周我一直在玩它&我在论坛上通过一些有用的帮助慢慢地掌握了它,但直到现在我才意识到我一直在使用一个有缺陷的思维过程来设计模式。最初我在UserSchema中将用户的响应用作字段,但现在我已将其删除,因为我意识到这不是用户的属性,而是一个不断更改yes/no/null的变量。我现在必须创建一个单独的答案。有人告诉我需要一个答案,但我坚决反对——在我开始这个项目的时候,我觉得没有任何意义,现在我已经做了,如果写错了/想错了,请纠正我。我现在的问题是如何修改api中的查询,以便在router post中的保存操作中将所有三个实体链接在一起?请注意,此处显示的保存操作代码有效,但存在缺陷,因为它适用于用户将响应作为其属性之一的情况。所以现在,在我删除UserSchema上的响应后,只有用户名显示在角度前端,这是有意义的Node.js Express:mongodb mongoose链接实体,node.js,mongodb,express,mongoose,Node.js,Mongodb,Express,Mongoose,我正在开发一个简单的web应用程序,公司向其员工发送一个问题,请求反馈。还在学习mongodb。这一周我一直在玩它&我在论坛上通过一些有用的帮助慢慢地掌握了它,但直到现在我才意识到我一直在使用一个有缺陷的思维过程来设计模式。最初我在UserSchema中将用户的响应用作字段,但现在我已将其删除,因为我意识到这不是用户的属性,而是一个不断更改yes/no/null的变量。我现在必须创建一个单独的答案。有人告诉我需要一个答案,但我坚决反对——在我开始这个项目的时候,我觉得没有任何意义,现在我已经做了
var QuestionSchema = Schema({
id : ObjectId,
title : String,
employees : [{ type: ObjectId, ref: 'User'}]
});
var UserSchema = Schema({
username : String,
//response : String,
questions : [{ type: ObjectId, ref: 'Question'}]
});
//new schema/collection I've had to create
var AnswerSchema = Schema({
response : {type :String, default:null},
question : { type: ObjectId, ref: 'Question'},
employees : [{ type: ObjectId, ref: 'User'}],
})
module.exports = mongoose.model('Question', QuestionSchema);
module.exports = mongoose.model('User', UserSchema);
module.exports = mongoose.model('Answer', AnswersSchema);
api.js
更新
添加AnswerSchema是正确的,因为这是一种多对多关系。一个问题可以由许多用户和员工回答。用户可以回答许多问题。因此,最好将答案作为两者之间的关联集合 考虑到这种关系,您需要稍微更改您的模式:
var QuestionSchema = Schema({
id : ObjectId,
title : String,
//employees : [{ type: ObjectId, ref: 'User'}]
});
var UserSchema = Schema({
username : String,
//response : String,
//questions : [{ type: ObjectId, ref: 'Question'}]
});
var AnswerSchema = Schema({
response : {type :String, default:null},
question : { type: ObjectId, ref: 'Question'},
employee : { type: ObjectId, ref: 'User'}, //a single employee
});
现在,要知道某个用户是否已经回答了某个问题,只需使用他的ID和问题的ID搜索答案:
Answer.findOne({
question: questionId,
employee: userId
})
.exec(function(err, answer) {
if (err) {
} else if (!answer) {
//the employee has not answered this question yet
} else {
//answered
}
});
最后,您的submit-answer API应该期望一个包含questionId和userId的主体。如果登录,您还可以从会话或令牌中获取userId。此路由将更新现有答案,否则将为“仅创建”使用“创建”功能创建该答案
@塔尔万再次感谢您的回复。在Answer.findOneAndUpdate{question:req.body.question,employee:req.body.user由于angular的http没有从api端返回响应,所以没有发生任何事情。当我执行console.logreq.body;位于Answer.findOneAndUpdate上方时,它会显示angular发送的带有问题、名称和响应的实际正文。不确定是什么p之后,实体也会保存到数据库中,尽管回答文档中的employee和response为空。您从何处发送响应?数据库条目是否显示所有三个字段?如果response是指回答的字段“response”,则我从angular发送。是的,所有三个字段都显示在回答集合中。我已经更新了t他贴了一张快照。我的req.body的实际值,如name:mike和问题:我们是否应该购买angular发送的咖啡机。我看到你的有你评论的实际ObjectId。ObjectId是如何被提取到req.body的?
Answer.findOne({
question: questionId,
employee: userId
})
.exec(function(err, answer) {
if (err) {
} else if (!answer) {
//the employee has not answered this question yet
} else {
//answered
}
});
router.post('/', function(req, res) {
//req.body = {question: "594315b47ab6ecc30d5184f7", employee: "594315d82ee110d10d407f93", response: "yes"}
Answer.findOneAndUpdate({
question: req.body.question,
employee: req.body.user
},
req.body,
{
upsert: true //updates if present, else inserts
}
})
.exec(function(err, answer) {
//...
});
});