Skip to content

Add instrumentation for quarkus-rest-client-reactive (MicroProfile REST Client 3.0+)#11495

Draft
dougqh wants to merge 1 commit into
masterfrom
feat/quarkus-rest-client-reactive-instrumentation
Draft

Add instrumentation for quarkus-rest-client-reactive (MicroProfile REST Client 3.0+)#11495
dougqh wants to merge 1 commit into
masterfrom
feat/quarkus-rest-client-reactive-instrumentation

Conversation

@dougqh
Copy link
Copy Markdown
Contributor

@dougqh dougqh commented May 28, 2026

Summary

  • Adds a new instrumentation module quarkus-rest-client-reactive-3.0 that intercepts RestClientBuilder.build(Class<?>) and registers a ClientRequestFilter to automatically inject Datadog and W3C trace propagation headers on every outbound REST call
  • Fixes the trace disconnection reported in APMS-19646 / APMS-19675 for customers using quarkus-rest-client-reactive in multi-service Quarkus stacks
  • Targets MicroProfile REST Client 3.0+ (jakarta namespace, Quarkus 3.x JVM mode); a parallel module for Quarkus 2.x (javax namespace) follows the same pattern

Implementation

The hook is RestClientBuilder.build(Class<?>) — the single point where all MicroProfile REST clients are finalized. Before the proxy is built, QuarkusRestClientTracingFilter.class is registered on the builder via ForTypeHierarchy advice. That filter fires on every outbound request to start an HTTP client span (component: quarkus-rest-client-reactive) and finish it on response.

CXF/SOAP propagation already works in the same Quarkus binary because CXF routes through HttpURLConnection, which we instrument at the connection level. quarkus-rest-client-reactive (RESTEasy Reactive → Vert.x HTTP Client) does not cross that instrumented path, hence the gap this PR closes.

Scope / known limitations

  • JVM mode only in this PR. GraalVM native requires Quarkus build-time reflection config for the filter class; that is tracked separately
  • Quarkus 2.x (javax namespace, MicroProfile REST Client < 3.0) is not covered here but can be added with an identical module swapping jakarta.* imports for javax.*

Test plan

  • Unit tests pass (QuarkusRestClientInstrumentationTest — 2 JUnit 5 tests using RESTEasy MicroProfile client + JDK HttpServer): verify x-datadog-trace-id / x-datadog-parent-id headers are injected and a span is created per request
  • ./gradlew :dd-java-agent:instrumentation:quarkus:quarkus-rest-client-reactive-3.0:test passes locally
  • Muzzle check configured against microprofile-rest-client-api ≥ 3.0
  • Manual validation against dd-smoke-tests/quarkus recommended before merge

Labels

comp:java-tracer, inst:quarkus, type:feature, tag:ai generated

🤖 Generated with Claude Code

…VM, MicroProfile REST Client 3.0+)

Intercepts RestClientBuilder.build(Class<?>) to register a ClientRequestFilter that starts an
HTTP client span and injects Datadog + W3C propagation headers on every outbound REST call.
Fixes trace disconnection seen when quarkus-rest-client-reactive is used in multi-service Quarkus
stacks (APMS-19675 / APMS-19646).

Scope: MicroProfile REST Client 3.0+ (jakarta namespace, Quarkus 3.x JVM mode). A separate
module targeting MicroProfile REST Client 2.x (javax namespace, Quarkus 2.x) can follow the
same pattern. GraalVM native support requires companion build-time configuration.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
@dd-octo-sts
Copy link
Copy Markdown
Contributor

dd-octo-sts Bot commented May 28, 2026

🟢 Java Benchmark SLOs — All performance SLOs passed

Suite Status
Startup 🟢 pass

SLO thresholds are defined here based on automatically generated metrics. A warning is raised when results are within 5% of the threshold.

PR vs. master results

Startup Time

Scenario This PR master Change
insecure-bank / iast 13,982 ms 13,960 ms +0.2%
insecure-bank / tracing 12,957 ms 12,985 ms -0.2%
petclinic / appsec 16,639 ms 16,259 ms +2.3%
petclinic / iast 16,560 ms 16,538 ms +0.1%
petclinic / profiling 16,543 ms 16,530 ms +0.1%
petclinic / tracing 15,786 ms 15,863 ms -0.5%

Commit: 5a176fad · CI Pipeline · Benchmarking Platform UI


Load and DaCapo benchmarks can be triggered manually in the GitLab pipeline. Results will appear in the Benchmarking Platform UI after completion.

@datadog-datadog-prod-us1
Copy link
Copy Markdown
Contributor

datadog-datadog-prod-us1 Bot commented May 28, 2026

Pipelines

Fix all issues with BitsAI

⚠️ Warnings

🚦 4 Pipeline jobs failed

DataDog/apm-reliability/dd-trace-java | muzzle: [3/8]   View in Datadog   GitLab

🔧 Fix in code (Fix with Cursor). Muzzle validation failed during instrumentation.

DataDog/apm-reliability/dd-trace-java | test_inst_latest: [8, 3/6]   View in Datadog   GitLab

🔧 Fix in code (Fix with Cursor). 8 tests failed due to initialization errors: Unable to find annotations of UnknownClass.

DataDog/apm-reliability/dd-trace-java | config-inversion-linter   View in Datadog   GitLab

🛟 This job is unlikely to succeed on retry. Please review your pipeline configuration. Decorator instrumentation entries missing from SUPPORTED or ALIASES in supported-configurations.json during validation.

View all 4 failed jobs.

Useful? React with 👍 / 👎

This comment will be updated automatically if new data arrives.
🔗 Commit SHA: 5a176fa | Docs | Datadog PR Page | Give us feedback!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant