我有以下代码,使用find()
使用array.map
提取的值搜索我的mongodb。所述搜索返回一个对象,然后我使用_.forEach
来提取值。
我使用this article作为基础,然而他的例子和我的例子之间的区别是他只使用了一个循环。我用了两个。在这种情况下,我应该在哪里放置q.all()
?
这是我的代码。 请注意,这是服务器端:
'use strict';
var q = require('q');
exports.downloadEmployee = function (req, res) {
var tempCtr = [];
if (req.params.hasdr === "yes") {
return queries.generateDirectReportsCSV(req.params.id).then(function (directReports) {
return directReports;
}).then(function (directReports) {
var empIDcoll = _.pluck(directReports.Data, "employeenumber");
return empIDcoll;
}).then(function (empIDcoll) {
var promises = [];
empIDcoll.map(function (id) {
return EmployeeInfo.find({ employeeID: id }, function (err, results) {
if (err) { return err; }
_.forEach(results, function (item) {
if (item) {
tempCtr.push({
employeeID: item.employeeID,
employeeName: item.employeeName
});
promises.push(tempCtr);
}
});
});
q.all(promises).then(function (results) {
return res.json(results);
});
});
});
}
当我跑步时,我得不到任何结果。
任何答案都将不胜感激。
谢谢。
更新:我已决定修改我的代码并将array.map
替换为通常的for loop
:
.then(function (empIDcoll) {
for (var i = 0; i <= empIDcoll.length - 1; i++) {
var promise = EmployeeInfo.find({ employeeID: empIDcoll[i] }, function (err, results) {
if (err) { return err; }
_.forEach(results, function (item) {
if (item) {
tempCtr.push({
employeeID: item.employeeID,
employeeName: item.employeeName,
currentShift: item.currentShift,
isOpenToIntlAssignment: item.isOpenToIntlAssignment,
desiredRole1: item.desiredRole1,
desiredRole2: item.desiredRole2,
desiredRole3: item.desiredRole3,
desiredRoleOther: item.desiredRoleOther,
passportInfo: item.passportInfo,
visaInfo: item.visaInfo,
yrsInIT: item.yrsInIT,
yrsAsCustomerPM: item.yrsAsCustomerPM,
yrsAsCustomerProgM: item.yrsAsCustomerProgM,
primaryDomain: item.primaryDomain,
primaryDomainOther: item.primaryDomainOther,
primaryIndustry: item.primaryIndustry,
primaryIndustryOther: item.primaryIndustryOther,
isPMPCertified: item.isPMPCertified,
pmpCertExpiryDate: item.pmpCertExpiryDate,
isPGMPCertified: item.isPGMPCertified,
pgmpCertExpiryDate: item.pgmpCertExpiryDate,
isScrumCertified: item.isScrumCertified,
scrumCertExpiryDate: item.scrumCertExpiryDate,
biggestProjectTCV: item.biggestProjectTCV,
biggestTeamSizeManaged: item.biggestTeamSizeManaged,
avgTeamSizeManaged: item.avgTeamSizeManaged,
biggestBilledFTE: item.biggestBilledFTE,
avgBilledFTE: item.avgBilledFTE
});
}
});
});
promises.push(promise);
}
return q.all(promises).then(function(data){
return res.json(data);
});
});
......但它仍然没有返回任何东西。我做错了什么?
答案 0 :(得分:2)
第一次几乎是正确的!
当你这样做时:
var promises = [];
empIDcoll.map(function (id) {
return EmployeeInfo.find({ employeeID: id }, function (err, results) {
if (err) { return err; }
_.forEach(results, function (item) {
if (item) {
tempCtr.push({
employeeID: item.employeeID,
employeeName: item.employeeName
});
promises.push(tempCtr);
}
});
});
q.all(promises).then(function (results) {
return res.json(results);
});
});
q.all
位置错误(.map
内);并且您在promises
数组中推送了对象,而不是实际的 promises 。尝试做类似的事情:
// Here, we will build an array of promises by transforming each element of `empIDcoll` to a promise (via `.map`).
var promises = empIDcoll.map(function (id) {
return EmployeeInfo.find({ employeeID: id }).exec(); // I assume that .exec() will return a promise.
});
q.all(promises).then(function (results) { // `results` will be an array, each element will contain the result of each promise pushed to `promises`.
return res.json(results);
});
试试这个。这可能需要一些调整(让我们知道),因为我真的不知道您的应用程序/模型的结构。
答案 1 :(得分:0)
删除return
之前的EmployeeInfo.find
声明?
答案 2 :(得分:0)
看看,
var promises = questions.map(function(question) {
return $http({
url : 'upload/question',
method: 'POST',
data : question
});
});
return $q.all(promises);
答案 3 :(得分:0)
我的第一个建议是首先停止遍历employeeId。 您可以像这样使用mongoDB的$in运算符
EmployeeInfo.find({ employeeID: {$in: empIDcoll} }, function (err, results) {
if(err) {
//handle error
return err;
}
res.json(results);
});
但是,由于我不知道您的应用程序,我真的无法判断您是否想要循环使用empIdColl。
循环使用empIdColl
现在我不确定你的monogdb查询是否会返回promise,所以为了更加安全,我会认为它不会
var promises = empIDcoll.map(function (id) {
var singleDefer = q.defer(); //create a deferred object which has promise in it
EmployeeInfo.find({ employeeID: id }, function(err, results) {
if(err) {
return singleDefer.reject(err);
}
return singleDefer.resolve(results); //resolve whole array
});
return singleDefer.promise;
});
q.all(promises)
.then(function (arrayOfResults) {
var responseData = [];
arrayOfResuls.forEach(function(results) {
results.forEach(function(individualResult) {
if(individualResult) {
responseData.push({
employeeID: item.employeeID,
...
...
avgBilledFTE: item.avgBilledFTE
});
}
});
});
return res.json(responseData);
})
.catch(function(err) {
//handle error
});
答案 4 :(得分:0)
我在这里发布我的工作解决方案,以便将来可能遇到同样问题的人受益。感谢SinDeus简单而简洁的解决方案。 :)
.then(function (empIDcoll) {
// push user's employee number in first row
empIDcoll.unshift(req.params.id);
// return resolved promises from EmployeeInfo.find()
// this will return user's direct reports' information (if any)
var promises = empIDcoll.map(function (id) {
return EmployeeInfo.find({ employeeID: id }).exec();
});
// Take resolved promises from above statement and iterate to get final results.
q.all(promises).then(function (results) {
_.forEach(results, function (item) {
var len = item.length - 1;
if (len >= 0) {
tempCtr.push({
employeeID: item[0].employeeID,
employeeName: item[0].employeeName
// ... other fields here ...
});
}
});
return res.json(tempCtr);
});
});
}