Skip to content

RUM-17709: Apply remote configuration to Trace module at SDK instance ready - #3663

Merged
hamorillo merged 3 commits into
feature/remote-configfrom
hector.morilloprieto/RUM-17709
Jul 27, 2026
Merged

RUM-17709: Apply remote configuration to Trace module at SDK instance ready#3663
hamorillo merged 3 commits into
feature/remote-configfrom
hector.morilloprieto/RUM-17709

Conversation

@hamorillo

@hamorillo hamorillo commented Jul 23, 2026

Copy link
Copy Markdown
Contributor

What does this PR do?

Applies the RC trace namespace to both Android tracing paths when the SDK instance becomes available:

  • Commit 1 — introduces TraceRemoteConfigExt.kt (shared helpers: applyRcSampleRate(), toSdkInjection(), buildRcHostResolver()) and wires RC into TracingInterceptor.onSdkInstanceReady()
  • Commit 2 — wires RC into ApmNetworkInstrumentation.onSdkInstanceReady() (the modern OkHttp/Cronet path)

RC is applied once per interceptor lifetime, guarded by AtomicBoolean.compareAndSet, on both the legacy (TracingInterceptor/DatadogInterceptor) and modern (ApmNetworkInstrumentation) paths.

Motivation

RUM-17709 — applies the RC trace namespace on Android. Mirrors the iOS implementation in dd-sdk-ios#3047.

Additional Notes

RC fields mapped from RemoteConfiguration.Trace:

RC field Effect on both paths
trace.sampleRate Replaces traceSampler with DeterministicTraceSampler(rcRate); preserves SessionRebasedSampler wrapper when present (used by DatadogInterceptor for RUM × APM cross-product rebasing)
trace.traceContextInjection Updates traceContextInjection / injectionType
trace.tracedHosts + trace.tracingHeaderTypes Replaces localFirstPartyHostHeaderTypeResolver via buildRcHostResolver(). Semantics mirror iOS PR #3047: null → no-op; [] → clear hosts; non-empty → replace

propagatorTypes / tracingHeaderTypes semantics (matching iOS):

  • null (absent) → fall back to global types / SDK default
  • [] (explicit empty list) → no headers for that host / no global fallback — not treated as absent

Review checklist (to be filled by reviewers)

  • Feature or bugfix MUST have appropriate tests (unit, integration, e2e)
  • Make sure you discussed the feature or bugfix with the maintaining team in an Issue
  • Make sure each commit and the PR mention the Issue number (cf the CONTRIBUTING doc)

@hamorillo

Copy link
Copy Markdown
Contributor Author

@codex review

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 9ae030be9e

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment on lines +70 to +71
if (rcHosts.isEmpty()) {
return DefaultFirstPartyHostHeaderTypeResolver(emptyMap())

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Honor empty RC host lists over global hosts

When RC sends an explicit empty tracedHosts, this only clears the local resolver. Requests can still be traced through sdkCore.firstPartyHostResolver: both trace paths check the global resolver for traceability and fall back to its headerTypesForUrl(...) when the local set is empty, so apps that configured global first-party hosts keep creating spans and propagating headers even though the RC payload is intended to replace/clear developer hosts. Please make a present RC host list authoritative, or skip the global resolver fallback for this instrumentation once RC has supplied tracedHosts.

Useful? React with 👍 / 👎.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is different from the iOS SDK, which doesn't have a global firstPartyHostResolver concept — all host configuration lives directly on Trace.Configuration. If we want RC to also control global first-party hosts on Android, that would need a dedicated Android-specific RC field. For now, tracedHosts correctly controls the per-interceptor local resolver as intended.

@codecov-commenter

codecov-commenter commented Jul 23, 2026

Copy link
Copy Markdown

Codecov Report

❌ Patch coverage is 89.13043% with 5 lines in your changes missing coverage. Please review.
⚠️ Please upload report for BASE (feature/remote-config@d6c4f82). Learn more about missing BASE report.
⚠️ Report is 2 commits behind head on feature/remote-config.

Files with missing lines Patch % Lines
...dog/android/trace/internal/TraceRemoteConfigExt.kt 88.00% 0 Missing and 3 partials ⚠️
...ndroid/trace/internal/ApmNetworkInstrumentation.kt 90.91% 0 Missing and 1 partial ⚠️
...datadog/android/okhttp/trace/TracingInterceptor.kt 90.00% 0 Missing and 1 partial ⚠️
Additional details and impacted files
@@                   Coverage Diff                    @@
##             feature/remote-config    #3663   +/-   ##
========================================================
  Coverage                         ?   73.47%           
========================================================
  Files                            ?     1002           
  Lines                            ?    36572           
  Branches                         ?     6195           
========================================================
  Hits                             ?    26869           
  Misses                           ?     7982           
  Partials                         ?     1721           
Files with missing lines Coverage Δ
...ndroid/trace/internal/ApmNetworkInstrumentation.kt 64.34% <90.91%> (ø)
...datadog/android/okhttp/trace/TracingInterceptor.kt 83.29% <90.00%> (ø)
...dog/android/trace/internal/TraceRemoteConfigExt.kt 88.00% <88.00%> (ø)
🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.

@hamorillo
hamorillo force-pushed the hector.morilloprieto/RUM-17709 branch from 9ae030b to 6e16895 Compare July 23, 2026 15:30
@hamorillo
hamorillo marked this pull request as ready for review July 24, 2026 06:05
@hamorillo
hamorillo requested review from a team as code owners July 24, 2026 06:05

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 6e16895354

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment on lines +81 to +83
val types = tracedHost.propagatorTypes
?.map { it.toSdkHeaderType() }
?.toSet()

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Preserve authoritative empty RC propagators

When RC sends a traced host with propagatorTypes: [], these lines store an empty header set. The downstream injection paths (ApmNetworkInstrumentation.traceRequest and TracingInterceptor.updateRequest) treat an empty local header set as “no local match” via .ifEmpty { sdkCore.firstPartyHostResolver.headerTypesForUrl(...) }, so apps that also configured the same host globally still inject those global headers even though the RC payload explicitly asked for no propagators. Fresh evidence is the new test/comment that defines empty propagatorTypes as “trace host with no headers”; please carry an authoritative/no-fallback state instead of representing it as an empty set.

Useful? React with 👍 / 👎.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is similar to #3663 (comment). I would say that If we want RC to suppress global header injection for a host, that would require a dedicated Android-specific approach. For now, propagatorTypes: [] correctly controls the per-interceptor local resolver as intended.

@sbarrio
sbarrio requested a review from jonathanmos July 24, 2026 07:07
jonathanmos
jonathanmos previously approved these changes Jul 27, 2026
Comment thread detekt_custom_safe_calls_third_party.yml Outdated
@hamorillo
hamorillo merged commit 0087107 into feature/remote-config Jul 27, 2026
26 checks passed
@hamorillo
hamorillo deleted the hector.morilloprieto/RUM-17709 branch July 27, 2026 12:35
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.

4 participants