Spring Boot 2.5 WAR app fails to deploy in Wildfly due to "ClassNotFoundException: # Licensed to the Apache ..." #26640
Labels
for: external-project
For an external project and not something we can fix
#24744 switched the default EL implementation from glassfish to tomcat-el-embed. However, the tomcat implementation appears to violate the spec (https://docs.oracle.com/javaee/7/api/javax/el/ExpressionFactory.html#newInstance-- ):
The trouble being that the first line of that file in the TC implementation is indeed a comment indicating it's licenced under Apache 2.0 (I can't find a direct link to show this in their git repo so it may be generated, or a service to directly link to the file within the built JAR, but I'll repeat the whole file as I see it inside
tomcat-embed-el-9.0.46.jar
:So I believe the issue is that the wildfly module system overrides the tomcat-embed-el implementation of
javax.el.ExpressionFactory
with the version from JBoss (https://github.com/jboss/jboss-jakarta-el-api_spec) which seems to be much stricter when it comes to the spec adherence (along with the Jakarta RI), and so ...Underneath, this is likely a Tomcat issue (on the basis that both the JBoss impl + Jakarta impl strictly read the first line of the file and use that - https://github.com/jboss/jboss-jakarta-el-api_spec/blob/master/api/src/main/java/org/jboss/el/cache/FactoryFinderCache.java#L99), but SB 2.5 users deploying into an environment where
javax.el.ExpressionFactory
uses the JBoss/Jakarta version are going to notice the problem sooner I guess. I'm raising thisa. for visibility,
b. to pick up an updated Tomcat dependency as/when/if they move the licence down in the file or remove it entirely. (or if Spring wants to reverse the decision until Tomcat fixes its file?)
c. to list potential workarounds for others who run into the issue.
Possible workarounds:
tomcat-el-embed
dependency and replace with the org.glassfish:jakarta-el implementation again, reversing the effects of Switch to Apache EL implementation by default #24744 - this works because the JBoss module system also has a fallback class ofcom.sun.el.ExpressionFactoryImpl
defined which is provded by jakarta-elMETA-INF/services/javax.el.ExpressionFactory
file in the application WAR where the first line really isorg.apache.el.ExpressionFactoryImpl
(I would guess this carries some risks about which file will be picked up by the service loader first, but one would presume WAR resources will be picked ahead of resources insideWEB-INF/lib/*.jar
. Seems to work for me for the mo ...)<local-last value="false" />
in asrc/main/webapp/META-INF/jboss-deployment-structure.xml
file and ensure that jakarta-el implementation is not also on the classpath of the WAR application itself.The text was updated successfully, but these errors were encountered: