Arthas通过classloader
命令将 JVM 中所有的classloader的信息统计出来,并可以展示继承树,urls等。可以让指定的classloader去getResources,打印出所有查找到的resources的url。对于ResourceNotFoundException
比较有用。
Arthas的classloader的查找本质也是通过Instrumentation获取所有的加载的class,然后通过class的getClassLoader方法查找对应的ClassLoader对象。
public class ClassLoaderCommand extends AnnotatedCommand {
private void getAllClasses(String hashCode, Instrumentation inst, RowAffect affect, CommandProcess process) {
int hashCodeInt = -1;
if (hashCode != null) {
hashCodeInt = Integer.valueOf(hashCode, 16);
}
// bootstrapClassSet保存class
SortedSet<Class<?>> bootstrapClassSet = new TreeSet<Class<?>>(new Comparator<Class>() {
@Override
public int compare(Class o1, Class o2) {
return o1.getName().compareTo(o2.getName());
}
});
// 通过inst.getAllLoadedClasses获取所有加载的类
Class[] allLoadedClasses = inst.getAllLoadedClasses();
// classLoaderClassMap保存类加载器和对应的class
Map<ClassLoader, SortedSet<Class<?>>> classLoaderClassMap = new HashMap<ClassLoader, SortedSet<Class<?>>>();
for (Class clazz : allLoadedClasses) {
// 获取类对应的类加载器
ClassLoader classLoader = clazz.getClassLoader();
// Class loaded by BootstrapClassLoader
if (classLoader == null) {
if (hashCode == null) {
bootstrapClassSet.add(clazz);
}
continue;
}
if (hashCode != null && classLoader.hashCode() != hashCodeInt) {
continue;
}
SortedSet<Class<?>> classSet = classLoaderClassMap.get(classLoader);
if (classSet == null) {
classSet = new TreeSet<Class<?>>(new Comparator<Class<?>>() {
@Override
public int compare(Class<?> o1, Class<?> o2) {
return o1.getName().compareTo(o2.getName());
}
});
classLoaderClassMap.put(classLoader, classSet);
}
classSet.add(clazz);
}
}
}
ClassLoaderCommand通过getAllClasses来获取类加载器classloader。
通过Instrumentation.getAllLoadedClasses获取所有的class,通过class.getClassLoader获取对应的类加载器。
public class ClassLoaderVO {
private String name;
private String hash;
private String parent;
private Integer loadedCount;
private Integer numberOfInstances;
private List<ClassLoaderVO> children;
public ClassLoaderVO() {
}
public void addChild(ClassLoaderVO child){
if (this.children == null){
this.children = new ArrayList<ClassLoaderVO>();
}
this.children.add(child);
}
}
构造类加载器的树形结构主要是通过ClassLoaderVO对象,每个类加载器的VO对象包含子节点列表的children。
版权说明 : 本文为转载文章, 版权归原作者所有 版权申明
原文链接 : https://blog.csdn.net/qq_21383435/article/details/123975504
内容来源于网络,如有侵权,请联系作者删除!