This is an automated email from the ASF dual-hosted git repository.
reta pushed a commit to branch 3.6.x-fixes
in repository https://gitbox.apache.org/repos/asf/cxf.git
The following commit(s) were added to refs/heads/3.6.x-fixes by this push:
new 0c0b8b5372a Improve tracing test diagnostics for flaky test
investigation (#2999)
0c0b8b5372a is described below
commit 0c0b8b5372af77ea34663c877201e5e8163977df
Author: Guillaume Nodet <[email protected]>
AuthorDate: Fri May 8 01:32:13 2026 +0200
Improve tracing test diagnostics for flaky test investigation (#2999)
* Improve tracing test diagnostics: use untilAsserted with span list output
Replace await().until(() -> spans.size() == N) with
await().untilAsserted(() -> assertThat(message, size, equalTo(N)))
across all tracing system tests. When the Awaitility wait times out,
the error message now includes the actual span count and the full
list of collected spans, making it much easier to diagnose whether
the failure is caused by missing spans, extra spans from cross-test
contamination, or a timing issue.
Co-Authored-By: Claude Opus 4.6 <[email protected]>
* Extract HasSize matcher to reduce assertion duplication in tracing tests
Address review feedback: replace verbose untilAsserted assertions with
a custom HasSize matcher that includes span list contents on mismatch.
Co-Authored-By: Claude Opus 4.6 (1M context) <[email protected]>
---------
Co-authored-by: Claude Opus 4.6 <[email protected]>
(cherry picked from commit 440137a58e82769ada0a4fc8b431f288ff78dc53)
---
.../test/java/org/apache/cxf/systest/HasSize.java | 52 ++++++++++++++++++++++
.../JaxrsOpenTelemetryTracingTest.java | 22 ++++-----
.../opentracing/JaxrsOpenTracingTracingTest.java | 22 ++++-----
.../JaxwsOpenTelemetryTracingTest.java | 6 +--
.../opentracing/JaxwsOpenTracingTracingTest.java | 6 +--
5 files changed, 74 insertions(+), 34 deletions(-)
diff --git a/systests/tracing/src/test/java/org/apache/cxf/systest/HasSize.java
b/systests/tracing/src/test/java/org/apache/cxf/systest/HasSize.java
new file mode 100644
index 00000000000..af74e6cb784
--- /dev/null
+++ b/systests/tracing/src/test/java/org/apache/cxf/systest/HasSize.java
@@ -0,0 +1,52 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.cxf.systest;
+
+import java.util.Collection;
+
+import org.hamcrest.Description;
+import org.hamcrest.TypeSafeMatcher;
+
+public class HasSize extends TypeSafeMatcher<Collection<?>> {
+ private final int expectedSize;
+
+ public HasSize(int expectedSize) {
+ this.expectedSize = expectedSize;
+ }
+
+ @Override
+ protected boolean matchesSafely(Collection<?> collection) {
+ return collection.size() == expectedSize;
+ }
+
+ @Override
+ public void describeTo(Description description) {
+ description.appendText("a collection with size
").appendValue(expectedSize);
+ }
+
+ @Override
+ protected void describeMismatchSafely(Collection<?> collection,
Description description) {
+ description.appendText("size was ").appendValue(collection.size())
+ .appendText(", contents: ").appendValue(collection);
+ }
+
+ public static HasSize hasSize(int size) {
+ return new HasSize(size);
+ }
+}
diff --git
a/systests/tracing/src/test/java/org/apache/cxf/systest/jaxrs/tracing/opentelemetry/JaxrsOpenTelemetryTracingTest.java
b/systests/tracing/src/test/java/org/apache/cxf/systest/jaxrs/tracing/opentelemetry/JaxrsOpenTelemetryTracingTest.java
index 0ca554c9752..4c8eed86d20 100644
---
a/systests/tracing/src/test/java/org/apache/cxf/systest/jaxrs/tracing/opentelemetry/JaxrsOpenTelemetryTracingTest.java
+++
b/systests/tracing/src/test/java/org/apache/cxf/systest/jaxrs/tracing/opentelemetry/JaxrsOpenTelemetryTracingTest.java
@@ -81,6 +81,7 @@ import org.junit.Rule;
import org.junit.Test;
import org.junit.rules.ExpectedException;
+import static org.apache.cxf.systest.HasSize.hasSize;
import static
org.apache.cxf.systest.jaxrs.tracing.opentelemetry.HasAttribute.hasAttribute;
import static
org.apache.cxf.systest.jaxrs.tracing.opentelemetry.HasSpan.hasSpan;
import static
org.apache.cxf.systest.jaxrs.tracing.opentelemetry.IsLogContaining.hasItem;
@@ -258,10 +259,9 @@ public class JaxrsOpenTelemetryTracingTest extends
AbstractClientServerTestBase
final Response r =
withTrace(createWebClient("/bookstore/books/async")).get();
assertEquals(Status.OK.getStatusCode(), r.getStatus());
- await().atMost(Duration.ofSeconds(1L)).until(() ->
otelRule.getSpans().size() == 2);
+ await().atMost(Duration.ofSeconds(5L)).untilAsserted(() ->
assertThat(otelRule.getSpans(), hasSize(2)));
final List<SpanData> spans = getSpansSorted();
- assertThat(spans.size(), equalTo(2));
assertEquals("Processing books", spans.get(0).getName());
assertEquals("GET /bookstore/books/async", spans.get(1).getName());
@@ -288,10 +288,9 @@ public class JaxrsOpenTelemetryTracingTest extends
AbstractClientServerTestBase
final Response r = createWebClient("/bookstore/books/async").get();
assertEquals(Status.OK.getStatusCode(), r.getStatus());
- await().atMost(Duration.ofSeconds(1L)).until(() ->
otelRule.getSpans().size() == 2);
+ await().atMost(Duration.ofSeconds(5L)).untilAsserted(() ->
assertThat(otelRule.getSpans(), hasSize(2)));
final List<SpanData> spans = getSpansSorted();
- assertThat(spans.size(), equalTo(2));
assertThat(spans.get(0).getName(), equalTo("Processing books"));
assertThat(spans.get(1).getName(), equalTo("GET
/bookstore/books/async"));
}
@@ -304,9 +303,8 @@ public class JaxrsOpenTelemetryTracingTest extends
AbstractClientServerTestBase
final Response r = client.async().get().get(1L, TimeUnit.SECONDS);
assertEquals(Status.OK.getStatusCode(), r.getStatus());
- await().atMost(Duration.ofSeconds(1L)).until(() ->
otelRule.getSpans().size() == 3);
+ await().atMost(Duration.ofSeconds(5L)).untilAsserted(() ->
assertThat(otelRule.getSpans(), hasSize(3)));
- assertThat(otelRule.getSpans().size(), equalTo(3));
assertThat(otelRule.getSpans().get(0).getName(), equalTo("Get Books"));
assertThat(otelRule.getSpans().get(1).getName(), equalTo("GET
/bookstore/books"));
assertThat(otelRule.getSpans().get(1).getKind(),
equalTo(SpanKind.SERVER));
@@ -374,9 +372,8 @@ public class JaxrsOpenTelemetryTracingTest extends
AbstractClientServerTestBase
}
// Await till flush happens, usually every second
- await().atMost(Duration.ofSeconds(1L)).until(() ->
otelRule.getSpans().size() == 4);
+ await().atMost(Duration.ofSeconds(5L)).untilAsserted(() ->
assertThat(otelRule.getSpans(), hasSize(4)));
- assertThat(otelRule.getSpans().size(), equalTo(4));
assertThat(otelRule.getSpans().get(3).getName(), equalTo("test span"));
assertThat(otelRule.getSpans().get(3).getParentSpanContext().isValid(),
equalTo(false));
}
@@ -393,9 +390,8 @@ public class JaxrsOpenTelemetryTracingTest extends
AbstractClientServerTestBase
assertThat(Span.current().getSpanContext().getSpanId(),
equalTo(span.getSpanContext().getSpanId()));
- await().atMost(Duration.ofSeconds(1L)).until(() ->
otelRule.getSpans().size() == 3);
+ await().atMost(Duration.ofSeconds(5L)).untilAsserted(() ->
assertThat(otelRule.getSpans(), hasSize(3)));
- assertThat(otelRule.getSpans().size(), equalTo(3));
assertThat(otelRule.getSpans().get(0).getName(), equalTo("Get
Books"));
assertThat(otelRule.getSpans().get(0).getParentSpanContext(),
notNullValue());
assertThat(otelRule.getSpans().get(1).getName(), equalTo("GET
/bookstore/books"));
@@ -407,9 +403,8 @@ public class JaxrsOpenTelemetryTracingTest extends
AbstractClientServerTestBase
}
// Await till flush happens, usually every second
- await().atMost(Duration.ofSeconds(1L)).until(() ->
otelRule.getSpans().size() == 4);
+ await().atMost(Duration.ofSeconds(5L)).untilAsserted(() ->
assertThat(otelRule.getSpans(), hasSize(4)));
- assertThat(otelRule.getSpans().size(), equalTo(4));
assertThat(otelRule.getSpans().get(3).getName(), equalTo("test span"));
assertThat(otelRule.getSpans().get(3).getParentSpanContext().isValid(),
equalTo(false));
}
@@ -444,8 +439,7 @@ public class JaxrsOpenTelemetryTracingTest extends
AbstractClientServerTestBase
try {
client.get();
} finally {
- await().atMost(Duration.ofSeconds(1L)).until(() ->
otelRule.getSpans().size() == 2);
- assertThat(otelRule.getSpans().toString(),
otelRule.getSpans().size(), equalTo(2));
+ await().atMost(Duration.ofSeconds(5L)).untilAsserted(() ->
assertThat(otelRule.getSpans(), hasSize(2)));
assertThat(otelRule.getSpans().get(0).getName(), equalTo("GET " +
client.getCurrentURI()));
assertThat(otelRule.getSpans().get(0).getStatus().getStatusCode(),
equalTo(StatusCode.ERROR));
assertThat(otelRule.getSpans().get(1).getName(), equalTo("GET
/bookstore/books/long"));
diff --git
a/systests/tracing/src/test/java/org/apache/cxf/systest/jaxrs/tracing/opentracing/JaxrsOpenTracingTracingTest.java
b/systests/tracing/src/test/java/org/apache/cxf/systest/jaxrs/tracing/opentracing/JaxrsOpenTracingTracingTest.java
index d63f498e627..50c006889c1 100644
---
a/systests/tracing/src/test/java/org/apache/cxf/systest/jaxrs/tracing/opentracing/JaxrsOpenTracingTracingTest.java
+++
b/systests/tracing/src/test/java/org/apache/cxf/systest/jaxrs/tracing/opentracing/JaxrsOpenTracingTracingTest.java
@@ -72,6 +72,7 @@ import org.junit.Rule;
import org.junit.Test;
import org.junit.rules.ExpectedException;
+import static org.apache.cxf.systest.HasSize.hasSize;
import static org.apache.cxf.systest.jaxrs.tracing.opentracing.HasSpan.hasSpan;
import static
org.apache.cxf.systest.jaxrs.tracing.opentracing.IsLogContaining.hasItem;
import static
org.apache.cxf.systest.jaxrs.tracing.opentracing.IsTagContaining.hasItem;
@@ -201,10 +202,9 @@ public class JaxrsOpenTracingTracingTest extends
AbstractClientServerTestBase {
final Response r =
withTrace(createWebClient("/bookstore/books/async"), spanId).get();
assertEquals(Status.OK.getStatusCode(), r.getStatus());
- await().atMost(Duration.ofSeconds(1L)).until(()->
REPORTER.getSpans().size() == 2);
+ await().atMost(Duration.ofSeconds(5L)).untilAsserted(() ->
assertThat(REPORTER.getSpans(), hasSize(2)));
final List<JaegerSpan> spans = getSpansSorted();
- assertThat(spans.size(), equalTo(2));
assertEquals("Processing books", spans.get(0).getOperationName());
assertEquals("GET /bookstore/books/async",
spans.get(1).getOperationName());
assertThat(spans.get(1).getReferences(), not(empty()));
@@ -228,10 +228,9 @@ public class JaxrsOpenTracingTracingTest extends
AbstractClientServerTestBase {
final Response r = createWebClient("/bookstore/books/async").get();
assertEquals(Status.OK.getStatusCode(), r.getStatus());
- await().atMost(Duration.ofSeconds(1L)).until(()->
REPORTER.getSpans().size() == 2);
+ await().atMost(Duration.ofSeconds(5L)).untilAsserted(() ->
assertThat(REPORTER.getSpans(), hasSize(2)));
final List<JaegerSpan> spans = getSpansSorted();
- assertThat(spans.size(), equalTo(2));
assertThat(spans.get(0).getOperationName(), equalTo("Processing
books"));
assertThat(spans.get(1).getOperationName(), equalTo("GET
/bookstore/books/async"));
}
@@ -243,9 +242,8 @@ public class JaxrsOpenTracingTracingTest extends
AbstractClientServerTestBase {
final Response r = client.async().get().get(1L, TimeUnit.SECONDS);
assertEquals(Status.OK.getStatusCode(), r.getStatus());
- await().atMost(Duration.ofSeconds(1L)).until(()->
REPORTER.getSpans().size() == 3);
+ await().atMost(Duration.ofSeconds(5L)).untilAsserted(() ->
assertThat(REPORTER.getSpans(), hasSize(3)));
- assertThat(REPORTER.getSpans().size(), equalTo(3));
assertThat(REPORTER.getSpans().get(0).getOperationName(), equalTo("Get
Books"));
assertThat(REPORTER.getSpans().get(1).getOperationName(), equalTo("GET
/bookstore/books"));
assertThat(REPORTER.getSpans().get(1).getTags(),
hasItem(Tags.SPAN_KIND.getKey(), Tags.SPAN_KIND_SERVER));
@@ -327,9 +325,8 @@ public class JaxrsOpenTracingTracingTest extends
AbstractClientServerTestBase {
}
// Await till flush happens, usually every second
- await().atMost(Duration.ofSeconds(1L)).until(()->
REPORTER.getSpans().size() == 4);
+ await().atMost(Duration.ofSeconds(5L)).untilAsserted(() ->
assertThat(REPORTER.getSpans(), hasSize(4)));
- assertThat(REPORTER.getSpans().size(), equalTo(4));
assertThat(REPORTER.getSpans().get(3).getOperationName(),
equalTo("test span"));
assertThat(REPORTER.getSpans().get(3).getReferences(), empty());
}
@@ -344,9 +341,8 @@ public class JaxrsOpenTracingTracingTest extends
AbstractClientServerTestBase {
assertEquals(Status.OK.getStatusCode(), r.getStatus());
assertThat(tracer.activeSpan().context(), equalTo(span.context()));
- await().atMost(Duration.ofSeconds(1L)).until(()->
REPORTER.getSpans().size() == 3);
+ await().atMost(Duration.ofSeconds(5L)).untilAsserted(() ->
assertThat(REPORTER.getSpans(), hasSize(3)));
- assertThat(REPORTER.getSpans().size(), equalTo(3));
assertThat(REPORTER.getSpans().get(0).getOperationName(),
equalTo("Get Books"));
assertThat(REPORTER.getSpans().get(0).getReferences(),
not(empty()));
assertThat(REPORTER.getSpans().get(1).getOperationName(),
equalTo("GET /bookstore/books"));
@@ -358,9 +354,8 @@ public class JaxrsOpenTracingTracingTest extends
AbstractClientServerTestBase {
}
// Await till flush happens, usually every second
- await().atMost(Duration.ofSeconds(1L)).until(()->
REPORTER.getSpans().size() == 4);
+ await().atMost(Duration.ofSeconds(5L)).untilAsserted(() ->
assertThat(REPORTER.getSpans(), hasSize(4)));
- assertThat(REPORTER.getSpans().size(), equalTo(4));
assertThat(REPORTER.getSpans().get(3).getOperationName(),
equalTo("test span"));
assertThat(REPORTER.getSpans().get(3).getReferences(), empty());
}
@@ -393,8 +388,7 @@ public class JaxrsOpenTracingTracingTest extends
AbstractClientServerTestBase {
try {
client.get();
} finally {
- await().atMost(Duration.ofSeconds(1L)).until(()->
REPORTER.getSpans().size() == 2);
- assertThat(REPORTER.getSpans().toString(),
REPORTER.getSpans().size(), equalTo(2));
+ await().atMost(Duration.ofSeconds(5L)).untilAsserted(() ->
assertThat(REPORTER.getSpans(), hasSize(2)));
assertThat(REPORTER.getSpans().get(0).getOperationName(),
equalTo("GET " + client.getCurrentURI()));
assertThat(REPORTER.getSpans().get(0).getTags(),
hasItem(Tags.ERROR.getKey(), Boolean.TRUE));
assertThat(REPORTER.getSpans().get(1).getOperationName(),
equalTo("GET /bookstore/books/long"));
diff --git
a/systests/tracing/src/test/java/org/apache/cxf/systest/jaxws/tracing/opentelemetry/JaxwsOpenTelemetryTracingTest.java
b/systests/tracing/src/test/java/org/apache/cxf/systest/jaxws/tracing/opentelemetry/JaxwsOpenTelemetryTracingTest.java
index d71ea64b51e..7ba35543372 100644
---
a/systests/tracing/src/test/java/org/apache/cxf/systest/jaxws/tracing/opentelemetry/JaxwsOpenTelemetryTracingTest.java
+++
b/systests/tracing/src/test/java/org/apache/cxf/systest/jaxws/tracing/opentelemetry/JaxwsOpenTelemetryTracingTest.java
@@ -67,6 +67,7 @@ import org.junit.BeforeClass;
import org.junit.ClassRule;
import org.junit.Test;
+import static org.apache.cxf.systest.HasSize.hasSize;
import static
org.apache.cxf.systest.jaxrs.tracing.opentelemetry.HasAttribute.hasAttribute;
import static org.awaitility.Awaitility.await;
import static org.hamcrest.CoreMatchers.containsString;
@@ -248,9 +249,8 @@ public class JaxwsOpenTelemetryTracingTest extends
AbstractClientServerTestBase
}
// Await till flush happens, usually every second
- await().atMost(Duration.ofSeconds(1L)).until(() ->
otelRule.getSpans().size() == 4);
+ await().atMost(Duration.ofSeconds(5L)).untilAsserted(() ->
assertThat(otelRule.getSpans(), hasSize(4)));
- assertThat(otelRule.getSpans().size(), equalTo(4));
assertThat(otelRule.getSpans().get(3).getName(), equalTo("test
span"));
assertThat(otelRule.getSpans().get(3).getParentSpanContext().isValid(),
equalTo(false));
}
@@ -332,7 +332,7 @@ public class JaxwsOpenTelemetryTracingTest extends
AbstractClientServerTestBase
service.orderBooks();
// Await till flush happens, usually every second
- await().atMost(Duration.ofSeconds(1L)).until(() ->
otelRule.getSpans().size() == 2);
+ await().atMost(Duration.ofSeconds(5L)).untilAsserted(() ->
assertThat(otelRule.getSpans(), hasSize(2)));
assertThat(otelRule.getSpans().get(0).getName(), equalTo("POST
/BookStore"));
assertThat(otelRule.getSpans().get(1).getName(),
diff --git
a/systests/tracing/src/test/java/org/apache/cxf/systest/jaxws/tracing/opentracing/JaxwsOpenTracingTracingTest.java
b/systests/tracing/src/test/java/org/apache/cxf/systest/jaxws/tracing/opentracing/JaxwsOpenTracingTracingTest.java
index 1027dcf6c3f..8e9c291fa27 100644
---
a/systests/tracing/src/test/java/org/apache/cxf/systest/jaxws/tracing/opentracing/JaxwsOpenTracingTracingTest.java
+++
b/systests/tracing/src/test/java/org/apache/cxf/systest/jaxws/tracing/opentracing/JaxwsOpenTracingTracingTest.java
@@ -58,6 +58,7 @@ import org.junit.After;
import org.junit.BeforeClass;
import org.junit.Test;
+import static org.apache.cxf.systest.HasSize.hasSize;
import static
org.apache.cxf.systest.jaxrs.tracing.opentracing.IsTagContaining.hasItem;
import static org.awaitility.Awaitility.await;
import static org.hamcrest.CoreMatchers.equalTo;
@@ -179,9 +180,8 @@ public class JaxwsOpenTracingTracingTest extends
AbstractClientServerTestBase {
}
// Await till flush happens, usually every second
- await().atMost(Duration.ofSeconds(1L)).until(()->
REPORTER.getSpans().size() == 4);
+ await().atMost(Duration.ofSeconds(5L)).untilAsserted(() ->
assertThat(REPORTER.getSpans(), hasSize(4)));
- assertThat(REPORTER.getSpans().size(), equalTo(4));
assertThat(REPORTER.getSpans().get(3).getOperationName(),
equalTo("test span"));
assertThat(REPORTER.getSpans().get(3).getReferences(), empty());
}
@@ -235,7 +235,7 @@ public class JaxwsOpenTracingTracingTest extends
AbstractClientServerTestBase {
service.orderBooks();
// Await till flush happens, usually every second
- await().atMost(Duration.ofSeconds(1L)).until(() ->
REPORTER.getSpans().size() == 2);
+ await().atMost(Duration.ofSeconds(5L)).untilAsserted(() ->
assertThat(REPORTER.getSpans(), hasSize(2)));
assertThat(REPORTER.getSpans().get(0).getOperationName(),
equalTo("POST /BookStore"));
assertThat(REPORTER.getSpans().get(1).getOperationName(),