Java与命令提示进行交互

时间:2018-07-27 17:32:20

标签: java command-prompt

使用

String cmdString = "cmd.exe /c start python ";
Process p = Runtime.getRuntime().exec(cmdString);

我可以打开命令提示符并运行python。我现在想与命令提示符进行交互。我已经读过

public static void main(String[] args)
{

    BufferedWriter writerToProc;

    String scriptPath = "C:\\Users\\MichaelMi\\Documents\\SourceTree\\NODE-Sensor-Configurator\\src\\application\\resources\\BACnet-CMD-Line-Upgrader\\UpgradeApplication.py";
    String iniPath = "C:\\Users\\MichaelMi\\Documents\\SourceTree\\NODE-Sensor-Configurator\\src\\application\\resources\\BACnet-CMD-Line-Upgrader\\BACpypes.ini";

    String execString  = "python " + scriptPath + " --ini " + iniPath;
    String cmdString = "cmd.exe /c start " + execString ;

    try {
        Process p = Runtime.getRuntime().exec(cmdString);


        writerToProc = new BufferedWriter(new OutputStreamWriter(p.getOutputStream()));

        writerToProc.write(cmdString);
        writerToProc.flush();

        writerToProc.write("whois\n");
        writerToProc.flush();

        readErrors(p);
        readOutput(p);

    } catch (IOException e) {
        e.printStackTrace();
    }
}

public static void readOutput(Process p)
{
    BufferedReader stdInput = new BufferedReader(new InputStreamReader(p.getInputStream()));
    Runnable task = new Runnable() {

        @Override
        public void run() {
            try {
                if(stdInput.ready())
                {
                    stdInput.lines().forEach((l) -> System.out.println(l));
                }
            } catch (IOException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }
        }
    };
    Thread backgroundThread = new Thread(task);
    backgroundThread.setDaemon(true);
    backgroundThread.start();
}

public static void readErrors(Process p)
{
    BufferedReader stdError = new BufferedReader(new InputStreamReader(p.getErrorStream()));
    Runnable task = new Runnable() {

        @Override
        public void run() {
            try {
                if(stdError.ready())
                {
                    stdError.lines().forEach((l) -> System.out.println(l));
                }
            } catch (IOException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }
        }
    };
    Thread backgroundThread = new Thread(task);
    backgroundThread.setDaemon(true);
    backgroundThread.start();
}

应该允许我写打开命令提示符。但是,这对我不起作用。我没有抛出任何异常或状态错误。我根本不知道如何写一个打开的命令提示符。

2 个答案:

答案 0 :(得分:0)

我在您的代码中看到两个问题:

一个问题是使用的命令行:

@Before public void setUp() { initMocks(this); when(classA.doSmt()).thenCallRealMethod(); when(classB.doSmt()).thenCallRealMethod(); classB = new classB(classA); } 这将启动一个新的cmd.exe实例,该实例本身使用cmd.exe /c start python来启动分离的python进程。因此,分离的进程未连接到您的BufferedReader / BufferedWriter。

您的第二个问题是python无法通过stdin执行“ 1 + 1”。 您可以通过使用上下文start创建文件test并在控制台1+1\n上执行文件来简单地进行验证。您将看不到任何输出。

另请参阅piping from stdin to a python code in a bash script

答案 1 :(得分:-1)

在这种情况下,您需要先关闭输入流,然后才能读取python进程的输出流。如果有人知道更好的方法,请告诉我们。

public static void main(String[] args) {
    String cmdString = "python";
    try {
        ProcessBuilder pb = new ProcessBuilder(cmdString);
        Process pr = pb.start();
        try (BufferedReader readerOfProc = new BufferedReader(
                new InputStreamReader(pr.getInputStream()));
                BufferedReader errorsOfProc = new BufferedReader(
                        new InputStreamReader(pr.getErrorStream()))) {

            try (BufferedWriter writerToProc = new BufferedWriter(
                    new OutputStreamWriter(pr.getOutputStream()));) {
                writerToProc.write("myVar=1+1\r\n");
                writerToProc.write("print(myVar)\r\n");
                writerToProc.flush();
            } catch (Exception e) {
                e.printStackTrace();
            }

            String s;
            while ((s = readerOfProc.readLine()) != null) {
                System.out.println("stdout: " + s);
            }
            while ((s = errorsOfProc.readLine()) != null) {
                System.out.println("stdout: " + s);
            }

            System.out.println("exit code: " + pr.waitFor());
        }
    } catch (Exception e) {
        e.printStackTrace();
    }
}

希望这会有所帮助!