Я написал собственный загрузчик классов 'JarClassLoader', который сам по себе работает нормально, так как следующий тестовый пример зеленый:
public void testJarClassLoader() throws Exception
{
JarClassLoader cl = new JarClassLoader();
cl.addURLsByClassPath("lib/a-lot-of-jars.jar|lib/more-jars.jar", "\\|");
Class c = cl.loadClass("com.packagepath.classname");
assertNotNull(c);
System.out.println("Class: "+ c);
}
Но следующий тест не будет работать:
public void testSetThreadClassLoader() throws Exception
{
JarClassLoader cl = new JarClassLoader();
cl.addURLsByClassPath("lib/a-lot-of-jars.jar|lib/more-jars.jar", "\\|");
Thread t = new Thread() {
public void run()
{
TestCase.assertEquals("com.packagepath.JarClassLoader",
Thread.currentThread().getContextClassLoader().getClass().getName());
//this assertion passed
try
{
Class c = Class.forName("com.packagepath.classname");
//it doesn't work, throws ClassNotFoundException
TestCase.assertNotNull(c);
}
catch (ClassNotFoundException e)
{
e.printStackTrace();
}
**com.packagepath.classname.methodname("params");**
//it doesn't work, throws java.lang.ClassNotFoundException
}
};
t.setContextClassLoader(cl);
t.start();
}
обратите внимание на размеченную строку, я хотел использовать потоковый загрузчик классов, когда я буквально вызываю метод.
Я прочитал десятки веб-страниц и документов, и ни один из них не сказал мне точно, должна ли жирная линия работать или нет. Я не могу понять, где что-то пошло не так.
Может ли буквально вызываемый метод использовать classloader для загрузки соответствующего класса? Если нет, то почему не можете? Мне нужно, чтобы это работало, поскольку вызовы в jar-файлах, предоставляемых поставщиками, в буквальном смысле слова не используют отражение или что-либо еще, и мне приходится назначать разные загрузчики классов для разных потоков, чтобы избежать конфликта имен в jar-файлах поставщика.
Кто-нибудь может мне помочь? Спасибо миллион!