【问题标题】:java command execution escapes '|'java命令执行转义'|'
【发布时间】:2021-04-12 18:29:01
【问题描述】:

我有一个执行系统命令的函数:

public String cmd(String s) {
    String out = "";
    try {
        Runtime run = Runtime.getRuntime();
        Process pr = run.exec(s.split(" "));
        pr.waitFor();
        BufferedReader buf = new BufferedReader(new InputStreamReader(pr.getInputStream()));
        String line = "";
        while ((line=buf.readLine())!=null) {
            out+=line+"\n";
        }
    } catch(Exception e) {
        e.printStackTrace();
    }
    return out;
}

命令通过:

cmd("nmap -sL -n 192.168.1.0/24 | awk '/Nmap scan report/{print $NF}'");

预期输出:

192.168.1.0
192.168.1.1
 ...

实际输出:

Starting Nmap 7.80 ( https://nmap.org ) at 2021-04-12 20:27 EET
Nmap scan report for 192.168.1.0 ...

【问题讨论】:

    标签: java command-line


    【解决方案1】:

    类似的问题很好地回答了这个问题:

    要执行管道,您必须调用 shell,然后在该 shell 中运行命令。

    Process p = new ProcessBuilder().command("bash", "-c", command).start();
    

    bash 调用一个 shell 来执行你的命令,-c 表示命令是从字符串中读取的。因此,您不必将命令作为数组发送到 ProcessBuilder

    适应你的情况

    String cmd(String command) {
      ProcessBuilder builder = new ProcessBuilder();
      builder.redirectErrorStream(true); // add stdErr to output
    
      Process process = builder.command("bash", "-c", command).start();
        
      StringBuilder processOutput = new StringBuilder(); // add lines easier
      // try-with to auto-close resources
      try (BufferedReader processOutputReader = new BufferedReader(new InputStreamReader(process.getInputStream()));) {
        String readLine;
        while ((readLine = processOutputReader.readLine()) != null) {
          processOutput.append(readLine + System.lineSeparator()); // use system's line-break
        }
    
        process.waitFor();
      }
    
      return processOutput.toString().trim();
    }
    

    然后按预期调用:

    cmd("nmap -sL -n 192.168.1.0/24 | awk '/Nmap scan report/{print $NF}'");
    

    注意:我对它进行了一些改进

    灵感来自: read the output from java exec

    【讨论】:

      【解决方案2】:

      管道由 shell 解释。它执行一个命令,然后将一个命令的输出传递给下一个命令。您可以在 Java 中模拟这一点,启动两个命令,然后将第一个程序的 OutputStream 泵入第二个程序的 InputStream

      或者,如果您不想这样做,您仍然可以调用诸如“sh -c 'command1 | command2”之类的东西

      【讨论】:

      • 您能否展示一个模拟将 cmd1 的输出传递给 cmd2 的示例?谢谢。
      猜你喜欢
      • 2015-05-10
      • 2012-04-17
      • 2017-04-11
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多