Как мне написать неблокирующий код в Node.js? - PullRequest
20 голосов
/ 15 апреля 2011

Я могу написать неблокирующую I / O в Node.js очень легко.Это то, для чего создана вся библиотека.

Но любое вычисление блокируется.Любое сообщение, проходящее через отправителей событий, блокирует .

Например, отправляющие события разрешаются немедленно и, таким образом, блокируются:

var e = new process.EventEmitter;
e.on("foo", function() {
    console.log("event");
});
process.nextTick(function() {
    console.log("next tick");
});
setTimeout(function() {
    console.log("timeout");
}, 0);
e.emit("foo");

> event
> next tick
> timeout

Помимо переноса вызовов в nextTick, как сделать код неблокирующим?

Я хочу сделать как можно меньше вычислений за цикл цикла событий, чтобы я мог одновременно обслуживать как можно больше клиентов.

Как мне написать свой код неблокирующим образом?

А когда у меня есть неблокирующий код, как мне масштабировать его по нескольким процессам?

Один вариант ожидаетAPI подпроцесса WebWorker будет завершен.

Ответы [ 2 ]

9 голосов
/ 15 апреля 2011

JavaScript является однопоточным. Это означает, что независимо от событий, тайм-аутов или задержек с помощью nextTick любое выполненное вычисление заблокирует весь процесс.

Если вы разделите свою обработку по шагам, используя process.nextTick, как это делается с setTimeout(fn, 0) на стороне клиента, чтобы избежать блокировки пользовательского интерфейса, вы можете распределить свою рабочую нагрузку на более длительный промежуток времени, предоставив место для других функций. бежать.

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

child_process.fork() был добавлен в v0.5 несколько дней назад. Это упрощает создание и взаимодействие дочерних процессов - не совсем API веб-работников, но близко, см. URL https://github.com/joyent/node/blob/master/doc/api/child_process.markdown.

1 голос
/ 15 апреля 2011

В JavaScript нет реальной многопоточности, и это то, что вам нужно, чтобы сделать вызов неблокирующим.Единственное, о чем я могу думать, это веб-работники: https://developer.mozilla.org/en/Using_web_workers

...