Node.js Spawn vs. Execute

5

В онлайн-обучающем видео я смотрю, чтобы узнать Node, рассказчик говорит, что "spawn лучше для более длинных процессов, связанных с большими объемами данных, тогда как выполнение лучше для коротких бит данных".

Почему это? В чем разница между функциями child_process spawn и execute в Node.js, и когда я знаю, какой из них использовать?

Теги:
function
spawn

4 ответа

8
Лучший ответ

Основным отличием является то, что spawn больше подходит для длительных процессов с огромным выходом. ввод/вывод потоков spawn с дочерним процессом. буферизованный вывод exec в небольшом (по умолчанию 200K) буфере. Также, как я знаю, exec сначала вызывает подоболочку, затем попытайтесь выполнить ваш процесс. Если коротко, коротко, используйте spawn в случае, если вам нужно много данных, передаваемых из дочернего процесса, и exec если вам нужны такие функции, как конвейеры оболочки, перенаправления или даже если вам нужно выполнить несколько программ за один раз.

Несколько полезных ссылок - DZone Hacksparrow

7

Хорошее место для начала - документация NodeJS.

Для "порождения" состояние документации:

Метод child_process.spawn() порождает новый процесс, используя данную команду с аргументами командной строки в аргументах. Если опущено, args по умолчанию является пустым массивом.

В то время как для "exec":

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

Похоже, главное - нужно ли вам обрабатывать вывод команды или нет, что, я думаю, может повлиять на производительность (я не сравнивал). Если вы заботитесь только о завершении процесса, а не о его выводе, тогда "spawn" будет вполне достаточно.

0
  • дочерний процесс, созданный spawn()

    • не порождает раковину
    • потоковые данные, возвращаемые дочерним процессом (поток данных является постоянным)
    • не имеет предела размера передачи данных
  • дочерний процесс, созданный exec()

    • порождает оболочку, в которой выполняется переданная команда
    • буферизует данные (ждет, пока процесс закроется, и передаст данные в чанк)
    • максимальная скорость передачи данных 200 КБ (по умолчанию)

-main.js (файл)

var {spawn, exec} = require('child_process');

    // 'node' is an executable command (can be executed without a shell) 
    // uses streams to transfer data (spawn.stout)  
var spawn = spawn('node', ['module.js']);     
spawn.stdout.on('data', function(msg){         
    console.log(msg.toString())
});

    // the 'node module.js' runs in the spawned shell 
    // transfered data is handled in the callback function 
var exec = exec('node module.js', function(err, stdout, stderr){
    console.log(stdout);
});

-module.js(baiscally возвращает сообщение каждую секунду в течение 5 секунд, чем выход)

var interval;
interval = setInterval(function(){
    console.log( 'module data' );
    if(interval._idleStart > 5000) clearInterval(interval);
}, 1000);
  • дочерний процесс spawn() возвращает module data сообщений каждую 1 секунду в течение 5 секунд, поскольку данные "потоковые"
  • дочерний процесс exec() возвращает module data module data module data module data module data только одного сообщения через 5 секунд (когда процесс закрыт), потому что данные "буферизируются"

Обратите внимание, что ни дочерние процессы spawn() ни дочерние процессы exec() не предназначены для запуска модулей узлов, эта демонстрация предназначена только для демонстрации различия (если вы хотите запускать модули узлов, поскольку дочерние процессы используют вместо этого метод fork())

0

Наиболее существенное различие между child_process.spawn и child_process.exec заключается в том, что они возвращают - spawn возвращает поток, а exec возвращает буфер.

child_process.spawn возвращает объект с потоками stdout и stderr. Вы можете нажать на поток stdout, чтобы прочитать данные, которые дочерний процесс отправляет обратно в Node. stdout, являющийся потоком, имеет "данные", "конец" и другие события, которые имеют потоки. spawn лучше всего использовать, когда вы хотите, чтобы дочерний процесс возвращал большой объем данных в Node - обработка изображений, чтение двоичных данных и т.д.

child_process.spawn является "асинхронно асинхронным", что означает, что он начинает отправлять данные из дочернего процесса в потоке, как только дочерний процесс начинает выполняться.

child_process.exec возвращает весь буферный вывод дочернего процесса. По умолчанию размер буфера установлен на 200k. Если дочерний процесс возвращает что-то большее, ваша программа завершится сбоем с сообщением об ошибке "Ошибка: превышен maxBuffer". Вы можете решить эту проблему, установив больший размер буфера в параметрах exec. Но вы не должны этого делать, потому что exec не предназначен для процессов, которые возвращают ОГРОМНЫЕ буферы в Node. Вы должны использовать Spawn для этого. Так для чего вы используете exec? Используйте его для запуска программ, которые возвращают статусы результатов, а не данные.

child_process.exec является "синхронно асинхронным", то есть, хотя exec асинхронный, он ожидает завершения дочернего процесса и пытается вернуть все буферизованные данные одновременно. Если размер буфера exec не установлен достаточно большим, он завершается с ошибкой "maxBuffer Превышен".

Ещё вопросы

Сообщество Overcoder
Наверх
Меню