getsentry / sentry-dotnet

Sentry SDK for .NET
https://docs.sentry.io/platforms/dotnet
MIT License
604 stars 206 forks source link

Exception on shutdown when using Sentry & OpenTelemetry #3724

Closed petedishman closed 3 weeks ago

petedishman commented 3 weeks ago

Package

Other

.NET Flavor

.NET Core

.NET Version

8.0.0

OS

Any (not platform specific)

SDK Version

4.12.1

Self-Hosted Sentry Version

No response

Steps to Reproduce

I have a minimal repo available at https://github.com/petedishman/SentryShutdownBug

This is a minimal aspnetcore app configured with Sentry & OpenTelemetry together

Can repro the issue with:

  1. clone the above repo
  2. configure a Sentry DSN in program.cs
  3. Run the app with dotnet run
  4. Browse to http://localhost:5005
  5. Close the app with CTRL+C
  6. exception should be logged

It appears to be dependent on the TracesSampleRate setting and this needs to be discarding traces for the error to occur, otherwise if it's set to 1.0 it will exit without error.

Expected Result

Application should shutdown without an exception being thrown

Actual Result

This exception is logged, then app continues to shutdown

fail: Sentry.ISentryClient[0]
      Error while sending final client report (event ID: '(null)').
      System.InvalidCastException: Unable to cast object of type 'Sentry.Internal.NoOpTransaction' to type 'Sentry.TransactionTracer'.
         at Sentry.OpenTelemetry.SentrySpanProcessor.CreateRootSpan(Activity data)
         at Sentry.OpenTelemetry.SentrySpanProcessor.OnStart(Activity data)
         at OpenTelemetry.CompositeProcessor`1.OnStart(T data)
         at OpenTelemetry.Trace.TracerProviderSdk.<.ctor>b__12_1(Activity activity)
         at System.Diagnostics.SynchronizedList`1.EnumWithAction(Action`2 action, Object arg)
         at System.Diagnostics.Activity.Start()
         at System.Net.Http.DiagnosticsHandler.SendAsyncCore(HttpRequestMessage request, Boolean async, CancellationToken cancellationToken)
         at System.Net.Http.RedirectHandler.SendAsync(HttpRequestMessage request, Boolean async, CancellationToken cancellationToken)
         at System.Net.Http.DecompressionHandler.SendAsync(HttpRequestMessage request, Boolean async, CancellationToken cancellationToken)
         at Sentry.Internal.Http.GzipBufferedRequestBodyHandler.SendAsync(HttpRequestMessage request, CancellationToken cancellationToken)
         at Sentry.Internal.Http.RetryAfterHandler.SendAsync(HttpRequestMessage request, CancellationToken cancellationToken)
         at System.Net.Http.HttpClient.<SendAsync>g__Core|83_0(HttpRequestMessage request, HttpCompletionOption completionOption, CancellationTokenSource cts, Boolean disposeCts, CancellationTokenSource pendingRequestsCts, CancellationToken originalCancellationToken)
         at Sentry.Internal.Http.HttpTransport.SendEnvelopeAsync(Envelope envelope, CancellationToken cancellationToken)
         at Sentry.Internal.BackgroundWorker.SendFinalClientReportAsync(CancellationToken cancellationToken)
jamescrosswell commented 3 weeks ago

Hi @petedishman , thank you for putting together repo demonstrating the issue ❤

I can confirm that I can reproduce this... I'll do a bit of digging to see if I can work out why it's happening.

petedishman commented 3 weeks ago

Excellent, thanks @jamescrosswell