Java getRuntime Exec

时间:2015-03-03 18:24:54

标签: java exec runtime.exec

在Java 1.8上调用p = Runtime.getRuntime()。exec(command)。 该命令调用bash脚本,如下所示:

#!/bin/bash
args=("$@")
cat /home/user/Downloads/bigtext.txt | grep ${args[0]}

使用命令行调用时,上面的bash脚本工作正常。使用exec()在我的Java应用程序中调用时,我没有收到CAT输出。它似乎没有通过p.waitFor();我哪里错了?

如果我直接运行命令,例如" ls -alF"每件事都按预期工作。

$ java -version java version "1.8.0_31" Java(TM) SE Runtime Environment (build 1.8.0_31-b13) Java HotSpot(TM) 64-Bit Server VM (build 25.31-b07, mixed mode)


String tmp = "/home/user/search "+input;        
System.out.println(tmp); //  /home/user/search sometextarg
String woa = executeCommand(tmp);


private String executeCommand(String command) {     
        StringBuilder output = new StringBuilder();
                BufferedReader reader = null;
        Process p;
        try {
            p = Runtime.getRuntime().exec(command);
            p.waitFor();

                        reader = new BufferedReader(new InputStreamReader(p.getInputStream()));

            String line = "";

            while ((line = reader.readLine())!= null) {
                output.append(line + "\n");
            }

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

        return output.toString();
    }

1 个答案:

答案 0 :(得分:3)

你的Java进程和你的脚本在彼此等待死锁:你正在等待进程退出,进程正在等待你读取输出。

它恰好适用于ls -alF和其他具有小输出的命令,因为它们都适合管道缓冲区(我系统上的64kib)。

只需移动while循环下面的p.waitFor(),您就会有更多的运气:

private String executeCommand(String command) {     
    StringBuilder output = new StringBuilder();
            BufferedReader reader = null;
    Process p;
    try {
        p = Runtime.getRuntime().exec(command);
        reader = new BufferedReader(new InputStreamReader(p.getInputStream()));

        String line = "";
        while ((line = reader.readLine())!= null) {
            output.append(line + "\n");
        }
        p.waitFor();

    } catch (Exception e) {
        e.printStackTrace();
    }
    return output.toString();
}

如果您还希望使用包含空格和某些其他字符的值正常工作,则必须:

  1. 在您的脚本中引用"${args[0]}"
  2. 重写您的executeCommand以使用Runtime.exec(String[])代替Runtime.exec(String)