You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何获取运行中JVM内java.security.Security的所有属性当前状态

如何获取运行中JVM的Security类实时属性

好问题!我之前也碰到过类似的调试需求——要拿到java.security.Security维护的所有实时属性,但官方确实没有提供直接遍历所有属性的公开API。不过咱们可以通过反射来实现,因为这些属性本质上是存储在类内部的私有集合里的,下面是具体的方案:

核心实现思路

java.security.Security类把所有属性存在一个私有静态集合中(不同JDK版本可能用Map或Hashtable,比如OpenJDK 8+大多是volatile Map<String, String> props)。我们可以通过反射获取这个私有字段,然后遍历其中的键值对,就能拿到所有实时属性了——包括配置文件初始化的,以及通过Security.setProperty()动态修改/添加的。

代码示例

import java.security.Security;
import java.lang.reflect.Field;
import java.util.Map;

public class SecurityPropsDebugger {
    public static void main(String[] args) throws Exception {
        // 定位Security类中的私有静态字段"props"
        Field propsField = Security.class.getDeclaredField("props");
        // 开启字段的访问权限(因为是私有字段)
        propsField.setAccessible(true);
        // 取出字段值,转换为Map类型
        Map<String, String> securityProps = (Map<String, String>) propsField.get(null);
        
        // 遍历并打印所有属性
        System.out.println("当前JVM中Security类的实时属性列表:");
        for (Map.Entry<String, String> entry : securityProps.entrySet()) {
            System.out.printf("属性名:%s,值:%s%n", entry.getKey(), entry.getValue());
        }
    }
}

注意事项

  • JDK版本兼容性:不同厂商(Oracle JDK/OpenJDK)或不同版本的JDK,这个私有字段的名称或类型可能有变化。比如有些早期版本用的是Hashtable而非Map,如果遇到类型转换错误,可以尝试把Map换成Hashtable再试。
  • 模块系统限制(Java 9+):如果你的项目用了Java模块系统,直接运行上面的代码可能会抛出IllegalAccessException。这时候需要在JVM启动参数中添加:
    --add-opens java.base/java.security=ALL-UNNAMED
    
    或者在module-info.java中声明对java.security模块的访问权限。
  • 反射的风险:反射会破坏Java的封装性,而且如果未来JDK内部实现变更,这段代码可能会失效。所以只建议在调试场景下使用,不要放到生产代码里。
  • 替代方案(无反射):如果不想用反射,你可以收集所有已知的安全属性名称(比如从java.security配置文件、官方文档里找),然后逐个调用Security.getProperty()获取值。但这种方法无法覆盖动态添加的新属性,只能拿到已知的属性。

内容的提问来源于stack exchange,提问作者jr10

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.28 06:33:15