在tomcat中,我通过使用类加载器加载HelloWorld。
sb.append("package XXXX.XXXXX.XXXX.freemarkerjob;\n");
sb.append("import XXXX.XXXXX.XXXX.freemarkerjob.DoStuff;\n");
sb.append("public class HelloWorld implements DoStuff {\n");
sb.append(" public void doStuff() {\n");
sb.append(" System.out.println(\"Hello world\");\n");
sb.append(" }\n");
sb.append("}\n");
Class<?> helloClass = InMemoryJavaCompiler.compile("XXXX.XXXXX.XXXX.HelloWorld", sb.toString(), optionList);
我发现如果我使用Thread.currentThread()。getContextClassLoader()作为DynamicClassLoader的父级,那么我可以成功加载该类,但是如果我使用(ClassLoader.getSystemClassLoader(),则抛出classnotfoundexception)当调用方法cl.loadClass(className);,它无法加载HelloWorld实现它的接口DoStuff。 我需要知道为什么SystemClassLoader无法加载接口?
DynamicClassLoader cl = new DynamicClassLoader(Thread.currentThread().getContextClassLoader());
DynamicClassLoader cl = new DynamicClassLoader(ClassLoader.getSystemClassLoader());
Class<?> helloClass = InMemoryJavaCompiler.compile("XXXX.XXXXX.XXXX.HelloWorld", sb.toString(), optionList);
public static Class<?> compile(String className, String sourceCodeInText, Iterable<String> options) throws Exception {
This one successfully
DynamicClassLoader cl = new DynamicClassLoader(Thread.currentThread().getContextClassLoader());
This one failed
// DynamicClassLoader cl = new DynamicClassLoader(ClassLoader.getSystemClassLoader());
cl.loadClass(className);
}
package XXXX.XXXXX.XXXX.dynamicjava;
import java.util.HashMap;
import java.util.Map;
public class DynamicClassLoader extends ClassLoader {
private Map<String, CompiledCode> customCompiledCode = new HashMap<>();
public DynamicClassLoader(ClassLoader parent) {
super(parent);
}
public void setCode(CompiledCode cc) {
customCompiledCode.put(cc.getName(), cc);
}
@Override
protected Class<?> findClass(String name) throws ClassNotFoundException {
CompiledCode cc = customCompiledCode.get(name);
if (cc == null) {
Class<?> curClass = super.findClass(name);
if (curClass == null) {
return null;
} else {
return curClass;
}
}
byte[] byteCode = cc.getByteCode();
return defineClass(name, byteCode, 0, byteCode.length);
}
}
答案 0 :(得分:0)
您的界面(DoStuff)未由SystemClassLoader加载,通常由应用程序类加载器加载。
如果您想在DoStuff的上下文中使用HelloWorld,请使用以下内容,
DynamicClassLoader cl = new DynamicClassLoader(DoStuff.class.getClassLoader());