- iOS/Objective-C 元类和类别
- objective-c - -1001 错误,当 NSURLSession 通过 httpproxy 和/etc/hosts
- java - 使用网络类获取 url 地址
- ios - 推送通知中不播放声音
眼前的情况并不像标题所暗示的那么简单。
通过 JWS 运行的 Java 1.6_17。
我有一个类,比方说 MyClass
,它的一个实例成员变量是来自错误的第三方库的类型,在类初始化期间,它动态地尝试使用 加载它自己的一些类>Class.forName(字符串)
。在其中一种情况下,它恰好动态调用:Class.forName("foo/Bar")
。这个类名不遵循二进制名称的 JLS,最终导致 java .lang.NoClassDefFoundError: foo/Bar
.
我们有一个自定义的 ClassLoader
,我已将清理方法添加到 ClassLoader.findClass(String)
和 ClassLoader.loadClass(String)
这解决了这个问题。
我可以这样调用:myCustomClassLoader.findClass("foo/Bar")
然后加载类没有任何问题。但是即使我提前加载了类,我仍然会在以后得到异常。这是因为在引用 Bar
的 MyClass
初始化期间 - 他们的 代码最终调用 Class.forName("foo/Bar")
在某处的静态 block 中。如果它尝试使用的 ClassLoader 是我的自定义类加载器,这实际上是可以的。但事实并非如此。 com.sun.jnlp.JNLPClassLoader
不执行此类清理,因此是我的问题。
我已确保将 Thread.currentThread().getContextClassLoader()
设置为我的自定义类加载器。但这(如您所知)没有效果。由于我阅读了一些内容,我什至将它设置为我在 main()
中做的第一件事,MyClass.class.getClassLoader()
- 是 JNLPClassLoader。如果我可以强制它不是 JNLPClassLoader 而是使用我的,问题就解决了。
如何通过在类初始化期间进行的静态 Class.forName("foo/Bar") 调用来控制使用哪个 ClassLoader 来加载类?我相信如果我可以强制 MyClass.class.getClassLoader()
返回我的自定义类加载器,我的问题就会得到解决。
如果有人有想法,我愿意接受其他选择。
TL;DR: 帮我强制所有 MyClass
引用的第三方库中的 Class.forName(String)
调用 - 使用我选择的类加载器.
最佳答案
这让我想起了10年前读过的一篇关于Java类加载安排的文章。它还在那里on JavaWorld .
本文不会直接回答您的问题,但可能有助于理解您的问题。您需要使 MyClass
通过您的自定义类加载器加载并胜过默认的类加载行为,即首先将类加载委托(delegate)给父类加载器,并且仅在失败时才尝试加载类。
允许 MyClass
由您以外的类加载器加载将存储从实例化类到该类加载器的关系(通过 getClassLoader
)并导致 Java 使用其他类加载器类加载器尝试发现任何引用的类 found at compile time ,凭借类加载器层次结构和委托(delegate)模型有效地绕过您的自定义类加载器。如果 MyClass
由您的类加载器定义,您将获得第二次机会。
这听起来像是 URLClassLoader
之类的工作,覆盖 loadClass
并胜过驻留在您的 JAR 中的类的委托(delegate)模型。您可能希望使用 Bootstrap 方法(如 Thomas 在上面的评论中所建议的那样)强制通过您的自定义类加载器加载单个入口点类,同时拖动所有其他入口点类。
同样提供信息的是 this other JavaWorld article由同一个人发出警告,警告您有关 Class.forName 的注意事项。这也可能会影响您的类加载安排。
我希望这会有所帮助并提供信息。无论如何,这听起来像是一个困难的解决方案,随着代码的发展很容易被破坏。
关于java - 如何控制哪个 ClassLoader 加载类?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13925224/
我只是想知道如果我知道类加载器,我是否可以在 JVM 运行时获取类的实例(对对象的引用)。请引用下面的代码来理解我的问题。 A类: package local.run; public class A
我们正在尝试调试 WebStart 的一个不可重现的问题,即访问 Jars 内的资源将“随机”失败。也许每 1000 个应用程序运行中就有一个会出现此错误,这种错误可能发生在从 jar 读取资源的任何
在从属实例(AIX 5.3 上的主服务器;Windows 2008(R2) 上的从属服务器)上运行 Maven2 作业时,我收到以下消息(下面粘贴了完整的堆栈跟踪):“java.lang.ClassN
我正在编写一个游戏引擎,我需要在其中分析程序中提到的每个类。由于这是一个游戏引擎,因此它将作为 JAR 文件附加到客户的项目中。从该 JAR 文件中,我需要能够扫描客户端正在使用的每个类。 所以我想我
Java安全之BCEL ClassLoader 写在前面 BCEL平常在测试反序列化的时候也经常会用到,比如延时测Gadget以及在某些场景下执行命令不是那么顺手的情况下选择BCEL去打内存马,就像F
比如说,我有一个 A 类,由 ClassLoader CL1 加载。 我有另一个 B 类,由 ClassLoader CL2 加载。 假设这两个类现在都由各自的类加载器加载。 如果我从 A 执行以下语
在 org.dozer.BeanFactory.createBean(Object, Class, String) 的实现中我尝试将对象转换为它的类型。如果我部署所有 bundle ,即关闭并启动所有
它过去曾经可以工作,但是我中间没有发生什么,现在它总是返回null。 要读取的文件在项目root diretory中,该项目与Paths.get(".")的输出相对应。 注意:功能是顶级的 我正在读取
在 org.dozer.BeanFactory.createBean(Object, Class, String) 的实现中我尝试将对象转换为它的类型。如果我部署我所有的包,即关闭并启动所有包,我得到
我必须使用第 3 方平台,但该平台具有无法替换的较旧版本的 jar libjar-1.0.0.jar。该平台允许我在其上运行我自己的(平面文件)包。我将新版本的 libjar-2.0.0.jar 放在
我正在尝试使用下面的类加载器在我的 Maven 插件中加载特定的类: public ClassLoader getClassLoader(MavenProject project) { tr
以下场景: CustomClassLoaderA 加载 ClassA CustomClassLoaderB 加载 ClassB 到目前为止一切顺利,但是: CustomClassLoaderA 应该能
我试图强制使用我的自定义类加载器加载某些类,问题是在加载调用类之后仍然不知道类定义并尝试再次加载它,当然之后我们对该类有两种不同的定义,并将一种定义分配给另一种会导致类转换异常。有什么建议或想法可以解
我在尝试指示 Java 类加载器在部署后从 test/resources 目录中检索 JSON 文件时遇到了问题。 public class TestFileUtil { private st
我似乎在为我正在开发的应用程序的模块加载器中加载类时遇到问题。基本上,我将用它加载的所有类都扩展了另一个类,该类位于实际应用程序的包中。出于我们的目的,我们将其称为模块。模块位于实际应用程序之外的单独
关闭。这个问题需要details or clarity .它目前不接受答案。 想改进这个问题吗? 通过 editing this post 添加细节并澄清问题. 关闭 8 年前。 Improve t
我正在使用 URLClassLoader 创建一个新的类加载器,并尝试将其设置为当前线程的类加载器。但它对我来说不能正常工作。按照我的理解,如果我给当前线程设置一个classLoader,那么当前线程
昨天我想到了一个问题,下面是细节: 我有 3 个 JAR 文件,a.jar、b.jar、c.jar。这两个 jars 文件都有一个名为 com.test.Test 的类,并且 sayHello() 是
我想创建一个新的 ClassLoader 实例,它在开始时绝对不包含任何类。它不应该有一个可用的类。甚至没有 java.lang 类。我希望能够为我自己的位置手动加载每个类。 (使用覆盖的 defin
我正在开发一个个人用药时间提醒应用程序。除了在通知几次用药时间后停止之外,它几乎可以正常工作。在监视应用程序的日志猫时,我发现它在收到以下警告后正在停止警报接收器。 W/System: ClassLo
我是一名优秀的程序员,十分优秀!