JAR Hell

It seems like some of the problems that plagued the windows environment have followed into the Java world, im talking about JAR hell. If one has worked in the windows environment, they would be familiar with the DLL hell problem.

What is DLL Hell?

Unlike Hell, DLL Hell is reserved for Microsoft software users, bad ones and good ones. DLL Hell is what happens, when your computer or software stops operating because you’ve tried to install some new software, so the old software stops working or the new software fails to work.

I see a similar problem happening with jars in java. With the amount of open source components(jars) being created and distributed the problem is bound to affect everyone. The problem only worsens when you have software supporting multiple solutions to a similar problem. For instance, a software supporting both castor & hibernate. Im not even going down the Class Loading lane!

What is Jar Hell?

JAR-hell occurs when software is deployed into a runtime environment which is unsuitable, but nothing other than full integration testing would detect this. Having multiple software packages dependent upon the same piece of software, with unpredictable incompatibilities, is pure hell. Ensuring the compatibility of a variety of dependent packages is duanting, doing it amongst the variety supported by a hierarchy of complex class loaders, is inhuman. Jar Hell also occurs when you try to build/compile software that is dependent on other components.

Im not saying component development is bad, Im just saying that there needs to be a solution to this problem. A side effect to component development is having programmers who just understand syntax and have no clue about concepts! Im digressing! Anyways, unless one has been extremely careful with the components that they have been downloading and using, they are bound to find multiple copies of the same jars files floating around (Apache Commons is fine example) and they problem is going to alleiviate with multiple versions. A good test to see if you have unknowingly have the problem, trying search your hard drive for the ant installation to see how many associated jars you have.

 A classic example that I know off is Roller, the number of jars file on the client(web app) side is 50 and on the server side is 72!  Its only a matter of time before one realises that the number of classes in your application are going to be less than the jars that you would need to include! Heck, thats true if you write a hello world struts application! (9 jars  & 6 classes including one JSP)

Im beginning to wonder, if creating a Package distribution of jar is good idea? But then linux has about 100+ distributions. A quick peek @ JSR’s does not reveal any requests for component deployment. I did however find one for Application deployment, which caters to J2EE server deployment. One solution that I can think of is as follows

Have a file like Manifest file that describes the dependencies(list of jars and versions) and the compiler/Class loader checks against this file or one could atleast have an Ant task that does the verification before it compiles the sources. It would be even cooler if this architecture was extensible so that someone can write a component which allow the jar file to be downloaded if it cannot be found 😉

What do you think?

I did find a project that is trying to address the problem with class loaders http://www.krysalis.org/version/ . Are there other solutions or works in progress around? Is the community already addressing this problem?

Advertisements

7 thoughts on “JAR Hell”

  1. I’ve been feeling the same way lately. Worse yet is where to put all the JARs on my development machine. On the one hand I like to keep my projects nice and tidy with the required JARs in a lib folder under the project but on the other hand I don’t like having multiple copies of those files (and most often, different versions of each jar) for each project.

    I have to point out though that MS put a lot of effort into avoiding this problem with .NET and it’s support for versioned assemblies. There’s a great post about it here:

    http://flyingchihuahuas.editthispage.com/stories/storyReader$216

  2. The extensions directory is a major pain in the neck. We recognized that at SAS some years ago when one of the groups decided to go their own way and reuse the same packages. We were installing our jars into the extension directory and suddenly things were no longer working. We came up with a versioning scheme that allows applets to work independantly of each other. If they need jars downloaded, they are downloaded to a versioned cache and the classloader only loads the jars specified in a manifest obtained from the server. We have often though of extending this to the application space, but have yet to do so.

  3. I just attended to a presentation about Continuous Integration at a local JUG meeting and it looks like Apache Foundation Maven is the solution you are asking for. Please take a look and share your impressions with us. 🙂

  4. Hey, 🙂

    I notice that you have some ctg jar files in there…. so nice to see someone except me doing ctg stuff.. Do you like ctg, is it more stable than rmi/iiop?

    email me at my email address below, when you get time. I need to have a jam session with someone using ctg, bcoz for me it is still an unknown.

    On the jar hell, lol, you should look at my workbench, with log4j, xml, ctg, rmi, avalon, xslt, rhino, I got it going on in jar hell.

    later

    TP

  5. Another solution is to use a pluggable architecture like the one I have developed. Each plugin is loaded within its own classloader, but each plugin can use it’s own libraries and the classloader always looks in the plugin classpath first so that plugins can have their own versions of libraries.

    Now, the argument of disk space comes into play.. yes it is possible many plugins have the same version of a library or “compatible” version. If jar files were required to have specific version info, it would be easy enough to bump a jar file that more than one plugin share, into a “shared” classloader that sits as each plugin’s classloader’s parent classloader, and NOT look within the plugin’s classpath for a given library, so that it would be found in the shared parent loader. But like someone else said, this requires jar packagers to make sure they put in version info, which is not the case most of the time.

    Using this type of architecture, you can place “shared” libraries that the core application uses within the applications classpath, then each plugin is loaded and uses its own libraries as needed. Oh, and back to the disk space issue. Space is cheap. What would you rather have, a few extra MB of HD space taken up BUT a working app that always works? OR save a few MB of space but pull your hair out trying to figure out why the app wont work, or why another app no longer works! To me, its an obvious choice, hence why I built the plugin engine and use it.

Leave a Reply

Please log in using one of these methods to post your comment:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s