2013-05-20 3 views
3

Я пытаюсь получить кучу ключей из экземпляра redis. Я использую node-redis. Я использую цикл:Получение нескольких ключей с помощью node-redis

for(var i=1; i<=num; ++i){ 
    client.get(key + ':' + num, function (err, reply) { 
     obj[num] = reply; 
    }); 
} 
return obj; 

Но obj это просто не определено. Я чувствую, что у меня могут быть проблемы, потому что get, очевидно, называется асинхронно. Есть ли другой способ достичь этого? Должен ли я просто сохранить значения в отсортированном наборе?

+1

Где 'obj' объявлен? – Ian

ответ

10

Я собираюсь угадать предположение, основанное на интерфейсе кодирования, и ваши комментарии, что client.get() является асинхронным. Это означает, что он вызывает функцию обратного вызова, переданную ему «через некоторое время», а не сразу. Таким образом, вы не можете использовать шаблоны синхронного кодирования для сбора результатов от нескольких вызовов до client.get(), потому что результаты в obj еще недоступны, когда ваша функция возвращается. Таким образом, obj еще не заполнен результатами.

Если вы хотите знать, когда выполняются множественные асинхронные вызовы, вам необходимо ввести код совсем по-другому. И результаты будут ТОЛЬКО доступны внутри функций обратного вызова, а не в конце вашей функции.

В целом, я вижу несколько проблем с кодом:

  1. client.get() является асинхронным, так что до сих пор не закончена, когда ваша функция возвращает
  2. Вы, вероятно, следует использовать i, не num в вашем client.get() чтобы каждый раз через цикл for генерировался другой запрос.
  3. Значение i в цикле должно быть заморожено в закрытии, чтобы сохранить его значение для использования в функции обратного вызова, которая вызывается позже.
  4. Если obj на самом деле не определено, это может быть связано с тем, что вы не инициализировали его пустым объектом.

Вот один из способов сделать это:

var obj = {}; 
var remaining = num; 
for(var i=1; i<=num; ++i){ 
    // create a closure here to freeze the value of i in the callback 
    (function(i) { 
     client.get(key + ':' + i, function (err, reply) { 
      obj[i] = reply; 
      // see if all asynch calls are done yet 
      --remaining; 
      if (remaining === 0) { 
       // all asynch calls to client.get() are done now 
       // in here, you can use the obj object and the results put on it 
      } 
     }); 
    })(i); 
} 
+0

Да, я подумал, что это может быть проблема асинхронной работы. И 'i' vs' num' вещь была просто ошибкой, которую я набрал на вопросы. И ваше решение прекрасно работает. – alf

+0

четкий и лаконичный –

Смежные вопросы