This is an automated email from the ASF dual-hosted git repository.
paulrutter pushed a commit to branch
maintenance/FELIX-6746-websocketservlet-init-NPE
in repository https://gitbox.apache.org/repos/asf/felix-dev.git
The following commit(s) were added to
refs/heads/maintenance/FELIX-6746-websocketservlet-init-NPE by this push:
new 0de03ea42d FELIX-6746 JettyWebSocketServlet: Error during calling
init() - Call init lazy in case of servlets that extend JettyWebSocketServlet -
This fixes the IT as well
0de03ea42d is described below
commit 0de03ea42d170aa982cafdccaf9b059596313e96
Author: Paul Rütter <[email protected]>
AuthorDate: Mon Dec 30 11:36:52 2024 +0100
FELIX-6746 JettyWebSocketServlet: Error during calling init()
- Call init lazy in case of servlets that extend JettyWebSocketServlet
- This fixes the IT as well
---
.../http/base/internal/handler/ServletHandler.java | 54 ++++++++++++++++++----
.../http/jetty/it/JettySpecificWebsocketIT.java | 10 ++--
2 files changed, 49 insertions(+), 15 deletions(-)
diff --git
a/http/base/src/main/java/org/apache/felix/http/base/internal/handler/ServletHandler.java
b/http/base/src/main/java/org/apache/felix/http/base/internal/handler/ServletHandler.java
index 5a9c97a0ac..1291c7a8a0 100644
---
a/http/base/src/main/java/org/apache/felix/http/base/internal/handler/ServletHandler.java
+++
b/http/base/src/main/java/org/apache/felix/http/base/internal/handler/ServletHandler.java
@@ -42,6 +42,9 @@ public abstract class ServletHandler implements
Comparable<ServletHandler>
private static final String JAVA_SERVLET_TEMP_DIR_PROP =
"jakarta.servlet.content.tempdir";
+ // The Jetty class used for Jetty WebSocket servlets
+ private static final String JETTY_WEB_SOCKET_SERVLET_CLASS =
"JettyWebSocketServlet";
+
private final long contextServiceId;
private final ServletInfo servletInfo;
@@ -52,6 +55,8 @@ public abstract class ServletHandler implements
Comparable<ServletHandler>
protected volatile int useCount;
+ private boolean isInitialized = false;
+
private final MultipartConfig mpConfig;
public ServletHandler(final long contextServiceId,
@@ -125,6 +130,16 @@ public abstract class ServletHandler implements
Comparable<ServletHandler>
final Servlet local = this.servlet;
if ( local != null )
{
+ if (!isInitialized){
+ // Lazy init if needed
+ try {
+ servlet.init(new ServletConfigImpl(getName(),
getContext(), getServletInfo().getInitParameters()));
+ isInitialized = true;
+ } catch (final Exception e) {
+
SystemLogger.LOGGER.error(SystemLogger.formatMessage(this.getServletInfo().getServiceReference(),
+ "Error calling init() lazy on servlet
".concat(this.servletInfo.getClassName(this.servlet))),
+ e);}
+ }
local.service(req, res);
}
else
@@ -173,21 +188,40 @@ public abstract class ServletHandler implements
Comparable<ServletHandler>
return DTOConstants.FAILURE_REASON_SERVICE_NOT_GETTABLE;
}
- try
- {
- servlet.init(new ServletConfigImpl(getName(), getContext(),
getServletInfo().getInitParameters()));
- }
- catch (final Exception e)
- {
-
SystemLogger.LOGGER.error(SystemLogger.formatMessage(this.getServletInfo().getServiceReference(),
- "Error during calling init() on servlet
".concat(this.servletInfo.getClassName(this.servlet))),
- e);
- return DTOConstants.FAILURE_REASON_EXCEPTION_ON_INIT;
+ if (!isJettyWebSocketServlet()) {
+ try {
+ servlet.init(new ServletConfigImpl(getName(), getContext(),
getServletInfo().getInitParameters()));
+ isInitialized = true;
+ } catch (final Exception e) {
+
SystemLogger.LOGGER.error(SystemLogger.formatMessage(this.getServletInfo().getServiceReference(),
+ "Error during calling init() on servlet
".concat(this.servletInfo.getClassName(this.servlet))),
+ e);
+ return DTOConstants.FAILURE_REASON_EXCEPTION_ON_INIT;
+ }
}
this.useCount++;
return -1;
}
+ /**
+ * Check if the servlet is a JettyWebSocketServlet.
+ * JettyWebSocket classes are handled differently due to FELIX-6746
+ * @return true if the servlet is a JettyWebSocketServlet, false otherwise
+ */
+ private boolean isJettyWebSocketServlet() {
+ final Class<?> superClass = servlet.getClass().getSuperclass();
+ SystemLogger.LOGGER.debug("Checking if the servlet is a
JettyWebSocketServlet: '" + superClass.getSimpleName() + "'");
+
+ // Now check if the servlet class extends 'JettyWebSocketServlet'
+ boolean isJettyWebSocketServlet =
superClass.getSimpleName().endsWith(JETTY_WEB_SOCKET_SERVLET_CLASS);
+ if (!isJettyWebSocketServlet && servlet instanceof
org.apache.felix.http.javaxwrappers.ServletWrapper) {
+ // In case the servlet is wrapped, we need to check the wrapped
servlet
+ isJettyWebSocketServlet =
((org.apache.felix.http.javaxwrappers.ServletWrapper) servlet)
+
.getServlet().getClass().getSuperclass().getSimpleName().endsWith(JETTY_WEB_SOCKET_SERVLET_CLASS);
+ }
+ return isJettyWebSocketServlet;
+ }
+
public boolean destroy()
{
diff --git
a/http/jetty12/src/test/java/org/apache/felix/http/jetty/it/JettySpecificWebsocketIT.java
b/http/jetty12/src/test/java/org/apache/felix/http/jetty/it/JettySpecificWebsocketIT.java
index 097dc83fe3..7f883370c5 100644
---
a/http/jetty12/src/test/java/org/apache/felix/http/jetty/it/JettySpecificWebsocketIT.java
+++
b/http/jetty12/src/test/java/org/apache/felix/http/jetty/it/JettySpecificWebsocketIT.java
@@ -138,15 +138,15 @@ public class JettySpecificWebsocketIT extends
AbstractJettyTestSupport {
@Test
public void testWebSocketServletWhiteboard() throws Exception {
- final JettyWebSocketServlet webSocketServlet2 = new
JettyWebSocketServlet() {
+ final JettyWebSocketServlet webSocketServlet = new
JettyWebSocketServlet() {
@Override
protected void configure(JettyWebSocketServletFactory
jettyWebSocketServletFactory) {
jettyWebSocketServletFactory.register(MyServerWebSocket.class);
}
};
- final Dictionary<String, Object> webSocketServletProps2 = new
Hashtable<>();
- webSocketServletProps2.put(HTTP_WHITEBOARD_SERVLET_PATTERN,
"/websocketservlet/*");
- bundleContext.registerService(Servlet.class, webSocketServlet2,
webSocketServletProps2);
+ final Dictionary<String, Object> props = new Hashtable<>();
+ props.put(HTTP_WHITEBOARD_SERVLET_PATTERN, "/websocketservlet");
+ bundleContext.registerService(Servlet.class, webSocketServlet, props);
HttpClientTransportOverHTTP transport = new
HttpClientTransportOverHTTP();
HttpClient httpClient = new
org.eclipse.jetty.client.HttpClient(transport);
@@ -155,7 +155,7 @@ public class JettySpecificWebsocketIT extends
AbstractJettyTestSupport {
Object value =
bundleContext.getServiceReference(HttpService.class).getProperty("org.osgi.service.http.port");
int httpPort = Integer.parseInt((String)value);
- URI destUri = new
URI(String.format("ws://localhost:%d/websocketservlet/test", httpPort));
+ URI destUri = new
URI(String.format("ws://localhost:%d/websocketservlet", httpPort));
MyClientWebSocket clientWebSocket = new MyClientWebSocket();
ClientUpgradeRequest request = new ClientUpgradeRequest();