我有2个集Stud
和Prof
。
我有一个以id
为参数的函数,如果id属于任何一个集合,则返回相应的信息。
id
集合Prof
id
集合Stud
预期结果:首先获得Prof
结果,然后获得Stud
结果。
但是由于nodejs的异步特性,我总是首先获得Stud
结果,然后获得Prof
结果。
无论如何通过引入新变量或更改查询集合的方式来完成此任务?
非常感谢任何帮助
var check_user_info = function(userid, callback) {
Stud.findOne({
'_id': userid
}, function(err, stud) {
if (err)
throw err
if (stud) {
callback(stud);
} else {
Prof.findOne({
'_id': userid
}, function(err, prof) {
if (err)
throw err
if (prof) {
callback(prof);
} else {
callback(false);
}
})
}
})
return
}
答案 0 :(得分:3)
如前所述,您可以使用异步模块来完成此任务。有许多功能可以控制节点的非阻塞性质。在这里,我将建议您使用“并行”方法。由于查询彼此独立,因此它将比“瀑布式”方法更快。
根据您的问题,代码将如下所示。
var async = require('async');
async.parallel([
cb=>{
Stud.findOne({
'_id': userid
},cb);
},
cb=>{
Prof.findOne({
'_id': userid
},cb);
}
],(err,result)=>{
if(err) {
//handle error
return;
}
//result will be an array where the first element will be the result of first query and
// second element will be the query result for the second query
// so according to this .....
if(result[0]){
//id is matched with Stud collection
//result[0] is the student doc
}else if(result[1]) {
//id is matched with Prof collection
//result[0] is the professor doc
}else {
//Neither Stud or Prof
}
});
您可以从this other post
中了解异步方法答案 1 :(得分:1)
您可以使用waterfall mudule的async方法解决此问题
async.waterfall([
function(callback) {
//your fist query method can go here
callback(null, query_result1);
},
function(first_result1, callback) {
// your second query method go here
callback(null, query_result2);
}
], function (err, result) {
// final result'
});
答案 2 :(得分:1)
要回答您的问题,请申请@abdulbarik post。
以下是有关您实际代码的其他内容:
_id
键放入引号说明:
关于回调和功能切换的示例。我让你做其余的es6,瀑布处理......你可以看看Promise和Async / Await模式。
// Check if there is a student
function check_student(user_id, callback) {
Stud.findOne({
_id: user_id
}, function (err, stud) {
if (err) return callback(err, false);
// stud here can worth false
return callback(false, stud);
});
}
// Check if there is a prof
function check_prof(user_id, callback) {
Prof.findOne({
_id: user_id
}, function (err, prof) {
if (err) return callback(err, false);
// prof here can worth false
return callback(false, prof);
});
}
// Get Stud not Prof info
function check_user_info(user_id, callback) {
// Look if user_id match a stud
check_student(user_id, function (err, result) {
// We have an error
if (err) return callback(err, false);
// We have a student
if (result) return callback(false, result);
// Check if user_id match a prof
check_prof(user_id, function (err, result) {
// We have an error
if (err) return callback(err, false);
// We have a prof
if (result) return callback(false, result);
// No result at all
return callback(false, false);
});
});
}
你怎么称呼它
check_user_info(user_id, function (err, result) {
// ...
});
承诺代码示例:
// Check if there is a student
function check_student(user_id) {
return new Promise((resolve, reject) => {
Stud.findOne({
_id: user_id
}, (err, stud) => {
if (err) return reject(err);
// prof here can worth false
return resolve(stud);
});
});
}
// Check if there is a prof
function check_prof(user_id) {
return new Promise((resolve, reject) => {
Prof.findOne({
_id: user_id
}, (err, prof) => {
if (err) return reject(err);
// prof here can worth false
return resolve(prof);
});
});
}
// Get Stud not Prof info
function check_user_info(user_id) {
return Promise.all([
check_student(user_id),
check_prof(user_id),
]);
}
check_user_info(user_id)
.then([
stud,
prof,
] => {
// Handle result
})
.catch((err) => {
// Handle error
});