I don't think you can change the classpath of an already running java program, I tried this
projectA has class A
projectB has class B and Main
None of the projects import each other
public class Main {
public static void main(String[] args) throws Exception {
System.out.println(Main.class.getResource("/"));
System.setProperty("java.class.path", "/Users/kabir/sourcecontrol/jboss-as7/eclipse/projectA/bin/");
System.out.println(Class.forName("B"));
System.out.println("Test");
Class.forName("A1");
}
}
This shows this output:
file:/Users/kabir/sourcecontrol/jboss-as7/eclipse/projectB/bin/
class B
Test
Exception in thread "main" java.lang.ClassNotFoundException: A1
at java.net.URLClassLoader$1.run(URLClassLoader.java:202)
at java.security.AccessController.doPrivileged(Native Method)
at java.net.URLClassLoader.findClass(URLClassLoader.java:190)
at java.lang.ClassLoader.loadClass(ClassLoader.java:307)
at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:301)
at java.lang.ClassLoader.loadClass(ClassLoader.java:248)
at java.lang.Class.forName0(Native Method)
at java.lang.Class.forName(Class.java:169)
at Main.main(Main.java:37)
So the write to java.class.path has no effect, the system classloader probably only reads that once on startup.
If we want to only have one test project for this and control the app classpath I see the following options:
1) Have the test runner start another process with the minimal classpath and modules, I guess this would be something similar to what ant/maven does when running forked tests
2) jboss-modules makes it possible to configure the default ModuleLoader so we can do something more clever there such as specifying which packages should never be loaded from the system classpath even if they exit in both system and modules.
I prefer 2) which is needed for the flat embedded case anyway, but daren't start changing that on a whim :-) I can play with 1) for now and see if that gets me anywhere