wayofthefuture
wayofthefuture

Reputation: 9405

Why can't I respond with output from child process in Node JS?

I am using Node JS with Express and trying to execute a script and return the output of that script to the client via AJAX. The script is completing successfully, but for some reason I cannot get the output to show in the post response.

let childProcess = require('child_process');

router.post('/update', (req, res) => {
    childProcess.exec('/home/dir/app/update.sh', { shell: '/bin/bash' }, (error, stdout, stderr) => {
        res.json({ error, stdout, stderr });
    });
});

The Node process is run using Forever. If I look at the forever log, it shows:

Forever detected script was killed by signal: SIGKILL

Not sure what that means. It appears the script is completing successfully though.

EDIT To address Aikon's answer below. I tried the following and still no go.

router.post('/update', (req, res) => {
    console.log('start...');

    childProcess.exec('/home/dir/app/update.sh', { shell: '/bin/bash' }, (error, stdout, stderr) => {
        console.log('done');

        error = error || '';
        stdout = stdout || '';
        stderr = stderr || '';

        res.json({ error, stdout, stderr });
    });
});

It's as if the success function is never firing because it never logs "done" in the console. It just logs "start..." and the SIGKILL error above in the console.

Upvotes: 2

Views: 524

Answers (3)

DarkKnight
DarkKnight

Reputation: 5944

Your script kill(and restart) itself before it can read output from child process.

Look at your update.sh again:

#!/bin/bash
git pull
npm install
npm run build

#this command restarts your script
forever restartall

You could remove last line of update.sh, and after sending response, the script just exits, forever should restart it with updated version.

router.post('/update', (req, res) => {
  childProcess.exec('/home/dir/app/update.sh', { shell: '/bin/bash' }, 
  (error, stdout, stderr) => {
    res.json({ error, stdout, stderr });
    process.exit();
  });
});

Upvotes: 1

Aikon Mogwai
Aikon Mogwai

Reputation: 5225

  1. If error is not empty then output is undefined => fail
  2. After stringify error is empty object.

'use strict';
let error = new Error('err');
let str = 'text';
let obj = {a: 10, b: 15}; // Try comment to get fall
console.log(JSON.stringify({error, str, obj}))

Upvotes: 1

slebetman
slebetman

Reputation: 113906

You have a syntax error in your code. Try:

res.json({ error: error, output: stdout, error_log: stderr });

alternatively you can do:

res.json([ error, stdout, stderr ]);

Upvotes: 0

Related Questions