You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@cxf.apache.org by re...@apache.org on 2024/11/18 01:52:42 UTC
(cxf) 03/04: CXF-9076: Exception message is not unmarshalled with JDK17+ (limit the fix to JDK standard library exceptions) (#2148)
This is an automated email from the ASF dual-hosted git repository.
reta pushed a commit to branch 4.0.x-fixes
in repository https://gitbox.apache.org/repos/asf/cxf.git
commit d78b7b686ee03fba361099472bfde787cc33a9ed
Author: Andriy Redko <dr...@gmail.com>
AuthorDate: Sun Nov 17 11:39:54 2024 -0500
CXF-9076: Exception message is not unmarshalled with JDK17+ (limit the fix to JDK standard library exceptions) (#2148)
(cherry picked from commit e6229afc8c15fe46b2c64116e76fea794af03f98)
---
.../cxf/interceptor/ClientFaultConverter.java | 54 +++++++++++++++-------
.../systest/jaxws/ClientServerExceptionServer.java | 5 ++
.../systest/jaxws/ClientServerExceptionTest.java | 20 ++++++--
.../apache/cxf/systest/jaxws/ExceptionService.java | 1 +
.../{ExceptionService.java => SayException.java} | 19 ++++++--
5 files changed, 76 insertions(+), 23 deletions(-)
diff --git a/core/src/main/java/org/apache/cxf/interceptor/ClientFaultConverter.java b/core/src/main/java/org/apache/cxf/interceptor/ClientFaultConverter.java
index c2c1f9c365..c270f4d920 100644
--- a/core/src/main/java/org/apache/cxf/interceptor/ClientFaultConverter.java
+++ b/core/src/main/java/org/apache/cxf/interceptor/ClientFaultConverter.java
@@ -200,21 +200,8 @@ public class ClientFaultConverter extends AbstractInDatabindingInterceptor {
ReflectionUtil.setAccessible(f);
f.set(ex, fault.getMessage());
} catch (Exception e1) {
- try {
- // Fallback, try to clone the exception instead of accessing the detailMessage over reflection
- final Constructor<? extends Object> constructor = ReflectionUtil.getConstructor(ex.getClass(),
- String.class, Throwable.class); /* String message, Throwable cause */
-
- if (constructor != null) {
- final Exception clone = (Exception) constructor.newInstance(message, ex.getCause());
- clone.setStackTrace(ex.getStackTrace());
- if (ex.getSuppressed().length > 0) {
- Arrays.stream(ex.getSuppressed()).forEach(clone::addSuppressed);
- }
- ex = clone;
- }
- } catch (Exception e2) {
- /* nothing to do */
+ if (isJdkException(ex.getClass().getPackageName())) {
+ ex = cloneJdkException(ex, message);
}
}
}
@@ -222,6 +209,37 @@ public class ClientFaultConverter extends AbstractInDatabindingInterceptor {
}
}
+ private static Exception cloneJdkException(Exception ex, final String message) {
+ try {
+ // Fallback, try to clone the exception instead of accessing the detailMessage
+ // over reflection
+ Constructor<? extends Object> constructor = ReflectionUtil.getConstructor(
+ ex.getClass(), String.class, Throwable.class); /* String message, Throwable cause */
+
+ Exception clone = null;
+ if (constructor != null) {
+ clone = (Exception) constructor.newInstance(message, ex.getCause());
+ } else {
+ constructor = ReflectionUtil.getConstructor(ex.getClass(), String.class); /* String message */
+ if (constructor != null) {
+ clone = (Exception) constructor.newInstance(message);
+ clone.initCause(ex.getCause());
+ }
+ }
+
+ if (clone != null) {
+ clone.setStackTrace(ex.getStackTrace());
+ if (ex.getSuppressed().length > 0) {
+ Arrays.stream(ex.getSuppressed()).forEach(clone::addSuppressed);
+ }
+ return clone;
+ }
+ } catch (Exception e2) {
+ /* nothing to do */
+ }
+ return ex;
+ }
+
private Constructor<?> getConstructor(Class<?> faultClass, Object e) throws NoSuchMethodException {
Class<?> beanClass = e.getClass();
Constructor<?>[] cons = faultClass.getConstructors();
@@ -300,7 +318,7 @@ public class ClientFaultConverter extends AbstractInDatabindingInterceptor {
Throwable res = null;
if (firstLine.indexOf(':') != -1) {
String cn = firstLine.substring(0, firstLine.indexOf(':')).trim();
- if (cn.startsWith("java.lang")) {
+ if (isJdkException(cn)) {
try {
res = (Throwable)Class.forName(cn).getConstructor(String.class)
.newInstance(firstLine.substring(firstLine.indexOf(':') + 2));
@@ -327,6 +345,10 @@ public class ClientFaultConverter extends AbstractInDatabindingInterceptor {
return res;
}
+ private static boolean isJdkException(String pkg) {
+ return pkg.startsWith("java.lang");
+ }
+
private static StackTraceElement parseStackTrackLine(String oneLine) {
StringTokenizer stInner = new StringTokenizer(oneLine, "!");
return new StackTraceElement(stInner.nextToken(), stInner.nextToken(),
diff --git a/systests/jaxws/src/test/java/org/apache/cxf/systest/jaxws/ClientServerExceptionServer.java b/systests/jaxws/src/test/java/org/apache/cxf/systest/jaxws/ClientServerExceptionServer.java
index 06ad7e98f0..2cb2d371a6 100644
--- a/systests/jaxws/src/test/java/org/apache/cxf/systest/jaxws/ClientServerExceptionServer.java
+++ b/systests/jaxws/src/test/java/org/apache/cxf/systest/jaxws/ClientServerExceptionServer.java
@@ -33,6 +33,11 @@ public class ClientServerExceptionServer extends AbstractBusTestServerBase {
public String saySomething(String text) throws IllegalArgumentException {
throw new IllegalArgumentException("Simulated!");
}
+
+ @Override
+ public String sayNothing(String text) throws SayException {
+ throw new SayException("Simulated!", 100);
+ }
}
protected void run() {
diff --git a/systests/jaxws/src/test/java/org/apache/cxf/systest/jaxws/ClientServerExceptionTest.java b/systests/jaxws/src/test/java/org/apache/cxf/systest/jaxws/ClientServerExceptionTest.java
index 2e74489026..73db4fcc54 100644
--- a/systests/jaxws/src/test/java/org/apache/cxf/systest/jaxws/ClientServerExceptionTest.java
+++ b/systests/jaxws/src/test/java/org/apache/cxf/systest/jaxws/ClientServerExceptionTest.java
@@ -27,6 +27,7 @@ import javax.xml.namespace.QName;
import jakarta.xml.ws.Service;
import org.apache.cxf.testutil.common.AbstractBusClientServerTestBase;
+import org.junit.Before;
import org.junit.BeforeClass;
import org.junit.Test;
@@ -35,20 +36,33 @@ import static org.junit.Assert.assertThrows;
import static org.junit.Assert.assertTrue;
public class ClientServerExceptionTest extends AbstractBusClientServerTestBase {
+ private ExceptionService port;
+
@BeforeClass
public static void startServers() throws Exception {
assertTrue("server did not launch correctly", launchServer(ClientServerExceptionServer.class, true));
}
- @Test
- public void exceptionMessageIsPreserved() throws MalformedURLException {
+ @Before
+ public void setUp() throws Exception {
URL wsdlURL = new URL("http://localhost:" + ClientServerExceptionServer.PORT + "/ExceptionService?wsdl");
QName qname = new QName("http://cxf.apache.org/", "ExceptionService");
Service service = Service.create(wsdlURL, qname);
- ExceptionService port = service.getPort(ExceptionService.class);
+ port = service.getPort(ExceptionService.class);
+ }
+ @Test
+ public void exceptionMessageIsPreserved() throws MalformedURLException {
final IllegalArgumentException ex = assertThrows(IllegalArgumentException.class,
() -> port.saySomething("Hello World!"));
assertEquals("Simulated!", ex.getMessage());
}
+
+ @Test
+ public void exceptionCustomExceptionMessageIsPreserved() throws MalformedURLException {
+ final SayException ex = assertThrows(SayException.class,
+ () -> port.sayNothing("Hello World!"));
+ assertEquals("Simulated!", ex.getMessage());
+ assertEquals(100, ex.getCode());
+ }
}
diff --git a/systests/jaxws/src/test/java/org/apache/cxf/systest/jaxws/ExceptionService.java b/systests/jaxws/src/test/java/org/apache/cxf/systest/jaxws/ExceptionService.java
index ac2d87083f..6473b80972 100644
--- a/systests/jaxws/src/test/java/org/apache/cxf/systest/jaxws/ExceptionService.java
+++ b/systests/jaxws/src/test/java/org/apache/cxf/systest/jaxws/ExceptionService.java
@@ -24,4 +24,5 @@ import jakarta.jws.WebService;
@WebService
interface ExceptionService {
String saySomething(String text) throws IllegalArgumentException;
+ String sayNothing(String text) throws SayException;
}
diff --git a/systests/jaxws/src/test/java/org/apache/cxf/systest/jaxws/ExceptionService.java b/systests/jaxws/src/test/java/org/apache/cxf/systest/jaxws/SayException.java
similarity index 70%
copy from systests/jaxws/src/test/java/org/apache/cxf/systest/jaxws/ExceptionService.java
copy to systests/jaxws/src/test/java/org/apache/cxf/systest/jaxws/SayException.java
index ac2d87083f..0201400b0e 100644
--- a/systests/jaxws/src/test/java/org/apache/cxf/systest/jaxws/ExceptionService.java
+++ b/systests/jaxws/src/test/java/org/apache/cxf/systest/jaxws/SayException.java
@@ -19,9 +19,20 @@
package org.apache.cxf.systest.jaxws;
-import jakarta.jws.WebService;
+public class SayException extends Exception {
+ private static final long serialVersionUID = 1L;
+ private final int code;
-@WebService
-interface ExceptionService {
- String saySomething(String text) throws IllegalArgumentException;
+ public SayException() {
+ this(null, 0);
+ }
+
+ public SayException(final String message, final int code) {
+ super(message);
+ this.code = code;
+ }
+
+ public int getCode() {
+ return code;
+ }
}