该循环应该用于检查数据库中与从salesforce api结果中提取的opp相匹配的opp,然后创建新的opp或找到现有的opp并将其推送到阵列。似乎res.render在找到opp之前正在运行。它创建一个新的opp,但是在页面呈现时该数组返回空。
Account.find({owner:req.user._id, prospect:'false'}).sort({ammount:'desc'}).populate({path: "notes", options:{ sort:{ 'date': -1 } } }).exec(function(err, allAccounts) {
let callGoal = req.user.callGoal;
if(err){
res.send(err);
}else{
// if auth has not been set, redirect to index
if (!req.session.accessToken || !req.session.instanceUrl) { res.redirect('/'); }
//SOQL query
let q = "SELECT Id,Amount,CloseDate,LastActivityDate,Name,StageName,account.Name FROM Opportunity WHERE CloseDate < 2018-10-01 AND OwnerId = '0050a00000J12PdAAJ' AND IsClosed = false AND StageName != 'Stage 6: Won'";
//instantiate connection
let conn = new jsforce.Connection({
oauth2 : {oauth2},
accessToken: req.session.accessToken,
instanceUrl: req.session.instanceUrl
});
//set records array
let softopps = [];
let sfOpps = [];
let query = conn.query(q)
.on("record", function(record) {
sfOpps.push(record);
})
.on("end", function() {
console.log("total in database : " + query.totalSize);
console.log("total fetched : " + query.totalFetched);
let user = req.user;
sfOpps.forEach(function(sfopp){
if(err){
res.send(err);
}else{
Opp.findOne({sfid:sfopp.Id}).exec(function(err, opp){
if(!opp.length){
Opp.create(req.body, function(err, newOpp) {
if(err){
res.send(err)
}else{
newOpp.sfid = sfopp.Id;
newOpp.name = sfopp.Name;
newOpp.owner = user.sfid;
newOpp.save();
return softopps.push(newOpp)
}
})
}else{
return softopps.push(opp);
}
})
}
})
res.render("myaccounts", {accounts:allAccounts, callGoal:callGoal, user:user, sfOpps:sfOpps, opps:softopps});
})
.on("error", function(err) {
console.error(err);
})
.run({ autoFetch : true, maxFetch : 4000 });
}
});
最佳答案
您的Opp.findOne()
和Opp.create()
调用是异步的,因此它们在res.render()
之后触发。
一方面,您几乎用所有不必要的请求杀死了mongodb。
请尝试以下逻辑(从.forEach
开始)
通过Opp
的ID查找所有sfOpps
找出未找到的Opp
并创建它们
连接所有找到的和未找到的Opp
然后,然后才回应
我没有测试该代码,但可以大致了解我的意思
Opp.find({ sfid : { $in: sfOpps.map(opp => opp.id) } })
.then(found => {
const foundIds = found.map(opp => opp.sfid)
const notFound = sfOpps.filter(opp => !foundIds.includes(opp.sfid)).map(sfopp => {
return {
sfid: sfopp.sfid,
name: sfopp.name,
owner: user.sfid
}
})
Opp.insertMany(notFound)
.then((insertResult) => {
res.render("myaccounts", {
accounts: allAccounts,
callGoal: callGoal,
user: user,
sfOpps: found.concat(notFound),
opps: softopps
});
}).catch(handleError)
}).catch(handleError)
关于javascript - Javascript/NodeJS:.find在forEach内部完成之前的HTML呈现,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/52530076/