Fix base service logic and make it future proof#5510
Fix base service logic and make it future proof#5510
Conversation
|
👋 Hey @DataDog/ruby-guild, please fill "Change log entry" section in the pull request description. If changes need to be present in CHANGELOG.md you can state it this way **Change log entry**
Yes. A brief summary to be placed into the CHANGELOG.md(possible answers Yes/Yep/Yeah) Or you can opt out like that **Change log entry**
None.(possible answers No/Nope/None) Visited at: 2026-03-26 11:29:31 UTC |
Typing analysisNote: Ignored files are excluded from the next sections.
|
BenchmarksBenchmark execution time: 2026-03-26 11:59:04 Comparing candidate commit 4af83bd in PR branch Found 0 performance improvements and 0 performance regressions! Performance is the same for 46 metrics, 0 unstable metrics.
|
67c5108 to
61e0e33
Compare
|
✅ Tests 🎉 All green!❄️ No new flaky tests detected 🎯 Code Coverage (details) 🔗 Commit SHA: 79ce50f | Docs | Datadog PR Page | Was this helpful? React with 👍/👎 or give us feedback! |
raphaelgavache
left a comment
There was a problem hiding this comment.
nice catch, this match other tracer behavior and it's critical to never miss this tag
| stop(end_time) | ||
|
|
||
| # Set _dd.base_service when service overrides the global service | ||
| set_base_service_tag |
There was a problem hiding this comment.
Correct me if I am wrong. The tracing data models do not harbor the knowledge intrinsically, and service is an attribute provided to trace/span models by instrumentations or configurations.
Hence, the logic should be pushed higher and this file should not contains changes.
There was a problem hiding this comment.
For cross product correlation between tracing and other products (profiling/apm telemetry etc) we need this common base service tag to be enforced on all spans and their related stats
There was a problem hiding this comment.
Yes, and the original implementation (see #3018) had two main limitations: it was not fully implemented (e.g., it only covered integrations and not other span APIs), and it was not future-proof (there was no mechanism to automatically enforce it for new integrations).
@TonyCTHsu While it clearly needs to be addressed, suggestions on the most appropriate place to implement this logic are welcome.
In any case, it should be computed before spans are potentially sent to stats (if client-side stats are in scope for Ruby), which is why I placed it here rather than at serialization time for tracing.
There was a problem hiding this comment.
I think where it is today is probably ok, because it's ideal to have a correct span payload when we call build_span in the next line, since the immutable span built in build_span can be used for inspection in the processing pipeline, before the span is sent to the transport.
lib/datadog/tracing/contrib/ext.rb
Outdated
| # Set equal to the global service when contrib span.service is overriden | ||
| TAG_BASE_SERVICE = '_dd.base_service' | ||
| TAG_BASE_SERVICE = Tracing::Metadata::Ext::TAG_BASE_SERVICE |
There was a problem hiding this comment.
This constant is not public, you can delete it.
lib/datadog/tracing/metadata/ext.rb
Outdated
| TAG_APM_ENABLED = '_dd.apm.enabled' | ||
|
|
||
| # Set to the global service name when a span's service is overridden |
There was a problem hiding this comment.
Can we add a brief comment with the reason why we're setting this tag?
If there's a link for what this tag enpowers (e.g. Inferred services
I'm not actually sure if inferred services is the precise feature), that's super great to add here.
What does this PR do?
Moves
_dd.base_servicetag logic from 25 individual integration files intoSpanOperation#finish, making it apply universally to every span in the system.Motivation:
The
_dd.base_servicetag was previously set by copy-pasted boilerplate in each integration. This meant it was absent for spans created via the manual tracing API (e.g.Datadog::Tracing.trace('op', service: 'custom')), if the service name was manually changed, and any new integration had to remember to add it manually. Centralizing inSpanOperation#finishcloses the gap, removes the duplication, and makes future integrations correct by default.Change log entry
Additional Notes:
How to test the change?