gpt4 book ai didi

java - 一旦应用程序的其余部分运行,类是否会在主加载期间再次加载一次

转载 作者:太空宇宙 更新时间:2023-11-04 13:13:39 24 4
gpt4 key购买 nike

我正在尝试在服务器完成启动之前对其某些类进行检测,因为我需要监视它的一些 Activity 。在这种情况下,我使用带有 premain 方法的 javaagent。该代理加载任何所需的类,并使用 Instrumentation 接口(interface)的 retransformClasses 来检测它们。

我 100% 确定我尝试检测的类在服务器中运行,因为我之前通过迭代服务器加载的所有类来检测相同的类。由于这会增加服务器启动时的开销,因此我一直在尝试使用上述方法。当我在应用程序服务器之外运行时,它工作得很好。但是,当我尝试在服务器上运行它时,检测部分会毫无异常地执行或检测所需的类和方法。但是当应用程序在服务器上启动时,我没有从检测方法中获得任何输出。

(例如,假设我正在尝试检测 org.h2.jdbc.JdbcPreparedStatement 类的 executeQuery 方法。我必须将 h2 jar 添加到类路径中)

下面的代码段描述了 premain 方法,该方法用于使用 retransformClass 方法加载每个类:

for (InstrumentationClass instrumentationClass : instrumentationClasses){
Class currentClass = ClassLoader.getSystemClassLoader()
.loadClass(instrumentationClass.getClassName());
SchemaClass currentClassWithDetails = new SchemaClass(
scenario.getScenarioName(), currentClass, instrumentationClass);
InstrumentationClassTransformer.transformMe.add(currentClassWithDetails);
instrumentation.retransformClasses(currentClass);
InstrumentationClassTransformer.transformMe.remove(currentClassWithDetails);
}

当服务器的其余部分启动时,它是否可能加载同一类的不同副本?有办法克服这个问题吗?

最佳答案

应用程序服务器通常使用子优先类加载器将应用程序与应用程序服务器的代码隔离。这样,可以简单地删除应用程序服务器的类加载器,以便在不重新启动 JVM 的情况下取消部署应用程序。

Java 代理通过系统ClassLoader 访问类,该系统保留对服务器应用程序类的引用。因此,对于不同的类加载器(系统和应用程序类加载器),org.h2.jdbc.JdbcPreparedStatement 可能存在两次,其中您只检测部署的应用程序中未使用的类加载器。

但是我确实想知道你的方法有何意义。为什么不能只安装一个 ClassFileTransformer 并在加载类后检查名称是否为 org/h2/jdbc/JdbcPreparedStatement 并进行检测。开销不应该太大。这样,您就可以为任何类加载器检测该类,并且还可以在重新部署时重新检测类。

关于java - 一旦应用程序的其余部分运行,类是否会在主加载期间再次加载一次,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/33729823/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com