2015-02-11 128 views
0

我想弄清楚如何爲Web應用程序創建異步函數。我正在做一個數據庫查詢,將數據操作爲更方便的格式,然後嘗試將我的路由器設置爲傳回該文件。Node.js:異步回調混淆

//Module 1 
//Module 1 has 2 functions, both are necessary to properly format 
function fnA(param1){ 
    db.cypherQuery(query, function(err, result){ 
     if(err){ 
      return err; 
     } 
     var reformattedData = {}; 
     //code that begins storing re-formatted data in reformattedData 

     //the function that handles the rest of the formatting 
     fnB(param1, param2); 
    }); 
}); 

function fnB(param1, reformattedData){ 
    db.cypherQuery(query, function(err, result){ 
     if(err){ 
      return err; 
     } 
     //the rest of the reformatting that uses bits from the second query 
     return reformattedData; 
    }); 
}); 

exports.fnA = fnA; 

然後在我的路由器文件:

var db = require('module1'); 

router.get('/url', function(req,res,next){ 
    db.fnA(param1, function(err, result){ 
     if (err){ 
      return next(err); 
     } 
     res.send(result); 
    }); 
}); 

當我試圖通過敲擊路由器表明,它只是加載無限的URL測試了這一點。

我知道我上面有什麼是錯誤的,因爲我從來沒有寫我的函數來要求回調。當我試圖弄清楚如何重寫它時,我感到非常困惑 - 當異步內容發生在內部時,如何編寫我的函數來進行回調?

有人可以幫我重寫我的函數來正確使用回調,以便當我真正使用函數時,我仍然可以使用異步響應?

回答

1

從路由器文件中使用db.fa,並將第二個參數作爲回調函數傳遞。但函數簽名沒有cb參數並且不使用它。

主要思想 - 您嘗試啓動一個異步操作,並且無法知道它何時結束,因此您發送一個回調函數以在所有操作完成時觸發。

固定碼應該是這樣的:

//Module 1 
//Module 1 has 2 functions, both are necessary to properly format 
function fnA(param1, cb1){ 
    db.cypherQuery(query, function(err, result){ 
     if(err){ 
      cb1(err); <-- return error to original call 
     } 
     var reformattedData = {}; 
     //code that begins storing re-formatted data in reformattedData 

     //the function that handles the rest of the formatting 
     fnB(param1, param2, cb1); 
    }); 
}); 

function fnB(param1, reformattedData, cb1){ 
    db.cypherQuery(query, function(err, result){ 
     if(err){ 
      cb1(err); <-- return error to original call 
     } 
     //the rest of the reformatting that uses bits from the second query 
     cb1(false, dataObjectToSendBack); <--- This will call the anonymouse function in your router call 
    }); 
}); 

exports.fnA = fnA; 

路由器文件:

var db = require('module1'); 

router.get('/url', function(req,res,next){ 
    db.fnA(param1, function(err, result){ <-- This anonymous function get triggered last 
     if (err){ 
      return next(err); 
     } 
     res.send(result); 
    }); 
}); 
+0

的'回報err'是不正確的,因爲它返回你在哪裏,什麼也不做。你需要一種方法來告訴回調,有一個錯誤,因爲現在,當出現錯誤時,你沒有向外界傳達任何信息。 – jfriend00 2015-02-11 11:30:27

+0

@ jfriend00你是對的,那是Dude代碼的複製粘貼。固定 – 2015-02-11 11:32:22

+0

好吧,這現在更有意義了。非常感謝Ben! 只是爲了確保我現在明白這一點,是否意味着cb1在路由器文件中被調用之前沒有被定義?通過代碼說: ...功能(錯誤,結果){ if(err)... – Dude 2015-02-11 15:37:03