JDK6和xml-apis之间的冲突
Posted
技术标签:
【中文标题】JDK6和xml-apis之间的冲突【英文标题】:Conflicts between JDK6 and xml-apis 【发布时间】:2015-06-01 05:39:16 【问题描述】:将需要 xerces-impl 依赖的 OpenSAML 从 1.1 升级到 2.6.1 后,启动时出现以下堆栈:
Caused by: java.lang.ClassCastException: org.apache.xerces.jaxp.datatype.DatatypeFactoryImpl cannot be cast to javax.xml.datatype.DatatypeFactory
at javax.xml.datatype.DatatypeFactory.newInstance(DatatypeFactory.java:131) ~[xml-apis-1.4.01.jar:1.6.0_45]
at com.sun.xml.bind.DatatypeConverterImpl.<clinit>(DatatypeConverterImpl.java:831) ~[glassfish.jaxb_1.0.0.0_2-1-12.jar:2.1.12]
... 68 common frames omitted
xerces-impl 重新定义了一些 jre 类,并带有重新定义一些 jre 接口的 xml-apis。 org.apache.xerces.jaxp.datatype.DatatypeFactoryImpl 来自 xerces-impl。
我使用的是 weblogic 10.3.5 和 JDK 6。
我阅读了Dealing with "Xerces hell" in Java/Maven? 并尝试排除 xml-apis 但 xerces-impl 抛出 NoClassDefFoundError。在 jre/lib/endorsed 中复制 xml-apis 和 xerces-impl 也会引发 ClassCastException (http://docs.oracle.com/javase/6/docs/technotes/guides/standards/)。
在启动命令抛出时添加 -Djavax.xml.datatype.DatatypeFactory=com.sun.org.apache.xerces.internal.jaxp.datatype.DatatypeFactoryImpl :
Caused by: java.lang.ClassCastException: org.apache.xerces.jaxp.SAXParserFactoryImpl cannot be cast to javax.xml.parsers.SAXParserFactory
at javax.xml.parsers.SAXParserFactory.newInstance(SAXParserFactory.java:128) ~[xml-apis-1.4.01.jar:1.6.0_45]
at javax.xml.bind.helpers.AbstractUnmarshallerImpl.getXMLReader(AbstractUnmarshallerImpl.java:80) ~[na:1.6.0_45]
然后添加 -Djavax.xml.parsers.SAXParserFactory=com.sun.org.apache.xerces.internal.jaxp.SAXParserFactoryImpl 抛出:
Caused by: java.lang.ClassCastException: com.sun.org.apache.xerces.internal.jaxp.SAXParserFactoryImpl cannot be cast to javax.xml.parsers.SAXParserFactory
at javax.xml.parsers.SAXParserFactory.newInstance(Unknown Source)
at ch.qos.logback.core.joran.event.SaxEventRecorder.buildSaxParser(SaxEventRecorder.java:79)
我不知道下一步该做什么。有什么想法吗?
【问题讨论】:
【参考方案1】:WebLogic 在类路径中包含许多此类库的自己的版本,它们可能会干扰您的应用程序。尝试在weblogic.xml
文件中添加这样的部分:
<weblogic-web-app>
<container-descriptor>
<prefer-application-packages>
<package-name>org.slf4j.*</package-name>
<package-name>org.slf4j.helpers.*</package-name>
<package-name>org.slf4j.impl.*</package-name>
<package-name>org.slf4j.spi.*</package-name>
</prefer-application-packages>
</container-descriptor>
...
</weblogic-web-app>
该示例显示了 slf4j 的包;我不确定它们对 xerces 有什么影响。如果您可以访问wls-cat tool,那应该有助于解决这个问题。
更新
WLS 和您的应用程序之间的类路径冲突可以通过以下三种方式之一进行修复。
-
将包添加到
<prefer-application-packages>
元素,以便应用优先
更改 POM 以注意特定依赖项是 WLS 的 provided
从 POM 中完全排除依赖项。
我建议在以前版本的 OpenSAML 中使用 mvn dependency:tree
,注意依赖关系。然后切换到新的 OpenSAML 版本,并注意引入了哪些新依赖项。查看 WLS 服务器的 modules
目录以查看 WLS 正在使用哪些库,将其与新 OpenSAML 版本的更改依赖项交叉引用,并决定这 3 种可能性中的哪一种似乎最合适。例如,如果您看到 WLS 使用的 lib 版本比您的应用程序更早,您可能希望使用选项 1。这样做直到您可以部署应用程序,然后使用 wls-cat 完成这项工作。
【讨论】:
我添加了:org.apache.xerces
。这意味着您可能至少需要 weblogic.xml 文件中的<package-name>org.apache.xerces.*</package-name>
。可能还有其他要求。
感谢您的帮助。使用 weblogic-application.xml 中的包名称和 startCmd 中没有“-D”选项,我在不同的类上有一个 ClassCastException: 引起:java.lang.ClassCastException:weblogic.xml.jaxp.RegistrySAXParserFactory 不能转换为javax.xml.parsers.SAXParserFactory at javax.xml.parsers.SAXParserFactory.newInstance(Unknown Source) at ch.qos.logback.core.joran.event.SaxEventRecorder.buildSaxParser(SaxEventRecorder.java:79) ... 54 更多
我添加了一个更新。不幸的是,我没有列出要放入 <prefer-application-packages>
或 POM 更改的清单,这些更改将使问题消失,找出每种情况都是独一无二的。我确实找到了 blog post 提到 xml-apis 可能是问题的来源之一。【参考方案2】:
除了javax.xml.bind 作为prefer-application
<wls:package-name>javax.xml.bind.*</wls:package-name>
在 weblogic.xml 中,添加 jaxb 依赖解决了我的问题:
<dependency>
<groupId>com.sun.xml.bind</groupId>
<artifactId>jaxb-impl</artifactId>
<version>$jaxb-impl.version</version>
</dependency>
<dependency>
<groupId>javax.xml.bind</groupId>
<artifactId>jaxb-api</artifactId>
<version>$jaxb-api.version</version>
</dependency>
【讨论】:
以上是关于JDK6和xml-apis之间的冲突的主要内容,如果未能解决你的问题,请参考以下文章