Is it possible to pass the output of one process created by ProcessBuilder to another process created by another ProcessBuilder? For example, if I’m trying to execute this shell command:
ls | grep build.xml
how should I do it with ProcessBuilder?
as @erdinc suggested, I tried this:
Process process = Runtime.getRuntime().exec("ls");
InputStream is = process.getInputStream();
byte[] buf = new byte[1000];
is.read(buf);
String parameter = new String(buf);
System.out.println("grep build " + parameter);
Process proc2 = Runtime.getRuntime().exec("grep build " + parameter);
InputStream is2 = proc2.getInputStream();
byte[] buf2 = new byte[1000];
is2.read(buf2);
String result = new String(buf2);
System.out.println("proc2 result: " + result);
but it produces different result compare to when I run the script directly in the shell. Where did I do wrong?
Solved: Please see Philipp Wendler solution
The problem with the solution you have is that it reads only the first 1000 bytes from the output of ls and passes them to grep. As you don’t know the amount of output from ls before, you need to read it iteratively until it is exhausted.
Here is a solution using BufferedReader, which will send each line of output to grep:
Of course you need to add the appropriate error-handling here.
You can omit the Reader and Writer and pass
byte[]arrays directly from the input to the output stream if this solution is too slow.However, a much better solution would be not to use ls and grep to look for a file in the filesystem, but to use the appropriate Java API. For example if you create a
Fileobject for the directory you are interested in, you can use the variouslistFilesmethods on it to list all files in this directory. This method is much easier, portable, less error-prone and probably faster.