0

I am new to node js, I want to execute a command in node js and want to display the running status of the command to the terminal and also to some log file.

// Displaying the output in terminal but I am not able to access child.stdout
const child = spawn(command,[], {
      shell: true,
      cwd: process.cwd(),
      env: process.env,
      stdio: 'inherit',
      encoding: 'utf-8',
    });

// Pushing the output to file but not able to do live interaction with terminal
const child = spawn(command,[], {
      shell: true,
      cwd: process.cwd(),
      env: process.env,
      stdio: 'pipe',
      encoding: 'utf-8',
    });

Is it possible to do both? Please help me with this?

Thanks in advance.

1 Answers1

2

You can specify separate options for stdin, stdout and stderr:

const child = spawn(command,[], {
      shell: true,
      cwd: process.cwd(),
      env: process.env,
      stdio: ['inherit', 'pipe', 'pipe'],
      encoding: 'utf-8',
    });

This way the subprocess inherits stdin and you should be able to interact with it. The subprocess uses pipes for stdout (and stderr) and you can write the output to a file. Because output is not sent to the terminal by the subprocess, you need to write the output to the terminal yourself. This can easily be done by piping:

// Pipe child stdout to process stdout (terminal)...
child.stdout.pipe(process.stdout);

// ...and do something else with the data.
child.stdout.on('data', (data) => ...);

This probably only works correctly if the subprocess is a simple command line program and does not have an advanced text-based UI.

rveerd
  • 3,620
  • 1
  • 14
  • 30
  • I tried this, but the problem here is for example the command I am running is asking for some inputs like: ``` Enter your name: Enter your age: ``` In these cases, it's not showing the ```Enter your name and Enter your age ``` because we are piping stdout. – lakshmiravali rimmalapudi Jun 27 '21 at 07:52
  • Here I can use ```stdio: 'inherit',``` this, but I want to read the entire data in terminal, Is it possible to get the data that is in terminal after the command execution? – lakshmiravali rimmalapudi Jun 27 '21 at 07:55
  • Yes, you are piping stdout so you need to write the data to the terminal yourself. – rveerd Jun 28 '21 at 06:43
  • I have updated the answer with an exampe of how the handle the child stdout. – rveerd Jun 28 '21 at 09:47
  • But this will not give the interactiveness with the terminal right? The same example I mentioned above ```Enter your name``` will be output to the terminal once the command execution is done but not in between the command execution. – lakshmiravali rimmalapudi Jun 30 '21 at 08:08
  • No, this should work. I have tested it by spawning `npm init`. – rveerd Jun 30 '21 at 09:01
  • This is the sample script I am using ``` #!/bin/bash``` ```read -p "Enter Your Name: " username``` ```echo "Welcome $username!"``` running command as sh input.sh, but it is not asking ```Enter Your Name:``` in the terminal but taking the username and printing it in terminal(```Welcome $username!```). – lakshmiravali rimmalapudi Jul 01 '21 at 05:55
  • That is because `read -p` outputs to stderr, not stdout. You need to also pipe stderr or use `echo -n "Enter your name: "` for the prompt. – rveerd Jul 01 '21 at 06:46