Node.js запускает программу обновления и закрывает основную программу - PullRequest
1 голос
/ 22 мая 2019

Я проверяю, есть ли в моем приложении обновление, отправляя эхо-запрос по определенному URL-адресу, pinging по этому URL-адресу возвращает мне обновление или нет.

Теперь у меня есть файл powershell, который фактически обрабатывает обновление, поэтомуЯ пытаюсь запустить этот файл powershell изнутри моего приложения.

У меня это работает, я могу порождать мой файл обновления, и он будет работать, и все хорошо.Тем не менее, мое приложение остается открытым все время, а это означает, что после завершения обновления у меня будет запущено 2 экземпляра.

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

Вот мой код:

child = spawn("powershell.exe",['-ExecutionPolicy', 'ByPass', '-File', require("path").resolve(__dirname, '../../../../updater.ps1')]);
child.unref();

self.close();

Однако, когда я пытаюсь закрыть приложение, создается впечатление, что средство обновления никогда не запускается.Или, скорее, я считаю, что он запускается, но закрывается, когда закрывается основное приложение.

У меня есть строка child.unref(), которая, как я думал, должна была создать порожденное окно, не привязанное к основному приложению, ноUpdater не будет оставаться открытым.

Я также пытался добавить {detached: true} в качестве 3-го параметра моей команды spawn(), но это не имело никакого значения в том, как оно выполнялось.

Как я могу создать программу обновления отдельно от моего приложения?

1 Ответ

1 голос
/ 23 мая 2019

Чтобы запустить обновление отдельно от вашего приложения, я думаю, что вы должны использовать скрипт вместо встроенного параметра. Это гарантирует, что ОС создаст отдельный процесс из приложения вашего узла. Например:

var fs = require('fs');
var spawn = require('child_process').spawn;
var out = fs.openSync('./out.log', 'a');
var err = fs.openSync('./out.log', 'a');

var child = spawn('./myscript.sh', [], {
  detached: true,
  stdio: [ 'ignore', out, err ]
});

child.unref();

setTimeout(function(){
    process.exit();
}, 1000);

myscript.sh выглядит так:

sleep 5; ls >> out2.log

Приведенный выше код принудительно завершит работу узла (через 2 секунды), но непосредственно перед запуском сценария bash (который будет ждать 5 секунд для запуска команды ls). Запуск этого кода приводит к 2 выходным файлам (out.log и out2.log). Первый (out.log) - это вывод приложения узла, вызывающего дочерний процесс, а второй (out2.log) - результат выполнения сценария, перенаправленного из отдельного сценария.

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

var fs = require('fs');
var spawn = require('child_process').spawn;
var out = fs.openSync('./out.log', 'a');
var err = fs.openSync('./out.log', 'a');

var child = spawn('ls', [], {
  detached: true,
  stdio: [ 'ignore', out, err ]
});

child.on('exit', (code) => {
    console.log(`Child exited with code ${code}`);
});

child.unref(); 

Во втором примере результат ls будет сохранен в файле out.log. Так как основной процесс будет ждать ребенка до завершения.

Так что все зависит от того, чего вы желаете достичь. Первое решение не красиво, но запустит что-то действительно отдельно от вашего приложения узла.

...