Chris Nokleberg's Fizzy Weblog
After a few years of development I think Jar Jar Links is in the home stretch, up to version 1.0rc3 now.
Part of the problem was deciding how to handle manifest files in merged jars. Thankfully while I sat and did nothing the Ant team added a "filesetmanifest" attribute to the Jar task which for now should handle most needs (re-signing jars is a still a known issue).
Maven support also came up from time to time, so eventually I broke down and added a plugin. It is pretty simple but has almost all the features of the Ant task. Look for the "plugin" jar on the download page. I'm not sure if anyone has used this yet so feedback would be appreciated.
Finally, in the 11th hour I've added a new feature. Previously you could exclude certain classes from the resulting jar file using the "zap" rule. However, this was a course-grained and somewhat error-prone approach to shrinking your jar file. On some projects of mine I've avoided the use of "zap" and instead followed jarjar with ProGuard. While this can work well it is a heavyweight solution and configuring ProGuard can sometimes be a pain.
The solution is a new "keep" rule. You can have multiple keep rules and they each take a wildcard pattern which defines which classes must be retained in the final jar (the roots of the dependency tree). It then transitively computes all the dependencies and throws everything else away. Because jarjar already had a lot of dependency checking code built-in it was a relatively minor feature to add. Unlike ProGuard this only works on the class level, but for a lot of jarjar uses there will still be significant savings. For example, in the new Guice project adding a single
<keep pattern="com.google.**"/> rule reduced the jar size from 500K to 376K.
To give credit where it is due, this feature was partly inspired by Torsten Curdt's minijar project (which in turn has a repackaging feature which seems to have been inspired by jarjar?). I guess jarjar and minijar are pretty similar now, except for license differences and that minijar is Maven-specific. The more the merrier