2013-04-19 2 views
1

Я использую node.js для выполнения поиска DNS для возврата и IP-адреса (http://nodejs.org/api/dns.html). В этом примере я могу получить свой результат для правильной записи, хотя я бы предпочел иметь доступ к переменной за пределами области обратного вызова. Как это возможно?Как вернуть значение из обратного вызова

Мой текущий код:

var domain = 'google.co.uk'; 

dns.lookup(domain, function (err, aRecord) { 
    if (err) throw err; 
    console.log(aRecord); 
}); 

В идеале, я хотел бы быть в состоянии выполнить что-то вдоль линий:

var domain = 'google.co.uk'; 

var myfunction = dns.lookup(domain, function (err, aRecord) { 
    if (err) throw err; 
    return aRecord; 
}); 

var result = myfuction(domain); 
+0

Невозможно. Если бы это было так, вам не нужно было бы предоставлять обратный вызов. См. Первую часть [мой ответ здесь] (http://stackoverflow.com/a/14220323/218196) для объяснения синхронного и асинхронного кода. –

+0

Потенциальная копия этого дуплета: http://stackoverflow.com/questions/6847697/how-to-return-value-from-callback-функция. – Mogsdad

+0

Описывается разумная обходная ситуация [здесь] (http://stackoverflow.com/a/6847754/1677912). – Mogsdad

ответ

2

Как есть, это невозможно, так как оно асинхронно. Вы можете поместить весь свой код внутри обратного вызова, но это может быть не самое лучшее.

Один из способов, с помощью которого разработчик может работать с асинхронным возвратом данных, использует Promises. Лучшая статья, которую я когда-либо читал о концепции обещания, таков: http://blog.jcoglan.com/2013/03/30/callbacks-are-imperative-promises-are-functional-nodes-biggest-missed-opportunity/ Дайте ей прочитать!

В узле, хорошо известная библиотека обещания Q: https://github.com/kriskowal/q

Если вы хотите более концептуальный approah к поведению асинхронного/управления в Javascript, есть очень хорошая книга Тревор Бернхэмом называется «Асинхронный Javascript» http://pragprog.com/book/tbajs/async-javascript

0

Вы не можете. Javascript является асинхронным. Вы должны поместить весь свой код с логикой в ​​обратный вызов.

Javascript будет продолжать выполнять ваш код после var result = myfuction(domain); и не будет ждать завершения обратного вызова. И ваша функция не вернет ничего (неопределенное) в результате

+3

JavaScript не является асинхронным сам по себе, но большинство методов узла являются асинхронными. –

+0

То, что я имел в виду :) Операторы называются один за другим, конечно. – shift66

1

Вы можете (и должны) использовать Promise, как предложил Саймон. Запрет опечаток должен работать.

Одна хорошая вещь в этом подходе заключается в том, что вы можете передавать обещания в качестве аргументов другим функциям. Затем вы можете написать функцию, которая использует данные, возвращаемые функцией поиска dns, путем принятия (и возврата) обещания.

function useLookup(lookupPromise){ 
    var deferred = Q.defer(); 

    lookupPromise.then(function(lookupResponse){ 
     deferred.resolve(lookupResponse); 
    }).fail(function(err){ 
     deferred.reject(err); 
    }) 

    return deferred.promise; 
}