2012-04-29 1 views
1

内client.multi使用して、私は、デバイスのリストをretriveし、それらのそれぞれのステータスやラベルを取得する必要があり、次のコードしている:node_redis:forEachの

app.get('/test', function(req, res){ 
    db.smembers("devices", function(err1, devices){ 
    var jsonObj = {}; 
    if(!err1) { 
     var i = 0; 
     devices.forEach(function(id){ 
      db.multi([ 
      ["get", id + ":label"], 
      ["get", id + ":status"], 
      ]).exec(function (err, replies) { 
      jsonObj[id] = {"label":replies[0], "status":replies[1]}; 
      console.log(jsonObj);  // stuff is added on each loop 
      }); 

      i = i + 1; 
      if(i == devices.length){ 
      console.log(jsonObj);  // jsonObj is {}  
      h.respond(res, jsonObj); 
      } 
     }); 
    } else { 
     h.respond(res, { "error" : err1 }); 
    } 
    }); 
}); 

デバイスは、IDのリストです。各IDには、「ID:ステータス」、「ID:ラベル」の2つのキーがあります。

h.respondは、http応答を送信するヘルパーメソッドです。

新しいデータが各ループのjsonObjに追加されているのがわかりますが、すべてのループが完了すると空になります。

+0

同様の問題がありました。良い質問 – Federico

答えて

2

コードは非同期で実行されており、Redis呼び出しが実際に完了する前にdevices.lengthまでカウントアップしています(継続する前に返されるコールバックをmultiから待つことはありません)。あなたの小切手をコールバックに移すことでこれを防ぐことができます。

app.get('/test', function(req, res){ 
    db.smembers("devices", function(err1, devices){ 
    var jsonObj = {}; 
    if(!err1) { 
     var i = 0; 
     devices.forEach(function(id){ 
      db.multi([ 
      ["get", id + ":label"], 
      ["get", id + ":status"], 
      ]).exec(function (err, replies) { 
      jsonObj[id] = {"label":replies[0], "status":replies[1]}; 
      console.log(jsonObj);  // stuff is added on each loop 
      i = i + 1; 
      if(i == devices.length){ 
       console.log(jsonObj);  // jsonObj is {}  
       h.respond(res, jsonObj); 
      } 
      }); 


     }); 
    } else { 
     h.respond(res, { "error" : err1 }); 
    } 
    }); 
}); 

はおそらく別の関数にこのコードを移動するために、より理にかなって、うまくいけばあなたのアイデアを得ます。 asyncのような非同期ライブラリは、このような並列非同期ループをはるかに簡単にするヘルパーメソッドを提供します。

+0

私はリグのコールバックレベルにいませんでした。ありがとうございました。 – Luc

+0

きれいに見つかった!私は[async](https://github.com/caolan/async)の勧告の2番目の方法です。私はこのライブラリを十分に推薦することはできません。複雑さを最小限に抑えて、この種のフロー制御をきれいにするのに役立ちます。 –

関連する問題