I have a script which executes a program several times, producing about 350 lines of output to both STDERR and STDOUT. Now, I need to execute the script in Java, thereby printing the output streams to their original destinations. So, basically, I execute the script from inside a Java class, maintaining the original behavior for the user.
The way I do this is inspired from suggestions like Reading streams from java Runtime.exec and, functionally, works fine.
Process p = Runtime.getRuntime().exec(cmdarray);
new Thread(new ProcessInputStreamHandler(p.getInputStream(), System.out)).start();
new Thread(new ProcessInputStreamHandler(p.getErrorStream(), System.err)).start();
return p.waitFor();
And the class ProcessInputStreamHandler:
class ProcessInputStreamHandler implements Runnable {
private BufferedReader in_reader;
private PrintStream out_stream;
public ProcessInputStreamHandler(final InputStream in_stream, final PrintStream out_stream) {
this.in_reader = new BufferedReader(new InputStreamReader(in_stream));
this.out_stream = out_stream;
}
@Override public void run() {
String line;
try {
while ((line = in_reader.readLine()) != null) {
out_stream.println(line);
}
} catch (Exception e) {throw new Error(e);}
out_stream.flush();
}
}
Now regarding my problem statement: While the execution of the script takes about 17 seconds, the "encapsulated" execution takes at least 21 seconds. Where do I lose these 4 or more seconds?
I already tried using a ProcessBuilder with redirection of STDERR to STDOUT, using POSIX vfork with libraries like https://github.com/axiak/java_posix_spawn, using a byte buffer instead of a BufferedReader... everything with no positive result at all.
Are there any suggestings? I understand that there will be some performance loss, but 4 seconds seem to be a bit much to me...
Appreciate any suggestions!
Best Regards and Thanks in Advance.
STDERRandSTDOUT? Then you could run the Java script wrapper without theProcessInputStreamHandlerobjects to check whether that still takes an additional 4 seconds. If this is the case non-blocking I/O (nio) might help you.