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

如何解决Maven Spring项目中的java.lang.reflect.InaccessibleObjectException异常?

解决Java 17升级中JPMS反射访问异常问题

一、先解决当前异常:确保--add-opens参数覆盖所有运行阶段

你添加的maven-surefire-plugin配置仅作用于测试阶段,如果异常出现在应用启动或运行阶段,该配置不会生效。需要分场景补充配置:

1. 测试阶段异常:修正surefire配置

确保argLine参数格式正确,避免换行导致的解析问题,修改为单行配置:

<plugin>
  <groupId>org.apache.maven.plugins</groupId>
  <artifactId>maven-surefire-plugin</artifactId>
  <configuration>
    <argLine>@{argLine} --add-opens java.base/javax.crypto.spec=ALL-UNNAMED</argLine>
  </configuration>
</plugin>

@{argLine}用于保留其他插件注入的JVM参数(比如Spring Boot的内存配置),如果没有其他参数,也可以直接写--add-opens java.base/javax.crypto.spec=ALL-UNNAMED。

2. 应用运行阶段异常:补充Spring Boot插件配置

如果用mvn spring-boot:run启动应用,给spring-boot-maven-plugin添加JVM参数:

<plugin>
  <groupId>org.springframework.boot</groupId>
  <artifactId>spring-boot-maven-plugin</artifactId>
  <configuration>
    <jvmArguments>--add-opens java.base/javax.crypto.spec=ALL-UNNAMED</jvmArguments>
  </configuration>
</plugin>

如果是打包成jar后运行,在启动命令中添加参数:

java --add-opens java.base/javax.crypto.spec=ALL-UNNAMED -jar your-application.jar

二、长期解决方案:替代--add-opens的规范做法

--add-opens是绕过JPMS访问控制的临时手段,更合规的解决方式如下:

1. 替换反射访问为标准API

异常根源是代码(或依赖库)通过反射访问SecretKeySpec的私有key字段。实际上SecretKeySpec继承自SecretKey,后者提供了标准的getEncoded()方法可直接获取密钥字节数组,完全替代反射逻辑:

// 替换之前的反射代码
SecretKeySpec secretKeySpec = ...;
byte[] keyBytes = secretKeySpec.getEncoded(); // 标准API,无需反射

2. 升级依赖库

如果是第三方依赖库在使用反射访问私有字段,检查该库是否有适配Java 11+的新版本。多数开源库在JPMS推出后已修复这类反射问题,改用标准API或适配模块系统,升级后即可消除异常。

3. 排查并移除不必要的反射代码

通过异常栈跟踪定位触发反射的具体类和方法,确认是否真的需要反射访问私有字段。如果是自定义代码,优先重构为使用公开API;如果是依赖库的问题,考虑替换为更兼容的替代库。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.25 04:22:47