4

I need to run an ANT build using the build.xml file that is stored inside the jar file. This jar file is available on the classpath. Is it possible to do it, without exploding the jar file and saving the build.xml to local directory? If so how can I do it.

Update:

The jar file is a ant build project where a build.xml in classpath is run via a java program using ANT libraries. The front end is a web application, which loads this build project jar as a dependency. A user will click a Build App button to run the ANT build. So I need to run the build.xml file in a jar when user clicks Build App.

Code for reading the build.xml file

URL preBuildFileUrl = getClass().getClassLoader().getResource("build.xml");
Project p = new Project();
p.setUserProperty("ant.file", preBuildFileUrl.toURI().getPath());
p.init();
ProjectHelper helper = ProjectHelper.getProjectHelper();
p.addReference("ant.projectHelper", helper);
helper.parse(p, new File(preBuildFileUrl.toURI().getPath()));
p.executeTarget(p.getDefaultTarget());
Dhanush Gopinath
  • 5,652
  • 6
  • 37
  • 68
  • Can you provide more information about what you are trying to do? ANT usually works on the filesystem, compiles sources from it and creates artifacts in it, so most liekly you'll end up using the filesystem. Why do you not want to extract the build.xml file? – A4L May 07 '14 at 10:52
  • You could read the file, store it in a temporary location, run ant, and delete the temp file. – atoMerz May 07 '14 at 11:08
  • Yea, I could do that. But was just thinking if I can read it like this. – Dhanush Gopinath May 07 '14 at 11:10
  • This SO link might be useful. http://stackoverflow.com/questions/6733684/run-ant-from-java. The build.xml can be found using `getResource()`. – Priyesh May 07 '14 at 11:17
  • @DhanushGopinath I dont know the java ANT API, but if there is method which takes the ANT file content as `InputStream ` then you could use `ClassLoader#getResourceAsStream` and pass that stream to it. But again, ANT will work on the FS the build the application. Note that you could use this method to extract the `build.xml` file without having to unpack the whole jar. [Here you can find a code snipet for extracting a resource from a jar file](http://stackoverflow.com/a/17745868/1113392) – A4L May 07 '14 at 11:29
  • @A4L In fact I am just doing the same. Only thing is I am trying to load the file from the jar. Check the code snippet attached. If ANT can only build from the FS, then I will go with your idea of extracting the build.xml file. – Dhanush Gopinath May 07 '14 at 11:39

2 Answers2

4

I think it's not possible. The API for the ProjectHelper#parse method suggests that it is possible for a Project helper to support any kind of sources including InputStream

source - The source for XML configuration. A helper must support at least File, for backward compatibility. Helpers may support URL, InputStream, etc or specialized types.

running a modifiyed sample of you code

String buildXml = "build.xml";
Project p = new Project();
p.setUserProperty("ant.file", buildXml);
p.init();
ProjectHelper helper = ProjectHelper.getProjectHelper();
p.addReference("ant.projectHelper", helper);
InputStream inputStream = new FileInputStream(buildXml);
helper.parse(p, inputStream);
p.executeTarget(p.getDefaultTarget());

gives the following Exception:

Exception in thread "main" 
Source java.io.FileInputStream not supported by this plugin
at org.apache.tools.ant.helper.ProjectHelper2.parse(ProjectHelper2.java:233)
at org.apache.tools.ant.helper.ProjectHelper2.parse(ProjectHelper2.java:177)
at ant.test.App.main(App.java:28)

Unfortunatly after looking into the source code of the latest apache ant version (1.9.4 at posting time) the Built-In ProjectHelper implementation does only support

  • java.io.File
  • java.net.URL
  • org.apache.tools.ant.types.Resource

even though an InputStream is created a few lines later :/

The apache ant manual suggests that it is possible to implemt an own ProjectHelper and configure ant to use it using the system property org.apache.tools.ant.ProjectHelper.

The class org.apache.tools.ant.ProjectHelper is the API expected to be implemented. So write your own ProjectHelper by extending that abstract class.

But all the methods that need to be implemented seem to work only with java.io.File or java.net.URL.

So I think your best bet is to extrat the build.xml from the jar (as shown in my comment) and run ant against it.

A4L
  • 17,353
  • 6
  • 49
  • 70
0

It is possible by using the Java URL syntax for jars. If you obtained your build.xml with getResource() the URL external form looks like this:

file:///some/local/path/to/my.jar!/path/inside/jar/to/build.xml

So calling with the URL should be fine:

helper.parse(p, preBuildFileUrl);
Christian
  • 13,285
  • 2
  • 32
  • 49