假设有两个函数A和B都通过connection.query(...)方法调用mysql DB。我正在使用while循环遍历函数A中的响应。
再次,使用函数A的响应,在函数B中调用另一个DB请求并在其中循环遍历它的结果。
获取异步问题。如何解决这个问题。
307
这是实际代码:
RewriteRule ^ %1 [R=307,L,NC]
答案 0 :(得分:0)
在Nodejs中, 很少 您应该进行同步调用。如果你做错了,它必然会给你的系统增压......特别是如果你有很多流量。 Nodejs是单线程的,并且完全围绕异步构建,以便正常工作。
在您的情况下,您实际上是在查询某些数据库记录并使用这些记录来填充一些JSON对象。当你完成所有这些时,你想发送一个响应,这是一个json对象数组......对吗?
我强烈建议您使用Promises。一个非常受欢迎的库可以处理这个问题:Bluebird:http://bluebirdjs.com/docs/getting-started.html
请阅读承诺,以便您真正理解他们的所作所为。简短的回答是它保持所有异步,但允许你远离回调地狱,同时使你的异步代码“读取”更多,就好像它是同步的。
最终您需要做的是宣传您的数据库查询,将数据推送到其对象然后解决。一旦解决了所有数据库调用,例如使用Promise.all(),那么你应该将res.send与对象一起发回...并且它应该与您需要的所有内容保持一致,同时避免异步问题。
以下是您可能会做的一个示例。 请注意,这是未经测试的,我只是在记事本++中执行此操作...如果您只是复制/粘贴,它肯定无法正常工作!但它应该指向您沿着正确的道路......
var Promise = require('bluebird');
var connection = require('mysqllibrary');
app.get('/getmenu', function (req, res) {
Promise.promisifyAll(connection);
connection.queryAsync('SELECT * from zaitoon_menutypes')
.then(function(rows){
var output = [];
var i=0;
var j;
var main= rows[0].mainType;
var submenu=[];
var items=[];
var promises=[];
//Iterate through complete menu types
while( i < rows.length ){
//Do NOT MENU TYPE switch case
if (main == rows[i].mainType){
promises.push(connection.queryAsync("SELECT * from zaitoon_menu WHERE type='type'")
.then(function(rows2){
console.log('*************************'+rows2.length);
items = [];
j=0;
while(j < rows2.length){
items.push(
{
"itemCode":rows2[j].code,
"itemName":rows2[j].name,
"itemPrice":rows2[j].price
}
);
j++;
}
console.log(items);
}));
//Create Sub-menu
submenu.push(
{
"subType" : rows[i].subType,
"subName" : rows[i].subName,
"items" : items
}
);
if ( i ==(rows.length-1) ){
output.push(
{
"mainType":rows[i-1].mainType,
"mainName":rows[i-1].mainName,
"submenu": submenu
});
}
}
//SWITCH NEXT TYPE
else {
main = rows[i].mainType;
output.push(
{
"mainType":rows[i-1].mainType,
"mainName":rows[i-1].mainName,
"submenu": submenu
}
);
var submenu=[];
}
i++;
}
return Promise.all(promises).then(function() {
console.log("Output object has been hydrated");
return output;
});
}).then(function(output){
res.setHeader('Content-Type', 'application/json');
res.header("Access-Control-Allow-Origin", "*");
res.status(200).send(JSON.stringify(output))
}).catch(function(err){
res.status(500).send('Error: ' + err)
});
});