从JAR文件加载类及其数据是否完全无效?

时间:2018-04-10 15:26:52

标签: java reflection classloader

我真的不知道如何设置我的问题标题,因为它具体而且完全描述它会占用太多空间。

以下是我尝试做的事情:

我开发了一个应用程序,其中一部分允许其他人为它编写自己的插件。为了做到这一点,他们需要下载我的库,并将他们的插件类扩展到我的库中的一个抽象类:SimplePluginAdvancedPlugin。我还有一个名为Plugin的接口,两个类都实现了。为了在运行时动态加载插件,我设置了ClassLoader来搜索Plugin接口,因为它梳理了.class文件。我没有遇到任何问题,而且我已经能够毫无问题地创建插件了。

我遇到的问题是我决定让我的应用程序能够告诉插件正在使用的库的 build ,以便我可以防止如果使用旧版本,则加载插件。所以,在我的Plugin界面中,我有一个变量集来确定这个:

public interface Plugin {

    public static String PluginLibrary_BUILD = "0.1.1";

    //methods...
}

这是另外两个用于视觉参考的类:

public abstract class SimplePlugin implements Plugin { 

    //methods...
}

public abstract class AdvancedPlugin extends SimplePlugin implements Plugin {

    //methods...
}

但是每次我加载一个新的插件并尝试读取构建变量时,它总是会在我的项目中的Plugin类中包含值,而不是(我假设应该是这样),我通过导出插件生成的 JAR文件中的值。

以下是一个例子:

//import dependencies from my library

public class TestPlugin extends SimplePlugin {

    public TestPlugin() {
        super("TestPlugin", "v1.0");
    }

    @Override
    public void doOnAction() {
        System.out.println("Hello World!");
    }

}

因此,从这里开始,我将TestPlugin类导出为JAR文件,它将从我的库中导出依赖项。然后,我将JAR文件拖到我已设置的文件夹中,然后我的应用程序将其作为插件读取并执行其操作。不幸的是,"它的东西"涉及从我的项目文件而不是JAR文件中读取我的PluginLibrary_BUILD变量(可能?)因为如果我在项目文件中更改它,插件会告诉我它的构建也发生了变化。

我不确定发生了什么,这只是我最好的猜测,所以我正在寻找一些关于为什么会发生什么事情的见解,以及如何解决问题。如果您想完全按原样查看源文件,我会将其上传herePluginStreamSAKPlugin,两个抽象类位于/ types下,StreamSAKSimplePluginStreamSAKAdvancedPlugin(我只是简化了此问题的名称)。

如果您不想进行文件挖掘,我认为您认为重要的是每个文件:

StreamSAKPlugin

StreamSAKSimplePlugin

StreamSAKAdvancedPlugin

StreamSAKFileHandler(负责加载插件,向下滚动到底部)

2 个答案:

答案 0 :(得分:0)

您是否尝试过使用方法替换成员?使用每个实现覆盖它,Java没有默认的接口实现,所以也许你需要强制插件创建者扩展你的一些抽象类,而不仅仅是实现接口。

答案 1 :(得分:0)

所以我非常确定我对发生了什么有很好的了解,为什么不管我做了什么,我都无法达到我想要的效果。当我加载插件时,我不得不将它们转换为我的当前库构建所包含的类。因此,无论插件可能带有什么数据,都会被演员覆盖。

为了解决这个问题,我稍微改进了我的代码和文件结构。现在,我的库包含一个引用其内部版本号的文件。这样,当我的程序启动时,它可以从该文件中读取内部版本号,然后在使用该库作为资源的任何程序中从该文件中读取内部版本号。