33

How to write an ant task that removes files from a previously compiled JAR?

Let's say the files in my JAR are:

aaa/bbb/ccc/Class1
aaa/bbb/ccc/Class2
aaa/bbb/def/Class3
aaa/bbb/def/Class4

... and I want a version of this JAR file without the aaa.bbb.def package, and I need to strip it out using ant, such that I end up with a JAR that contains:

aaa/bbb/ccc/Class1
aaa/bbb/ccc/Class2

Thanks!

bguiz
  • 27,371
  • 47
  • 154
  • 243

6 Answers6

62

Have you tried using the zipfileset task?

<jar destfile="stripped.jar">
  <zipfileset src="full.jar" excludes="files/to/exclude/**/*.file" />
</jar>

Example

<property name="library.dir" value="dist" />
<property name="library.file" value="YourJavaArchive.jar" />
<property name="library.path" value="${library.dir}/${library.file}" />
<property name="library.path.new" value="${library.dir}/new-${library.file}" />

<target name="purge-superfluous">
  <echo>Removing superfluous files from Java archive.</echo>

  <jar destfile="${library.path.new}">
    <zipfileset src="${library.path}" excludes="**/ComicSans.ttf" />
  </jar>

  <delete file="${library.path}" />
  <move file="${library.path.new}" tofile="${library.path}" />
</target>
Mr. Polywhirl
  • 42,981
  • 12
  • 84
  • 132
mipadi
  • 398,885
  • 90
  • 523
  • 479
  • @mipadi Thanks for your answer! I was hoping that there was a method without an intermediate stage - that is directly removing files/ folders from the Jar. Failing which I guess this is the closest I'll get to it! – bguiz Mar 26 '10 at 10:39
  • Just a FYI, probably most know this, but I didn't think of it :-). The "jar" task will modify the MANIFEST.MF of the JAR, which in my case caused problems. I just added the "manifest" attribute to the jar task and pointed it at the manifest I wanted it to use. Great answer though, definitely helped me out, thanks! – Craig Aug 13 '13 at 15:38
  • 1
    Could also use `zip` instead of `jar` to avoid changing MANIFEST.MF – npostavs Aug 27 '15 at 17:26
5

You have to unjar and rejar.

<unzip src="myjar.jar" dest="/classes/">
<jar destfile="newjar.jar"
    basedir="/classes/"
    includes="**/*"
    excludes="**/def/*"
/>    
David
  • 7,011
  • 1
  • 42
  • 38
2

The answers didn't quite add up for me -

<zip destfile="tmp.jar">
  <zipfileset src="src.jar">
    <exclude name="**/*.class" />
  </zipfileset>
</zip>
<move file="tmp.jar" tofile="src.jar" />

This uses a single pass and doesn't add too much time to the build

Source: http://ant.1045680.n5.nabble.com/Remove-entru-from-ZIP-file-using-ANT-td1353728.html

Mr. Polywhirl
  • 42,981
  • 12
  • 84
  • 132
Marc Magon
  • 713
  • 7
  • 11
1

I came here looking to use ant as a workaround some short comings in Gradle unzip.

On the off chance someone else is in the same boat.

Here is an example:

task antUnzip() << {
  ant.jar(destfile: "stripped.jar") {
    zipfileset(src: "full.jar", excludes: "files/to/exclude/**/*.file") {}
  }
}
Mr. Polywhirl
  • 42,981
  • 12
  • 84
  • 132
Jeremy Bunn
  • 641
  • 6
  • 17
1

If a jar-file capable archiver program, like e.g. "zip" on Linux, is available, the task can be done by

<exec executable="zip">
  <arg value="-d" />
  <arg value="myJarCopyToStrip.jar" />
  <arg value="aaa/bbb/def/*" />
  <arg value="aaa/bbb/def" />
</exec>

Subtree deletion depends on the capabilities of the used archiver.
The "os" attribute of the Ant "exec" task allows to use different archivers on different OS's.

Mr. Polywhirl
  • 42,981
  • 12
  • 84
  • 132
Michael Besteck
  • 2,415
  • 18
  • 10
0

I am not sure if there a direct solution for your requirement. I would recommend to explode the jar to some temp directory and then remove unwanted class files. Finally create a new jar with required class files.

Apache Ant manual references:

Mr. Polywhirl
  • 42,981
  • 12
  • 84
  • 132
navr
  • 72
  • 5