Issue
I am upgrading a behemoth application from Java 8 to Java 11. We are still building with Java 8 but running with Java 11.
I am seeing a class not properly loading because of a loader constraint violation. The code base imports this class via a jar file in a maven dependency. If we remove the jar file before starting the application the issue goes away.
The error is below:
loader constraint violation: loader 'bootstrap' wants to load interface org.w3c.dom.traversal.NodeIterator. A different interface with the same name was previously loaded by com.app.CustomClassLoader @9626f9, parent loader java.net.URLClassLoader @13afaa3)
I found that previously this class was loaded by the bootstrap class loader first. Now it's loaded by the custom application loader first. The order difference is below:
Java 8:
INFO | jvm 1 | 2020/01/08 11:34:30.626 | [Loaded org.w3c.dom.traversal.NodeIterator from /java-1.8.0_221.i586/jre/lib/rt.jar] INFO | jvm 1 | 2020/01/08 11:34:34.184 | [Loaded org.dom4j.NodeIterator from file:/webapps/lib/dom4j-x.x.x.jar]
In Java 11
INFO | jvm 1 | 2020/01/07 17:45:49.426 | [3.787s][info
][class,load] org.dom4j.NodeIterator source: file:/webapps/lib/dom4j-x.x.x.jar INFO | jvm 1 | 2020/01/07 17:46:15.772 | [30.210s][info ][class,load ] org.w3c.dom.traversal.NodeIterator source: file:/webapps/lib/xml-x.x.x.jar INFO | jvm 1 | 2020/01/07 17:46:15.772 | [30.210s][info ][class,load ] org.w3c.dom.traversal.NodeIterator source: jrt:/java.xml
Manually removing xml-x.x.x.jar
before startup prevents this from happening. I am trying to resolve this without removing that jar or the dependency. Is there a way to force the bootstrap class loader into loading the xml-x.x.x.jar
file first? I tried adding the jar file in the bootclasspath but it did not resolve it.
Solution
If you need this artifact only during build, you can change its scope to provided
<scope>provided</scope>
, this way maven won't load this dependency for runtime
Answered By - ramazan
Answer Checked By - Willingham (JavaFixing Volunteer)