【问题标题】:Running a shell script from Nodejs从 Nodejs 运行 shell 脚本
【发布时间】:2017-01-14 12:10:46
【问题描述】:

我有一个 shell 脚本 start.sh,它的工作是在后台生成多个 java 进程,然后像这样正常退出:

java -jar jar1.jar &
java -jar jar2.jar &
...
exit 0

打印一堆输出:

Starting jar1
Starting jar2
...

现在我希望 nodejs 调用 start.sh 来跟踪输出,以便在 starter.sh 完成时对它采取行动

问题是 Nodejs 认为 starter.sh 只有在所有已启动的 java 进程都死了时才完成。 这很奇怪,因为从 shell 中,starter.sh 立即退出并且不再与 java 进程有任何关系

如何使starter.sh 从节点调用时的行为方式相同?

这是我用来生成starter.sh的代码:

  const process = spawn('starter.sh', []);

  process.stdout.on('data', (data) => {
    console.log(`stdout: ${data}`);
    // prints 'Starting jarx' like expected
  });

  process.stderr.on('data', (data) => {
    console.log(`stderr: ${data}`);
  });

  process.on('close', (code) => {
    console.log(`child process exited with code ${code}`);
    // Not called unless all the spawned java processes are dead :(
  });

【问题讨论】:

    标签: node.js shell child-process spawn


    【解决方案1】:

    我感觉我的问题与与节点父节点共享stdio 的子进程有关。事实上,如果java 进程没有要写入的stdout,它们会在哪里写入。因此节点必须等待它们完成才能考虑starter.sh完成

    我已经决定给子进程它自己的stdio 并将starter.sh 输出写入文件:

      const out = fs.openSync('/tmp/command.out', 'w');
      const err = fs.openSync('/tmp/command.err', 'w');
    
      const process = spawn(command, args, {detached: true, stdio: ['ignore', out , err]});
      process.unref();
    
      process.on('close', (code) => {
        console.log(`child process exited with code ${code}`);
        console.log(fs.readFileSync('/tmp/command.out', 'utf8');
        console.log(fs.readFileSync('/tmp/command.err', 'utf8'));
      });
    

    这样close 回调会在starter.sh 完成后立即调用,我仍然可以访问它的输出。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2016-07-10
      • 2012-03-28
      • 2013-07-29
      • 2010-12-08
      • 2015-05-15
      相关资源
      最近更新 更多