2011-09-16 2 views
1

Я довольно новичок в NodeJS и JavaScript в целом. Вот мой сценарий:Переменная вне обратного вызова в NodeJS

var data = []; 

    client.query(

     'SELECT * FROM cds', 
     function selectCb(err, results, fields) { 

     if (err) { 
      throw err; 
     } 

     console.log(results); 
     console.log(fields); 

     data.push(results); 
     } 
    ); 

    console.log(data); 

Как я могу получить доступ к results (или data) вар вне обратного вызова? Я не хочу писать тонну обратных вызовов внутри друг друга при выполнении запросов.

+0

Я не уверен, насколько я понимаю. Точка этих обратных вызовов заключается в том, что остальная часть кода может выполняться и не должна ждать запроса. Таким образом, предполагая, что 'results' является элементом' data' в вашей последней строке, не имеет большого смысла, потому что запрос еще не завершен. – pimvdb

+0

Я понял, что мой дизайн был неправильным и надеялся на лучшее решение. Вы знаете, как я могу получить данные из запроса с помощью node-mysql без использования обратного вызова? – mikelbring

+0

Похоже, вам нужен синхронный код, так что функция ждет завершения запроса. Я не уверен, что это лучший подход. Есть ли причина, по которой вы не просто выполняете зависимости запроса в обратном вызове? – pimvdb

ответ

1

То, о чем вы просите, является синхронным (или блокирующим) исполнением, и это действительно противоречит дизайну и духу node.js.

Узел, как и JavaScript, является однопоточным. Если у вас есть код блокировки, то весь процесс остановлен.

Это означает, что вы должны использовать обратные вызовы для всего, что займет много времени (например, запрос из базы данных). Если вы пишете инструмент командной строки, который проходит через один проход, вы можете захотеть жить с блокировкой. Но если вы пишете какое-нибудь отзывчивое приложение (например, веб-сайт), то блокирование - это убийство.

Значит, может, чтобы кто-то мог дать вам ответ о том, как сделать это блокирующим синхронным звонком. Если это так, и если вы его реализуете, вы делаете это неправильно. Вы также можете использовать многопоточный скриптовый язык, например Ruby или Python.

Письменные обратные вызовы не так уж плохи, но это требует некоторой мысли об архитектуре и упаковке, которые, вероятно, незнакомы для людей, не привыкших к стилю.

+0

Я исхожу из PHP-фона, возможно, поэтому я смущен. Похоже, мне нужно переосмыслить, как я создаю приложения при использовании NodeJS. Спасибо – mikelbring

+0

nodeJS - это другая парадигма, не пытайтесь закодировать ее как синхронные системы, обратные вызовы - это то, что позволяет запускать так быстро, как это делает (неблокирование). В начале это немного сложнее, но все же намного проще, чем пытаться реализовать асинхронный код на таких языках, как C, Java или PHP –

1

Node.js использует Continuation Passing Style для всех его асинхронных интерфейсов. Существует лот обсуждения вокруг этого и modules, которые были созданы для облегчения боли вложенных обратных вызовов. Слухи о том, что node.js могут начать повторно вводить Promises в его ядро ​​в ветке v0.7.x, но я не уверен, что это правда или нет.

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

var data = [], 
    handler = function(err, results, fields) { 
     if (err) { 
      throw err; 
     } 
     ... 
    }; 
client.query('SELECT * FROM cds', handler); 
Смежные вопросы