TOMEE-4642 - Don't fail deployment when a servlet/filter/listener class is missing#2848
Open
jungm wants to merge 1 commit into
Open
TOMEE-4642 - Don't fail deployment when a servlet/filter/listener class is missing#2848jungm wants to merge 1 commit into
jungm wants to merge 1 commit into
Conversation
…ss is missing
When a war's web.xml or annotations name a servlet, filter or listener
class that is not packaged in the war, ProcessAnnotatedBeans.deploy
rethrew the ClassNotFoundException/NoClassDefFoundError as an
OpenEJBException, which aborted startup of the whole web context.
These loads only feed the annotation scanner, so a missing class simply
means there is nothing to scan - it must not bring down the context.
Jakarta Servlet 6.1 section 2.3.1 allows servlet loading to be delayed
"until the container determines the servlet is needed to service a
request", so an unresolved class is deferred, not fatal. The three paths
now log a warning and continue, matching the existing tolerant handling
of taglib listeners and the servlet name-fallback case.
Also fixed off-by-one MessageFormat placeholder indices ({1}{2}{3} ->
{0}{1}{2}) in the four related logger.debug calls, which dropped the
first argument.
Two Jakarta Servlet TCK deployments triggered this (RegistrationTests
naming filter AddFilterString, DefaultMappingTests naming servlet
TestServlet1).
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
What
When a war's
web.xmlor annotations name a servlet, filter or listener class that is not packaged in the war,AnnotationDeployer.ProcessAnnotatedBeans.deploy(WebModule)rethrew theClassNotFoundException/NoClassDefFoundErroras anOpenEJBException. That propagates out throughConfigurationFactory.configureApplicationand aborts startup of the whole web context.This changes the servlet, filter and listener paths to log a warning and continue instead of failing.
Why
These
classLoader.loadClass(...)calls exist only to feed the annotation scanner. A class that cannot be loaded simply contributes nothing to scan — it should not bring the context down.The old behaviour was also internally inconsistent: the taglib-listener loop right below, and the servlet name-fallback case, already only logged and continued. Only the explicit-class servlet/filter/listener paths were fatal.
Jakarta Servlet 6.1 §2.3.1 ("Loading and Instantiation") permits servlet loading to be "delayed until the container determines the servlet is needed to service a request", so deferring an unresolved class rather than failing eagerly at deploy time is spec-compliant. If such a component is actually used, Tomcat still surfaces the missing class per-component.
The
WsDeployerthrow for webservice servlet classes was intentionally left as-is, since a WS endpoint genuinely cannot be built without its class.Also
Fixed off-by-one
MessageFormatplaceholder indices ({1}{2}{3}→{0}{1}{2}) in the four relatedlogger.debugcalls, which were dropping the first argument from the message.Testing
Added
AnnotationDeployerTest.missingServletFilterAndListenerClassesDoNotFailDeployment, using the class names from the ticket (TestServlet1,AddFilterString, plus a missing listener). Verified it is a real regression test: reverting the servlet fix makes it fail with exactly the reported error (OpenEJBException: Unable to load servlet class: ...TestServlet1), and it passes with the fix.This is the TomEE-side fix for the two Jakarta Servlet TCK deployments that triggered the abort (
RegistrationTestsnaming filterAddFilterString;DefaultMappingTestsnaming servletTestServlet1). Removing the corresponding entries fromrunner-standalone/exclusions/servlet.txtin the apache/tomee-tck harness and confirming both classes pass is a follow-up in that separate repo.Jira: https://issues.apache.org/jira/browse/TOMEE-4642
🤖 Generated with Claude Code