2

when I try to run child process and put to it stdin some text it throws error. here is code of child process:

import java.io.Console;

public class HelloWorld {
    public static void main(String[] args) {
        System.out.println("started");

        Console console = System.console();

        while (true) {
            String s = console.readLine();
            System.out.println("Your sentence:" + s);
        }
    }
}

code of script which run this process:

var spawn = require('child_process').spawn;

var child = spawn('java', ['HelloWorld', 'HelloWorld.class']);


child.stdin.setEncoding('utf-8');

child.stdout.pipe(process.stdout);


child.stdin.write("tratata\n");

// child.stdin.end();

it throws:

events.js:161
  throw er; // Unhandled 'error' event
  ^

Error: read ECONNRESET
    at exports._errnoException (util.js:1028:11)
    at Pipe.onread (net.js:572:26)

notice, when I uncomment line with child.stdin.end(); it only ends whithout any reaction

Dmytro Nalyvaiko
  • 1,664
  • 4
  • 16
  • 27
  • FWIW `child.stdin.setEncoding('utf-8');` is not correct. `setEncoding()` is for `Readable` streams, but `child.stdin` is to be used as a `Writable` stream. – mscdex Apr 05 '17 at 20:32
  • Also, did you try using CRLF instead of LF for line endings (e.g. `child.stdin.write("tratata\r\n");`)? – mscdex Apr 05 '17 at 20:36

1 Answers1

1

The one thing you need to make the script work was to add:

process.stdin.pipe(child.stdin);

If you added this before the child.stdin.write, that would solve half the problem. The other half had to do with the Java side. If the java program is not launched from a console by typing java HelloWorld, then Console will return null thus you will get a NullPointerException if you tried to use Console.readLine. To fix, this use BufferedReader instead.

Change your script to this:

const spawn = require('child_process').spawn;
const child = spawn('java', ['HelloWorld'], {
    stdio: ['pipe', process.stdout, process.stderr]
});

process.stdin.pipe(child.stdin);
setTimeout(() => {
    child.stdin.write('tratata\n');
}, 1000);

Then change your java code to this:

import java.io.BufferedReader;
import java.io.InputStreamReader;

import java.io.IOException;

public class HelloWorld {
    public static void main(String[] args) throws IOException {
        System.out.println("started");

        try(BufferedReader console = new BufferedReader(new InputStreamReader(System.in))) {
            for (String line = console.readLine(); line != null; line = console.readLine()) {
                System.out.printf("Your sentence: %s\n", line);
            }
        }

    }
}

See:

smac89
  • 39,374
  • 15
  • 132
  • 179