如何解决Java 9中的java.lang.NoClassDefFoundError:javax / xml / bind / JAXBException
我有一些使用JAXB API类的代码,它们是作为Java 6/7/8中JDK的一部分提供的。 当我使用Java 9运行相同的代码时,在运行时,我收到错误,指出在运行时无法findJAXB类。
自Java 6以来,JAXB类已经作为JDK的一部分提供,那么Java 9为什么不能再find这些类呢?
JAXB API被认为是Java EE API,因此不再包含在Java SE 9的默认类path中。
Java 9引入了模块的概念,默认情况下, java.se
聚合模块在类path(或模块path)上可用。 顾名思义, java.se
聚合模块不包含传统上与Java 6/7/8捆绑在一起的Java EE API。
幸运的是,JDK 6/7/8中提供的这些Java EE API仍然在JDK中,但默认情况下它们不在类path中。 额外的Java EE API在以下模块中提供:
java.activation java.corba java.transaction java.xml.bind << This one contains the JAXB APIs java.xml.ws java.xml.ws.annotation
快速解决scheme
要使JAXB API在运行时可用,请指定以下命令行选项:
--add-modules java.xml.bind
但我仍然需要这个与Java 8一起工作!
如果你尝试用一个较老的JDK来指定--add-modules
,它将会炸毁,因为这是一个无法识别的选项。 我build议两种select之一:
- 您可以通过检查
JAVA_VERSION
属性的$JAVA_HOME/release
来检查JDK版本,从而在启动脚本中有条件地应用参数(如果有的话)。 - 您可以添加
-XX:+IgnoreUnrecognizedVMOptions
以使JVM以静默方式忽略未经批准的选项,而不是炸毁。 但要小心! 您使用的任何其他命令行参数将不再由JVMvalidation。 此选项适用于Oracle / OpenJDK以及IBM JDK(从JDK 8sr4开始)
备用解决scheme:
请注意,通过指定--add-modules java.se.ee
选项,可以使所有上述Java EE模块在运行时可用。 java.se.ee
模块是一个包含java.se.ee
以及上述Java EE API模块的聚合模块。
尽pipeJava 10还有很长的路要走,但值得注意的是,所有上述的Java EE API模块都被标记为@Deprecated(forRemoval=true)
,所以它们在未来的Java版本中被移除是公平的游戏! 为了最大限度地面向未来,您应该养成在类path或模块path中指定自己的Java EE API拷贝的习惯。
有关Java模块化的完整详细信息,请参阅JEP 261页面: http : //openjdk.java.net/jeps/261
这对我工作:
<dependency> <groupId>javax.xml.bind</groupId> <artifactId>jaxb-api</artifactId> <version>2.3.0</version> </dependency> <dependency> <groupId>org.eclipse.persistence</groupId> <artifactId>eclipselink</artifactId> <version>2.7.0</version> </dependency>
作为我的Java 8应用程序的依赖项,它生成一个* .jar,可以由JRE 8或JRE 9运行,不需要额外的参数。
另外,这需要在使用JAXB API之前执行:
System.setProperty("javax.xml.bind.JAXBContextFactory", "org.eclipse.persistence.jaxb.JAXBContextFactory");
作为一个解决方法,到目前为止效果很好。 虽然看起来不是一个完美的解决scheme
在编译时以及运行时,添加开关--add-modules java.xml.bind
javac --add-modules java.xml.bind <java file name> java --add-modules java.xml.bind <class file>
有关JDK 9
模块的详细介绍,请访问: https : //www.youtube.com/watch?v = KZfbRuvv5qc
对于Java Web Start Execution,我们可以使用Andy Guibert的build议:
<j2se version="1.6+" java-vm-args="-XX:+IgnoreUnrecognizedVMOptions --add-modules=java.se.ee"/>
注意–add-modules中额外的“=”。 请参阅此OpenJDK故障单或Java Platform Standard Edition Oracle JDK 9迁移指南的 “了解运行时访问警告”中的最后一个注释。
您可以使用“ –add-modules = java.xml.bind ”JVM选项将xml绑定模块添加到JVM运行时环境。
例如:“java –add-modules = java.xml.bind XmlTestClass”