Interaction with a Powershell Process Invoked from a Java Application

I am trying to start a Java application that creates a new powershell process at startup and then interacts with it several times later. Calling powershell.exe and getting it to execute one command and return the result works fine for me. The problem occurs if I do not want the powershell process to end / exit immediately, but remain open, so I can write its outputStream and get the results back from inputStream.

String input = "dir"; String[] commandList = {"powershell.exe", "-Command", "dir"}; ProcessBuilder pb = new ProcessBuilder(commandList); Process p = pb.start(); if(input != null) { PrintWriter writer = new PrintWriter(new OutputStreamWriter(new BufferedOutputStream(p.getOutputStream())), true); writer.println(input); writer.flush(); writer.close(); } //p.getOutputStream().close(); Gobbler outGobbler = new Gobbler(p.getInputStream()); Gobbler errGobbler = new Gobbler(p.getErrorStream()); Thread outThread = new Thread(outGobbler); Thread errThread = new Thread(errGobbler); outThread.start(); errThread.start(); System.out.println("Waiting for the Gobbler threads to join..."); outThread.join(); errThread.join(); System.out.println("Waiting for the process to exit..."); int exitVal = p.waitFor(); System.out.println("\n****************************"); System.out.println("Command: " + "cmd.exe /c dir"); System.out.println("Exit Value = " + exitVal); List<String> output = outGobbler.getOuput(); input = ""; for(String o: output) { input += o; } System.out.println("Final Output:"); System.out.println(input); 

This code returns the result of the "dir" command from powershell - great. But, as you can see, I'm trying to run the second dir command using

  PrintWriter writer = new PrintWriter(new OutputStreamWriter(new BufferedOutputStream(p.getOutputStream())), true); writer.println(input); writer.flush(); 

This has no effect - when I run my code, the second dir output is not displayed. I also experimented with the powershell.exe parameter to open powershell, but not close it right away:

 String[] commandList = {"powershell.exe", "-NoExit", "-Command", "dir"}; 

But then my code freezes, that is, Gobbler, which consumes the inputStream process, doesn’t read anything - oddly enough: they don’t even read the first line - there should be at least some output ....

I also tried closing the outputStream process after writing the second dir command - nothing changed.

Any help is greatly appreciated. thanks kurt

+6
source share
1 answer

This sounds correct for the nature of the process associated with another process. I think you are experiencing fairly standard behavior.

This is the key: p.waitFor()

From Java docs:

makes the current thread wait, if necessary, until the process represented by this process object is completed.

You cannot get the PowerShell output stream until it completes. When you start with -NoExit , it never exits, which is why you are facing a hang.

If you run ProcExp from Sysinternals, you can see how your Java process launches the PowerShell process for children.

Therefore, I do not think that you can interact with it, as with a living object in memory.

0
source

Source: https://habr.com/ru/post/905176/


All Articles