Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Update telemetry benchmark #1311

Merged
merged 2 commits into from
Jun 16, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -1,17 +1,17 @@
``` ini

BenchmarkDotNet=v0.13.5, OS=Windows 11 (10.0.22621.1702/22H2/2022Update/SunValley2)
Intel Core i9-10885H CPU 2.40GHz, 1 CPU, 16 logical and 8 physical cores
.NET SDK=7.0.203
[Host] : .NET 7.0.5 (7.0.523.17405), X64 RyuJIT AVX2
BenchmarkDotNet=v0.13.5, OS=Windows 11 (10.0.22621.1702/22H2/2022Update/SunValley2), VM=Hyper-V
Intel Xeon Platinum 8370C CPU 2.80GHz, 1 CPU, 16 logical and 8 physical cores
.NET SDK=7.0.304
[Host] : .NET 7.0.7 (7.0.723.27404), X64 RyuJIT AVX2

Job=MediumRun Toolchain=InProcessEmitToolchain IterationCount=15
LaunchCount=2 WarmupCount=10

```
| Method | Telemetry | Mean | Error | StdDev | Median | Gen0 | Allocated |
|-------- |---------- |------------:|-----------:|-----------:|----------:|-------:|----------:|
| **Execute** | **False** | **90.27 ns** | **0.823 ns** | **1.207 ns** | **90.34 ns** | **-** | **-** |
| Retry | False | 435.25 ns | 8.593 ns | 12.595 ns | 433.63 ns | - | - |
| **Execute** | **True** | **311.60 ns** | **4.107 ns** | **5.890 ns** | **311.37 ns** | **-** | **-** |
| Retry | True | 1,004.07 ns | 106.845 ns | 159.921 ns | 922.31 ns | 0.0124 | 104 B |
| Method | Telemetry | Enrichment | Mean | Error | StdDev | Gen0 | Allocated |
|-------- |---------- |----------- |------------:|---------:|----------:|-------:|----------:|
| **Execute** | **False** | **False** | **80.13 ns** | **0.324 ns** | **0.486 ns** | **-** | **-** |
| **Execute** | **False** | **True** | **74.33 ns** | **0.286 ns** | **0.392 ns** | **-** | **-** |
| **Execute** | **True** | **False** | **494.33 ns** | **3.973 ns** | **5.698 ns** | **0.0029** | **72 B** |
| **Execute** | **True** | **True** | **1,157.27 ns** | **7.130 ns** | **10.450 ns** | **0.0286** | **728 B** |
59 changes: 42 additions & 17 deletions bench/Polly.Core.Benchmarks/TelemetryBenchmark.cs
Original file line number Diff line number Diff line change
@@ -1,28 +1,25 @@
using Microsoft.Extensions.Logging.Abstractions;
using Polly.Extensions.Telemetry;
using Polly.Telemetry;

namespace Polly.Core.Benchmarks;

public class TelemetryBenchmark
{
private ResilienceStrategy? _strategy;
private ResilienceStrategy? _retryStrategy;

[GlobalSetup]
public void Prepare()
{
_strategy = Build(new ResilienceStrategyBuilder());
_retryStrategy = Build(new ResilienceStrategyBuilder().AddRetry(new RetryStrategyOptions
{
ShouldRetry = _ => PredicateResult.True,
RetryCount = 1,
BaseDelay = TimeSpan.Zero,
BackoffType = RetryBackoffType.Constant
}));
}

[Params(true, false)]
public bool Telemetry { get; set; }

[Params(true, false)]
public bool Enrichment { get; set; }

[Benchmark]
public async ValueTask Execute()
{
Expand All @@ -31,21 +28,49 @@ public async ValueTask Execute()
ResilienceContext.Return(context);
}

[Benchmark]
public async ValueTask Retry()
{
var context = ResilienceContext.Get();
await _retryStrategy!.ExecuteOutcomeAsync((_, _) => new ValueTask<Outcome<string>>(new Outcome<string>("dummy")), context, "state").ConfigureAwait(false);
ResilienceContext.Return(context);
}

private ResilienceStrategy Build(ResilienceStrategyBuilder builder)
{
builder.AddStrategy(context => new TelemetryEventStrategy(context.Telemetry), new EmptyResilienceOptions());

if (Telemetry)
{
builder.EnableTelemetry(NullLoggerFactory.Instance);
TelemetryResilienceStrategyOptions options = new() { LoggerFactory = NullLoggerFactory.Instance };

if (Enrichment)
{
options.Enrichers.Add(context =>
{
// The Microsoft.Extensions.Resilience library will add around 6 additional tags
// https://github.com/dotnet/extensions/tree/main/src/Libraries/Microsoft.Extensions.Resilience
context.Tags.Add(new("dummy1", "dummy"));
context.Tags.Add(new("dummy2", "dummy"));
context.Tags.Add(new("dummy3", "dummy"));
context.Tags.Add(new("dummy4", "dummy"));
context.Tags.Add(new("dummy5", "dummy"));
context.Tags.Add(new("dummy6", "dummy"));
});
}

builder.EnableTelemetry(options);
}

return builder.Build();
}

private class TelemetryEventStrategy : ResilienceStrategy
{
private readonly ResilienceStrategyTelemetry _telemetry;

public TelemetryEventStrategy(ResilienceStrategyTelemetry telemetry) => _telemetry = telemetry;

protected override ValueTask<Outcome<TResult>> ExecuteCoreAsync<TResult, TState>(
Func<ResilienceContext, TState, ValueTask<Outcome<TResult>>> callback,
ResilienceContext context,
TState state)
{
_telemetry.Report("DummyEvent", context, "dummy-args");
return callback(context, state);
}
}

}
6 changes: 6 additions & 0 deletions bench/Polly.Core.Benchmarks/Utils/EmptyResilienceOptions.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
namespace Polly.Core.Benchmarks.Utils;

internal sealed class EmptyResilienceOptions : ResilienceStrategyOptions
{
public override string StrategyType => "Empty";
}