2017-02-28 90 views
0

一旦fs.readFile遍歷所有文件並獲取匹配的數據並將其推送到結果,我想調用callback(results),以便我可以向客戶端發送響應。我遇到以下代碼錯誤Error: Callback is already called我可以使用async解決此問題的方法。回調已使用異步調用?

app.js

searchFileService.readFile(searchTxt, logFiles, function(lines, err) { 
    console.log('Logs', lines); 
    if (err) 
     return res.send(); 
    res.json(lines); 
}) 

readFile.js

var searchStr; 
var results = []; 

function readFile(str,logFiles,callback){ 
    searchStr = str; 
    async.map(logFiles, function(logfile, callback) { 
      fs.readFile('logs/dit/' + logfile.filename, 'utf8', function(err, data) { 
       if (err) { 
        callback(null,err); 
       } 
       var lines = data.split('\n'); // get the lines 
       lines.forEach(function(line) { // for each line in lines 
        if (line.indexOf(searchStr) != -1) { // if the line contain the searchSt 
         results.push(line); 
         callback(results,null); 
        } 
       }); 
      }); 
    }), function(error, result) { 
     results.map(result,function (result){ 
      console.log(result); 
     }); 
    }; 
} 
+0

嘗試反向參數:callback(results,null);在確定的結果 –

+0

在app.js我試圖通過第一個錯誤像功能(錯誤,行)' – hussain

+0

是的,但是當好的時候,params倒過來 –

回答

2

注:這個答案的一個擴展trincot's answer。所以如果這回答你的問題,請將他標爲答案!

你說:在所有文件一旦fs.readFile循環並獲得匹配的數據,並將其推到結果話,我不認爲.map是此相應的功能,是誠實的。這是爲了將數組中的每個元素轉換爲另一個,這不是你正在做的。

更好的方法是.eachSeries一次讀取一個文件。

將第二個callback重命名爲其他內容是個好主意,例如done不要混淆你自己(和其他人)。調用done()是爲了告訴對文件的操作完成,因爲我們正在讀取文件「完成」。

最後,小心你的錯別字。第一個可能阻止你進入最後一部分。

var results = []; 
var searchStr; 

function readFile(str, logFiles, callback) { 
    searchStr = str; 
    // loop through each file 
    async.eachSeries(logFiles, function (logfile, done) { 
     // read file 
     fs.readFile('logs/dit/' + logfile.filename, 'utf8', function (err, data) { 
      if (err) { 
       return done(err); 
      } 
      var lines = data.split('\n'); // get the lines 
      lines.forEach(function(line) { // for each line in lines 
       if (line.indexOf(searchStr) != -1) { // if the line contain the searchSt 
        results.push(line); 
       } 
      }); 
      // when you are done reading the file 
      done(); 
     }); 

    // wrong: }), function (err) { 
    }, function (err) { 
     if (err) { 
      console.log('error', err); 
     } 
     console.log('all done: ', results); 

     // wrong: results.map(result, function (result){ 
     results.map(function (result){ 
      console.log(result); 
     }); 

     // send back results 
     callback(results); 
    }); 
} 
+0

與你的方法我得到'結果'到客戶端,有問題讓我們假設,如果用戶serach'id0536'如果任何行包含此id它將首次呈現結果,兩個問題#1如果我搜索相同的字符串兩次推它相同的數組和發送兩行#2如果我搜索不同字符串值,它發送第一個搜索的結果。 – hussain

+0

@Mikey,很好的發現,雙'callback'變量在我的答案中讓我困惑,我將刪除(+1)。 – trincot

+0

@ hussain,因爲你的問題已經明確地得到解答,請將任何後續問題作爲新問題提出。 – trincot