Friday, January 18, 2008

JAR internal classpath

The JAR tutorial notes:
"The Class-Path header points to classes or JAR files on the local network, not JAR files within the JAR file or classes accessible over internet protocols. To load classes in JAR files within a JAR file into the class path, you must write custom code to load those classes."

Here is the code:
public class JarredLauncher {

public static void launch(String className, String[] classPath) throws Throwable {

ClassLoader parent = JarredLauncher.class.getClassLoader();

// Extend the classloader's classpath with the jar subdirs.
URL[] uPath = new URL[classPath.length];
for (int i = 0 ; i != classPath.length ; i++) {
uPath[i] = parent.getResource(classPath[i] + "/");
}
URLClassLoader loader = new URLClassLoader(uPath, parent);



// Locate and run the "main" method.
Class mainClass = loader.loadClass(className);
java.lang.reflect.Method m = mainClass.getMethod("main", new Class[] { String[].class });
m.setAccessible(true);

m.invoke(null, new Object[] {new String[] {}});

}

public static void main(String args[]) throws Throwable {

// Run the class with the class path.
launch("AppMainClassName", new String[] {"dir1", "dir1/subdir", "more CPs"});

}

}


You supply the JAR's main class to the Launcher, which adds the necessary classpathes and transfers control to the app's main method. This Launcher class can be made universal by moving the paths and the app's main class name, which are hard-coded in this launcher demo, to the manifest. But I do not understand why Sun abandons the URL CPs right in the manifest. Perhaps, I take the JARs idea wrong. Report me if understand it better.

No comments: