0

I have following code:

ProcessBuilder pb = new ProcessBuilder("dir"); // or cat in linux
Process p = pb.start();
p.waitFor();
String result = IOUtils.toString(p.getInputStream(), "UTF-8");
System.out.println(result);

It throws

java.io.IOException: Cannot run program "dir": CreateProcess error=2, The system cannot find the file specified
    at java.lang.ProcessBuilder.start(ProcessBuilder.java:1048) ~[na:1.8.0_111]

I understand that I can write something like this:

ProcessBuilder pb = new ProcessBuilder("test.bat");

and inside test.bat you can write

dir

But it returns:

D:\nsd-rest>dir
 Volume in drive D is SECOND
 Volume Serial Number is CE52-8896

 Directory of D:\nsd-rest

03/24/17  15:53    <DIR>          .
03/24/17  15:53    <DIR>          ..
03/24/17  12:00               249 .gitignore
03/24/17  16:54    <DIR>          .idea
03/24/17  15:01    <DIR>          .mvn
03/24/17  12:00             7,058 mvnw
03/24/17  12:00             5,006 mvnw.cmd
03/24/17  15:53             6,265 nsd-rest.iml
03/24/17  15:52             1,993 pom.xml
03/24/17  15:01    <DIR>          src
03/24/17  15:19    <DIR>          target
03/24/17  16:52                 3 test.bat
               6 File(s)         20,574 bytes
               6 Dir(s)  587,412,844,544 bytes free

Row

D:\nsd-rest>dir

is redundant.

When I invoke bat file I feel that I do something incorrect.

Can you provide correct solution?

P.S. instead of dir can be any executable file.

zeppelin
  • 8,947
  • 2
  • 24
  • 30
gstackoverflow
  • 36,709
  • 117
  • 359
  • 710
  • Just a thought, Java may not have access to the same environment variables as your command prompt. (e.g. %PATH%) – CraigR8806 Mar 24 '17 at 14:02
  • @CraigR8806 Is there way to add dir to path ? – gstackoverflow Mar 24 '17 at 14:05
  • First argument in commands for process builder is treated as executable file, from what I can see, there's no exception to that rule. What you actually want is execute command line process with passing "dir" as first argument to that process. – M. Prokhorov Mar 24 '17 at 14:10
  • [This may help] (http://stackoverflow.com/questions/19621838/createprocess-error-2-the-system-cannot-find-the-file-specified) – CraigR8806 Mar 24 '17 at 14:10
  • `waitFor()` returns after the process has *finished.* Call it *after* you are done reading from the InputStream. – VGR Mar 24 '17 at 14:30
  • **String result = IOUtils.toString(p.getInputStream(), "UTF-8"); p.waitFor();** @VGR - is it correct ? – gstackoverflow Mar 24 '17 at 14:51
  • Yes. Although, you really should check the value returned by p.waitFor(). If it’s not zero, the external command failed. How you choose to do that is up to you, but your program should not act like the process succeeded. – VGR Mar 24 '17 at 14:55

1 Answers1

1

There's no dir executable actually - e.g. you can't find dir.exe anywhere on windows. This is pseudo-command which exist in cmd.exe executable context only.

If you want to get "dir" output - you can simply run cmd.exe /c dir

Also there's bug in your program:

p.waitFor();
String result = IOUtils.toString(p.getInputStream(), "UTF-8");

If program output is large enough and wouldn't fit into output buffer, p.waitFor() would never end - because buffer is overflown and nobody is reading it. I'd suggest swap these lines(or even better - read couple articles about interprocess IO, that's related to everything not to java world only).

Dmitry Zvorygin
  • 473
  • 6
  • 14