Skip to content

feat(server-utils): Add tracingChannel-to-span binding#21641

Draft
logaretm wants to merge 3 commits into
developfrom
awad/bind-tracing-channel
Draft

feat(server-utils): Add tracingChannel-to-span binding#21641
logaretm wants to merge 3 commits into
developfrom
awad/bind-tracing-channel

Conversation

@logaretm

@logaretm logaretm commented Jun 18, 2026

Copy link
Copy Markdown
Member

This abstracts away our tracing channels consumption into a utility that:

  • Activates a span for the tracing channel lifecycle
  • Manages the span across the entire lifecycle
    • Sets errors on the error channel
    • Correctly ends the span at the correct timing whether the traced call is sync or async
  • Allows span/error enrichment and overrides

This util can be consumed uniformly across all of our server-side runtimes, I will create a stacked PR that refactors our code to use it, showcasing Nitro, Redis, and Deno adoption of that util.

Lifecycle Management

After testing across several node releases (20 -> 26), I locked down the strategy that we can rely on to make this reliable and predictable.

  1. always start at start lifecycle event, this is emitted always and is reliable.
  2. Use error For capturing exceptions and setting error span status, always reliable.
  3. When end is emitted:
    1. If error is present on the context object, end the span immediatly, there won’t be any async events coming up, the function threw in the sync part, so there is no async part to execute.
    2. If result is present on the context object, end the span immediately, there won’t be any async events coming up. The function returned in the sync part or is sync trace itself. Use in or hasOwnProperty , Do not use undefined checks as the function can return nothing.
    3. Otherwise NO-OP, there is an async lifecycle events coming up.
  4. When asyncStart is emitted: Do nothing, this event has no value for us.
  5. When asyncEnd is emitted: Just end the span.

logaretm added 2 commits June 18, 2026 13:56
Add `bindTracingChannelToSpan` to generalize Node `diagnostics_channel`
TracingChannel instrumentation onto Sentry spans. It binds the active
span into async context on `start` and, in the default `auto` lifecycle,
ends the span on the canonical terminal event: `end` for synchronous
calls (detected via presence of `result`/`error` on the context object)
and `asyncEnd` for async calls, recording exceptions on `error`.

Backed by a new `getTracingChannelBinding` async context strategy hook
wired through core, node-core, opentelemetry, cloudflare, and deno.
@logaretm logaretm force-pushed the awad/bind-tracing-channel branch from 8c4ca47 to 61a560f Compare June 18, 2026 17:56
@github-actions

github-actions Bot commented Jun 18, 2026

Copy link
Copy Markdown
Contributor

size-limit report 📦

Path Size % Change Change
@sentry/browser 27.45 kB - -
@sentry/browser - with treeshaking flags 25.88 kB - -
@sentry/browser (incl. Tracing) 45.89 kB - -
@sentry/browser (incl. Tracing + Span Streaming) 48.12 kB - -
@sentry/browser (incl. Tracing, Profiling) 50.67 kB - -
@sentry/browser (incl. Tracing, Replay) 85.08 kB - -
@sentry/browser (incl. Tracing, Replay) - with treeshaking flags 74.69 kB - -
@sentry/browser (incl. Tracing, Replay with Canvas) 89.78 kB - -
@sentry/browser (incl. Tracing, Replay, Feedback) 102.45 kB - -
@sentry/browser (incl. Feedback) 44.62 kB - -
@sentry/browser (incl. sendFeedback) 32.25 kB - -
@sentry/browser (incl. FeedbackAsync) 37.38 kB - -
@sentry/browser (incl. Metrics) 28.52 kB - -
@sentry/browser (incl. Logs) 28.76 kB - -
@sentry/browser (incl. Metrics & Logs) 29.45 kB - -
@sentry/react 29.25 kB - -
@sentry/react (incl. Tracing) 48.18 kB - -
@sentry/vue 32.56 kB - -
@sentry/vue (incl. Tracing) 47.76 kB - -
@sentry/svelte 27.48 kB - -
CDN Bundle 29.86 kB - -
CDN Bundle (incl. Tracing) 48.3 kB - -
CDN Bundle (incl. Logs, Metrics) 31.4 kB - -
CDN Bundle (incl. Tracing, Logs, Metrics) 49.59 kB - -
CDN Bundle (incl. Replay, Logs, Metrics) 70.71 kB - -
CDN Bundle (incl. Tracing, Replay) 85.62 kB - -
CDN Bundle (incl. Tracing, Replay, Logs, Metrics) 86.88 kB - -
CDN Bundle (incl. Tracing, Replay, Feedback) 91.46 kB - -
CDN Bundle (incl. Tracing, Replay, Feedback, Logs, Metrics) 92.72 kB - -
CDN Bundle - uncompressed 88.8 kB - -
CDN Bundle (incl. Tracing) - uncompressed 146.09 kB - -
CDN Bundle (incl. Logs, Metrics) - uncompressed 93.5 kB - -
CDN Bundle (incl. Tracing, Logs, Metrics) - uncompressed 150.06 kB - -
CDN Bundle (incl. Replay, Logs, Metrics) - uncompressed 218.33 kB - -
CDN Bundle (incl. Tracing, Replay) - uncompressed 264.95 kB - -
CDN Bundle (incl. Tracing, Replay, Logs, Metrics) - uncompressed 268.91 kB - -
CDN Bundle (incl. Tracing, Replay, Feedback) - uncompressed 278.65 kB - -
CDN Bundle (incl. Tracing, Replay, Feedback, Logs, Metrics) - uncompressed 282.6 kB - -
@sentry/nextjs (client) 50.58 kB - -
@sentry/sveltekit (client) 46.27 kB - -
@sentry/core/server 76.19 kB +0.04% +25 B 🔺
@sentry/core/browser 63.34 kB +0.04% +23 B 🔺
@sentry/node-core 61.95 kB +0.14% +81 B 🔺
@sentry/node 124.73 kB +0.07% +82 B 🔺
@sentry/node/import (ESM hook with diagnostics-channel injection) 70.05 kB - -
@sentry/node/light 50.98 kB +0.11% +51 B 🔺
@sentry/node - without tracing 74.29 kB +0.08% +55 B 🔺
@sentry/aws-serverless 85.41 kB +0.08% +60 B 🔺
@sentry/cloudflare (withSentry) - minified 174.71 kB +0.13% +226 B 🔺
@sentry/cloudflare (withSentry) 436.97 kB +0.1% +427 B 🔺

View base workflow run

…oSpan

`bindTracingChannelToSpan` now returns a `TracingChannelBindingHandle`
`{ channel, unbind }` instead of the channel directly. `unbind()`
unsubscribes the auto lifecycle handlers and unbinds the start store
(idempotent; a no-op when no async context binding is available), so
callers can detach a binding — useful for teardown and test isolation.
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