如何通过java程序运行ant命令



我想通过java程序运行一个简单的ant-v命令。经过搜索,我知道我必须使用shell execute而不是process,因为ant并不是真正的exe格式。我有一个程序可以执行简单的JAVAC命令,但ant永远不会工作。以下是我的代码。

Runtime runtime = Runtime.getRuntime() ;  
Process shellProcess = runtime.exec("D:\installs\apache-ant-1.9.2\bin\ant -v") ;
shellProcess.waitFor() ;

当我运行这个时,我得到以下异常

Exception in thread "main" java.io.IOException: Cannot run program "D:installsapache-ant-1.9.2binant": CreateProcess error=193, %1 is not a valid Win32 application
at java.lang.ProcessBuilder.start(ProcessBuilder.java:1029)
at java.lang.Runtime.exec(Runtime.java:615)
at java.lang.Runtime.exec(Runtime.java:448)
at java.lang.Runtime.exec(Runtime.java:345)
at com.check.SystemCheck.main(SystemCheck.java:14)
Caused by: java.io.IOException: CreateProcess error=193, %1 is not a valid Win32 application

指定整个路径的原因是,如果我不这样做,我会得到找不到文件的错误。你知道怎么做吗??

许多事情突然向我袭来。

  1. 在windows下,ant命令应为ant.bat
  2. 您应该将命令与参数分开,以便每个参数表示一个单独的String。这大大降低了包含空格的参数的复杂性,例如
  3. 你真的应该使用ProcessBuilder,它会降低使用Process的复杂性

例如。。。

ProcessBuilder pb = new ProcessBuilder(
    "D:\installs\apache-ant-1.9.2\bin\ant.bat", 
    "-v");
pb.redirectError();
// This should point to where your build.xml file is...
pb.directory(new File("C:/"));
try {
    Process p = pb.start();
    InputStream is = p.getInputStream();
    int in = -1;
    while ((in = is.read()) != -1) {
        System.out.print((char) in);
    }
    int exitValue = p.waitFor();
    System.out.println("Exited with " + exitValue);
} catch (Exception ex) {
    ex.printStackTrace();
}

我还应该指出,ant是一个linux/unixshell脚本,Windows不知道该用它做什么;)

更新

我已经用Windows7和Java7测试过了,运行得很好

我已经用Windows7和Java6测试过了,效果很好。。。

如果直接运行ant.bat仍然存在问题,则需要通过命令处理器运行批处理文件

ProcessBuilder pb = new ProcessBuilder(
    "cmd",
    "/c",
    "D:\installs\apache-ant-1.9.2\bin\ant.bat", 
    "-v");
Ant是用Java编写的。为什么不在同一个Java进程中直接调用它的类,而不是启动一个外部进程呢?

这里有一个有趣的答案。

以下是答案上的代码:

File buildFile = new File("build.xml");
Project p = new Project();
p.setUserProperty("ant.file", buildFile.getAbsolutePath());
p.init();
ProjectHelper helper = ProjectHelper.getProjectHelper();
p.addReference("ant.projectHelper", helper);
helper.parse(p, buildFile);
p.executeTarget(p.getDefaultTarget());

它将执行build.xml文件的默认目标。很酷,不是吗?

对我来说,主要的优点是你可以更好地控制执行(例如,你可以很容易地知道某件事是否失败),当然也可以获得脚本将生成的输出。

尝试

ArrayList<String> argList = new ArrayList<String>();
argList.add("-v");
String[] args = argList.toArray(new String[argList.size()]);
Runtime.getRuntime().exec("D:\installs\apache-ant-1.9.2\bin\ant", args);

你也可以做以下

ProcessBuilder pb = new ProcessBuilder("D:\installs\apache-ant-1.9.2\bin\ant -v", "-v");
Process p = pb.start();

除了Aniket的答案之外,为了让事情变得更简单:

Runtime.getRuntime().exec("D:\installs\apache-ant-1.9.2\bin\ant", new String[]{"-v"});

可执行文件的参数必须单独传入:

Runtime.getRuntime().exec("D:\installs\apache-ant-1.9.2\bin\ant", "-v");

在您的尝试中,可执行文件实际上是ant -v(即文件名中有一个空格,以破折号v结尾)。

我会跳过bat文件,直接运行启动器jar

File java = new File(new File(new File(
    System.getProperty("java.home"), "bin"), "java");
File antHome = new File("path to ant installation");
File launcher = new File(new File(antHome, "lib"), "ant-launcher.jar");
ProcessBuilder pb = new ProcessBuilder(
    java.getAbsolutePath(),
    "-jar",
    launcher.getAbsolutePath(),
    "-v");
pb.directory(dirContainingBuildXml);
Process p = pb.start();

但正如其他答案中所建议的那样,直接调用ant的Java API而不是使用外部进程可能会得到更好的结果。如果您在问题中的示例使用-v,我认为您正试图从构建的详细输出中捕获一些内容。如果您通过其API调用ant,您可以在Project上注册一个侦听器,并且ant将直接向侦听器传递日志消息,而不必从流程输出中解析它们。

相关内容

  • 没有找到相关文章

最新更新