Skip to content

Commit

Permalink
feat: Check-In Upserts (#3330)
Browse files Browse the repository at this point in the history
  • Loading branch information
bitsandfoxes committed May 29, 2024
1 parent 6a08235 commit 37eb4a5
Show file tree
Hide file tree
Showing 15 changed files with 482 additions and 44 deletions.
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@

### Features

- The SDK now supports monitor upserting. You can programmatically set up your monitors via the options callback in `SentrySdk.CaptureCheckIn` ([#3330](https://github.com/getsentry/sentry-dotnet/pull/3330))
- Added an `SentrySdk.RunAsyncVoid` helper method that lets you capture exceptions from `async void` methods ([#3379](https://github.com/getsentry/sentry-dotnet/pull/3379))

### Fixes
Expand Down
9 changes: 9 additions & 0 deletions src/Sentry/Extensibility/DiagnosticLoggerExtensions.cs
Original file line number Diff line number Diff line change
Expand Up @@ -252,6 +252,15 @@ public static class DiagnosticLoggerExtensions
string message)
=> logger.LogIfEnabled(SentryLevel.Error, null, message);

/// <summary>
/// Log an error message.
/// </summary>
public static void LogError<TArg>(
this IDiagnosticLogger logger,
string message,
TArg arg)
=> logger.LogIfEnabled(SentryLevel.Error, null, message, arg);

/// <summary>
/// Log an exception with an error message.
/// </summary>
Expand Down
9 changes: 7 additions & 2 deletions src/Sentry/Extensibility/DisabledHub.cs
Original file line number Diff line number Diff line change
Expand Up @@ -183,8 +183,13 @@ public void CaptureSession(SessionUpdate sessionUpdate)
/// <summary>
/// No-Op
/// </summary>
public SentryId CaptureCheckIn(string monitorSlug, CheckInStatus status, SentryId? sentryId = null,
TimeSpan? duration = null, Scope? scope = null)
public SentryId CaptureCheckIn(
string monitorSlug,
CheckInStatus status,
SentryId? sentryId = null,
TimeSpan? duration = null,
Scope? scope = null,
Action<SentryMonitorOptions>? configureMonitorOptions = null)
=> SentryId.Empty;

/// <summary>
Expand Down
11 changes: 8 additions & 3 deletions src/Sentry/Extensibility/HubAdapter.cs
Original file line number Diff line number Diff line change
Expand Up @@ -270,9 +270,14 @@ public void CaptureSession(SessionUpdate sessionUpdate)
/// <summary>
/// Forwards the call to <see cref="SentrySdk"/>.
/// </summary>
public SentryId CaptureCheckIn(string monitorSlug, CheckInStatus status, SentryId? sentryId = null,
TimeSpan? duration = null, Scope? scope = null)
=> SentrySdk.CaptureCheckIn(monitorSlug, status, sentryId, duration);
public SentryId CaptureCheckIn(
string monitorSlug,
CheckInStatus status,
SentryId? sentryId = null,
TimeSpan? duration = null,
Scope? scope = null,
Action<SentryMonitorOptions>? monitorOptions = null)
=> SentrySdk.CaptureCheckIn(monitorSlug, status, sentryId, duration, scope, monitorOptions);

/// <summary>
/// Forwards the call to <see cref="SentrySdk"/>
Expand Down
9 changes: 7 additions & 2 deletions src/Sentry/ISentryClient.cs
Original file line number Diff line number Diff line change
Expand Up @@ -79,8 +79,13 @@ public interface ISentryClient
/// <param name="sentryId"></param>
/// <param name="duration"></param>
/// <param name="scope"></param>
SentryId CaptureCheckIn(string monitorSlug, CheckInStatus status, SentryId? sentryId = null,
TimeSpan? duration = null, Scope? scope = null);
/// <param name="configureMonitorOptions">The optional monitor config used to create a Check-In programmatically.</param>
SentryId CaptureCheckIn(string monitorSlug,
CheckInStatus status,
SentryId? sentryId = null,
TimeSpan? duration = null,
Scope? scope = null,
Action<SentryMonitorOptions>? configureMonitorOptions = null);

/// <summary>
/// Flushes the queue of captured events until the timeout is reached.
Expand Down
10 changes: 7 additions & 3 deletions src/Sentry/Internal/Hub.cs
Original file line number Diff line number Diff line change
Expand Up @@ -561,9 +561,13 @@ public void CaptureSession(SessionUpdate sessionUpdate)
}
}

public SentryId CaptureCheckIn(string monitorSlug, CheckInStatus status, SentryId? sentryId = null,
public SentryId CaptureCheckIn(
string monitorSlug,
CheckInStatus status,
SentryId? sentryId = null,
TimeSpan? duration = null,
Scope? scope = null)
Scope? scope = null,
Action<SentryMonitorOptions>? configureMonitorOptions = null)
{
if (!IsEnabled)
{
Expand All @@ -580,7 +584,7 @@ public void CaptureSession(SessionUpdate sessionUpdate)
scope = currentScope;
}

return _ownedClient.CaptureCheckIn(monitorSlug, status, sentryId, duration, scope);
return _ownedClient.CaptureCheckIn(monitorSlug, status, sentryId, duration, scope, configureMonitorOptions);
}
catch (Exception e)
{
Expand Down
18 changes: 13 additions & 5 deletions src/Sentry/SentryCheckIn.cs
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
namespace Sentry;

/// <summary>
/// The Checkin Status
/// The Check-In Status
/// </summary>
public enum CheckInStatus
{
Expand All @@ -25,13 +25,13 @@ public enum CheckInStatus
}

/// <summary>
/// Sentry Checkin
/// Sentry Check-In
/// </summary>
// https://develop.sentry.dev/sdk/check-ins/
public class SentryCheckIn : ISentryJsonSerializable
{
/// <summary>
/// CheckIn ID
/// Check-In ID
/// </summary>
public SentryId Id { get; }

Expand All @@ -40,13 +40,14 @@ public class SentryCheckIn : ISentryJsonSerializable
/// </summary>
public string MonitorSlug { get; }


/// <summary>
/// The status of the Checkin
/// The status of the Check-In
/// </summary>
public CheckInStatus Status { get; }

/// <summary>
/// The duration of the check-in in seconds. Will only take effect if the status is ok or error.
/// The duration of the Check-In in seconds. Will only take effect if the status is ok or error.
/// </summary>
public TimeSpan? Duration { get; set; }

Expand All @@ -65,6 +66,11 @@ public class SentryCheckIn : ISentryJsonSerializable
/// </summary>
internal SentryId? TraceId { get; set; }

/// <summary>
/// The Monitor Config
/// </summary>
internal SentryMonitorOptions? MonitorOptions { get; set; }

/// <summary>
/// Initializes a new instance of <see cref="SentryCheckIn"/>.
/// </summary>
Expand Down Expand Up @@ -103,6 +109,8 @@ public void WriteTo(Utf8JsonWriter writer, IDiagnosticLogger? logger)
writer.WriteEndObject();
}

MonitorOptions?.WriteTo(writer, logger);

writer.WriteEndObject();
}

Expand Down
17 changes: 15 additions & 2 deletions src/Sentry/SentryClient.cs
Original file line number Diff line number Diff line change
Expand Up @@ -220,7 +220,13 @@ public void CaptureSession(SessionUpdate sessionUpdate)
=> CaptureEnvelope(Envelope.FromSession(sessionUpdate));

/// <inheritdoc />
public SentryId CaptureCheckIn(string monitorSlug, CheckInStatus status, SentryId? sentryId = null, TimeSpan? duration = null, Scope? scope = null)
public SentryId CaptureCheckIn(
string monitorSlug,
CheckInStatus status,
SentryId? sentryId = null,
TimeSpan? duration = null,
Scope? scope = null,
Action<SentryMonitorOptions>? configureMonitorOptions = null)
{
scope ??= new Scope(_options);

Expand All @@ -234,9 +240,16 @@ public SentryId CaptureCheckIn(string monitorSlug, CheckInStatus status, SentryI
var checkIn = new SentryCheckIn(monitorSlug, status, sentryId)
{
Duration = duration,
TraceId = traceId
TraceId = traceId,
};

if (configureMonitorOptions is not null)
{
var monitorOptions = new SentryMonitorOptions();
configureMonitorOptions.Invoke(monitorOptions);
checkIn.MonitorOptions = monitorOptions;
}

_enricher.Apply(checkIn);

return CaptureEnvelope(Envelope.FromCheckIn(checkIn))
Expand Down
Loading

0 comments on commit 37eb4a5

Please sign in to comment.