VisualVM 中的 OQL - 从包中递归打印静态数据

OQL in VisualVM - recursively print static data from a package

我想构建 an OQL query 以递归打印来自 类 的 JVM 堆转储的所有 static 数据包裹。我知道递归遍历内存引用可能存在很多问题,但(至少在最初)我会通过设置深度阈值来缓解这些问题。

根据文档,类 有一个 statics 字段,而该字段 应该 namevalues:

statics - name, value pairs for static fields of the Class.

我已经停止使用 field.name 表达式获取每个静态字段的名称,并且不知道如何迭代对象的非静态字段。我目前有:

select map(
    filter(
        filter(heap.classes(), "/com.heap./.test(it.name)"),
        function (clazz) {
            if (clazz.statics) {
                return true;
            }
            return false;
        }
    ), function (clazz) {
        var res = '';
        res += toHtml(clazz.name) + " : " + toHtml(clazz.statics) + "<br>";
        map(clazz.statics, function (field) {
            res += "--" + toHtml(field) + "," + toHtml(field.name) + "," + toHtml(field.state) +"<br>";
        });
        return res + "<br>";
    }
)

并得到以下输出:

com.heap.dump.DataHolder : { :sun.misc.Launcher$AppClassLoader#1, }
--sun.misc.Launcher$AppClassLoader#1,null,null

com.heap.dump.HeapDumperTest : { dataHolder:com.heap.dump.DataHolder#1, mutableStaticState:java.lang.String#225, :sun.misc.Launcher$AppClassLoader#1, }
--com.heap.dump.DataHolder#1,null,java.lang.String#224
--java.lang.String#225,null,null
--sun.misc.Launcher$AppClassLoader#1,null,null

com.heap.dump.Main : { :sun.misc.Launcher$AppClassLoader#1, }
--sun.misc.Launcher$AppClassLoader#1,null,null

我在 .

之后使用 map() 函数迭代 clazz.statics

看起来 field 参数只是字段的值,因为 field.name 总是 null 并且 field.state 实际上检索对象之一的字段( com.heap.dump.DataHolder.state).

主要问题:

其他问题:

statics是一个映射,所以你应该使用for(..)来迭代它。我更新了您的查询。见下文:

select map(
    filter(
        filter(heap.classes(), "/com.heap./.test(it.name)"),
        function (clazz) {
            if (clazz.statics) {
                return true;
            }
            return false;
        }
    ), function (clazz) {
        var res = '';
        res += toHtml(clazz.name) + " :<br>";
        for (field in clazz.statics) {
            res += "-- " + toHtml(field) + ", " + toHtml(clazz.statics[field]) +"<br>";
        }
        return res + "<br>";
    }
)