Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

CDI can throw NullPointerException if application startup fails #26054

Closed
Azquelt opened this issue Aug 25, 2023 · 2 comments · Fixed by #26168
Closed

CDI can throw NullPointerException if application startup fails #26054

Azquelt opened this issue Aug 25, 2023 · 2 comments · Fixed by #26168
Labels
in:CDI in:Web Components release bug This bug is present in a released version of Open Liberty release:230010

Comments

@Azquelt
Copy link
Member

Azquelt commented Aug 25, 2023

Describe the bug

When an error occurs during application startup which causes startup to fail, CDI can sometimes throw a NullPointerException which appears in the logs.

This doesn't cause any harm to a working system since it only occurs when app startup fails, but it causes confusion because it looks like the NPE is the cause of the app startup failure, rather than being caused by it.

Log messages like the following are seen:

[24/08/2023, 16:17:17:806 BST] 0000003f com.ibm.ws.logging.internal.impl.IncidentImpl                I FFDC1015I: An FFDC Incident has been created: "java.lang.Error: Test error com.ibm.ws.webcontainer.osgi.DynamicVirtualHost startWebApp" at ffdc_23.08.24_16.17.17.0.log
[24/08/2023, 16:17:17:846 BST] 0000003d com.ibm.ws.webcontainer.osgi.mbeans.PluginGenerator          I SRVE9103I: A configuration file for a web server plugin was automatically generated for this server at /home/andrew/git/open-liberty/dev/build.image/wlp/usr/servers/cdi12BasicServer/logs/state/plugin-cfg.xml.
[24/08/2023, 16:17:17:871 BST] 0000003f com.ibm.ws.logging.internal.impl.IncidentImpl                I FFDC1015I: An FFDC Incident has been created: "java.lang.NullPointerException: Cannot invoke "org.jboss.weld.module.web.servlet.HttpContextLifecycle.contextDestroyed(jakarta.servlet.ServletContext)" because "this.lifecycle" is null com.ibm.ws.webcontainer.webapp.WebApp.notifyServletContextDestroyed 1405" at ffdc_23.08.24_16.17.17.1.log
[24/08/2023, 16:17:17:872 BST] 0000003f com.ibm.ws.webcontainer.webapp                               E SRVE0285E: Exception caught while destroying context: java.lang.NullPointerException: Cannot invoke "org.jboss.weld.module.web.servlet.HttpContextLifecycle.contextDestroyed(jakarta.servlet.ServletContext)" because "this.lifecycle" is null
	at org.jboss.weld.module.web.servlet.WeldInitialListener.contextDestroyed(WeldInitialListener.java:113)
	at com.ibm.ws.cdi.web.factories.Weld50InitialListener.contextDestroyed(Weld50InitialListener.java:51)
	at com.ibm.ws.webcontainer.webapp.WebApp.notifyServletContextDestroyed(WebApp.java:2700)
	at com.ibm.ws.webcontainer.webapp.WebApp.destroy(WebApp.java:4036)
	at com.ibm.ws.webcontainer.osgi.webapp.WebApp.destroy(WebApp.java:1470)
	at com.ibm.ws.webcontainer.osgi.DynamicVirtualHost.stopWebApp(DynamicVirtualHost.java:510)
	at com.ibm.ws.webcontainer.osgi.DynamicVirtualHost.startWebApp(DynamicVirtualHost.java:488)
	at com.ibm.ws.webcontainer.osgi.DynamicVirtualHost.startWebApplication(DynamicVirtualHost.java:473)
	at com.ibm.ws.webcontainer.osgi.WebContainer.startWebApplication(WebContainer.java:1206)
	at com.ibm.ws.webcontainer.osgi.WebContainer.access$100(WebContainer.java:112)
	at com.ibm.ws.webcontainer.osgi.WebContainer$3.run(WebContainer.java:994)
	at com.ibm.ws.threading.internal.ExecutorServiceImpl$RunnableWrapper.run(ExecutorServiceImpl.java:247)
	at java.base/java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:539)
	at java.base/java.util.concurrent.FutureTask.run(FutureTask.java:264)
	at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1136)
	at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:635)
	at java.base/java.lang.Thread.run(Thread.java:857)

[24/08/2023, 16:17:17:900 BST] 0000003f com.ibm.ws.app.manager.AppMessageHelper                      A CWWKZ0012I: The application servletStartup was not started.

Steps to Reproduce

  • Create an app with a ServletContainerInitializer which throws an Error from its onStartup method.
  • Ensure the app contains a CDI bean
  • Ensure the server config contains both the servlet and cdi features
  • Deploy the app and start the server

Expected behavior

The app should fail to start but a NullPointerException from CDI should not be logged.

Diagnostic information:

  • OpenLiberty Version: current integration, but likely affects many previous versions
  • Affected feature(s) cdi-4.0 and likely previous CDI features
  • Java Version: N/A
  • server.xml configuration (WITHOUT sensitive information like passwords)
  • If it would be useful, upload the messages.log file found in $WLP_OUTPUT_DIR/messages.log

Additional context
Add any other context about the problem here.

Debugging through, it looks like when application startup fails in this way, contextInitialized is not called for any registered ServletContextListeners, but contextDestroyed is called.

The NPE is a consequence of the WeldInitialListener accessing a field in contextDestroyed which would have been initialized by contextInitialized.

Although I've reproduced the problem by throwing an Error from a ServletContainerInitializer, this error will occur whenever ServletContextListener.contextDestroyed is called without contextInitialized being called first.

@Azquelt Azquelt added the release bug This bug is present in a released version of Open Liberty label Aug 25, 2023
@Azquelt Azquelt added this to Backlog in MicroProfile UK via automation Aug 25, 2023
@Azquelt Azquelt moved this from Backlog to Planned in MicroProfile UK Aug 25, 2023
@pmd1nh
Copy link
Member

pmd1nh commented Aug 28, 2023

Relevant links:

(1) Servlet API

(2) Servlet Spec

In the current design/flow, the ServletContextListener.contextDestroyed​ is invoked after ServletContainerInitializer if no exception has occured.

Both (1) and (2) have no requirement that contextDestroyed​ must not be called if contextInitialized​ has not been invoked.

Can Weld check for its null objects in the contextDestroyed ?

@Azquelt
Copy link
Member Author

Azquelt commented Sep 1, 2023

Fixing this for future versions of Weld under https://issues.redhat.com/projects/WELD/issues/WELD-2752

I'll implement a workaround for older versions.

MicroProfile UK automation moved this from Planned to Done Sep 8, 2023
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
in:CDI in:Web Components release bug This bug is present in a released version of Open Liberty release:230010
Projects
Development

Successfully merging a pull request may close this issue.

3 participants