Executing untokenized command line from Java

前端 未结 2 773
长情又很酷
长情又很酷 2021-01-24 18:37

I am currently using ProcessBuilder to run commands from a java server. This server is to replace an old Perl server, and a lot of our legacy code specifies platform specific c

相关标签:
2条回答
  • 2021-01-24 18:59

    I think the quotes are being interpreted by the shell. Instead, put the command in a shell script:

    $ cat temp.sh 
    #!/bin/sh
    perl -e "print 5"
    

    and execute it:

    import java.io.BufferedReader;
    import java.io.InputStreamReader;
    
    public class PBTest {
    
        public static void main(String[] args) {
            ProcessBuilder pb = new ProcessBuilder("./temp.sh");
            pb.redirectErrorStream(true);
            try {
                Process p = pb.start();
                String s;
                BufferedReader stdout = new BufferedReader (
                    new InputStreamReader(p.getInputStream()));
                while ((s = stdout.readLine()) != null) {
                    System.out.println(s);
                }
                System.out.println("Exit value: " + p.waitFor());
                p.getInputStream().close();
                p.getOutputStream().close();
                p.getErrorStream().close();
             } catch (Exception ex) {
                ex.printStackTrace();
            }
        }
    }
    

    Console:

    5
    Exit value: 0
    
    0 讨论(0)
  • 2021-01-24 19:04

    Are you able to use the overloaded Runtime.exec(String) that takes a single String and runs that as the entire command?


    The following works for me on Windows:

    Process p = Runtime.getRuntime().exec("perl -e \"print 5\"");
    System.out.println(IOUtils.toString(p.getInputStream()));
    p.destroy();
    

    This is more or less what Runtime.exec(String) is doing:

    public static void main(String [] args) throws Exception {
        Process p = new ProcessBuilder(getCommand("perl -e \"print 5\"")).start();
        System.out.println(IOUtils.toString(p.getInputStream()));
        p.destroy();
    
    }
    
    private static String[] getCommand(String input) {
        StringTokenizer tokenizer = new StringTokenizer(input);
        String[] result = new String[tokenizer.countTokens()];
        for (int i = 0; tokenizer.hasMoreTokens(); i++) {
            result[i] = tokenizer.nextToken();
        }
        return result;
    }
    
    0 讨论(0)
提交回复
热议问题