我有一个应用程序允许人们使用抽象类编写自己的实现。我从目录中将这些实现加载为.class-files。目前,我有这个解决方案:
File classDir = new File("/users/myproject/classes/");
URL[] url = { classDir.toURI().toURL() };
URLClassLoader urlLoader = new URLClassLoader(url);
String filename;
for (File file : classDir.listFiles()) {
filename = string.getFilenameWithoutExtension(file);
if (filename.equals(".") || filename.equals("..") || filename.startsWith("."))
continue;
AbstractClass instance = (AbstractClass)urlLoader
.loadClass("org.mypackage." + filename)
.getConstructor(ConfigUtil.class, DatabaseUtil.class, StringUtil.class)
.newInstance(config, database, string));
instance.doSomething();
}
如您所见 - 我需要指定类所在的包,以便正确加载它们。省略了包裹,我得到了一个
java.lang.NoClassDefFoundError:
MyClass (wrong name: org/mypackage/MyClass)
错误。
现在,从架构POV来看,我认为设计其他人的类必须在加载时编译为MY包。
所以我问你:有没有办法从文件系统加载类而不必指定它们所在的包?
答案 0 :(得分:3)
是;实现接口(或使用注释)。
然后使用任何类扫描库(有很多关于此的SO问题,如this one)来加载有问题的特定类。搜索“Java类扫描”或“Java插件机制”将有所帮助。
您可能只想使用Java Plugin Framework并避免一些努力。虽然我不清楚它是否已经维持,但我知道人们仍在使用它。
答案 1 :(得分:1)
您可以使用ServiceProvider加载您不知道的实现。