Skip to content

Commit

Permalink
Shared Waiter class
Browse files Browse the repository at this point in the history
  • Loading branch information
nvborisenko committed Jun 26, 2024
1 parent b9235b8 commit 1a5d100
Showing 1 changed file with 105 additions and 0 deletions.
105 changes: 105 additions & 0 deletions src/Yapoml.Framework/Waiter.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,105 @@
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Text;
using System.Threading;
using System.Threading.Tasks;

namespace Yapoml.Framework
{
public static class Waiter
{
public static void Until(Func<bool> condition, TimeSpan timeout, TimeSpan pollingInterval)
{
var stopwatch = Stopwatch.StartNew();

Lazy<List<Exception>> occuredExceptions = new Lazy<List<Exception>>(() => new List<Exception>());

do
{
try
{
var isSuccessful = condition();

if (isSuccessful)
{
return;
}
else
{
Thread.Sleep(pollingInterval);
}
}
catch (Exception ex)
{
occuredExceptions.Value.Add(ex);

Thread.Sleep(pollingInterval);
}
}
while (stopwatch.Elapsed <= timeout);

var timeoutMessageBuilder = new StringBuilder($"Condition was not satisfied within {timeout.TotalSeconds} seconds when polled every {pollingInterval.TotalSeconds} seconds.");

if (occuredExceptions.IsValueCreated)
{
timeoutMessageBuilder.AppendLine();
timeoutMessageBuilder.AppendLine("Occured errors:");

foreach (var occuredExceptionsGroup in occuredExceptions.Value.GroupBy(e => e.Message))
{
timeoutMessageBuilder.AppendLine($" - {occuredExceptionsGroup.Key} ({occuredExceptionsGroup.Count()} times)");
}
}

throw new TimeoutException(timeoutMessageBuilder.ToString());
}

public static async Task UntilAsync(Func<Task<bool>> condition, TimeSpan timeout, TimeSpan pollingInterval)
{
var stopwatch = Stopwatch.StartNew();

Lazy<List<Exception>> occuredExceptions = new Lazy<List<Exception>>(() => new List<Exception>());

do
{
try
{
var isSuccessful = await condition().ConfigureAwait(false);

if (isSuccessful)
{
return;
}
else
{
await Task.Delay(pollingInterval).ConfigureAwait(false);
}
}
catch (Exception ex)
{
occuredExceptions.Value.Add(ex);

await Task.Delay(pollingInterval).ConfigureAwait(false);
}
}
while (stopwatch.Elapsed <= timeout);

var timeoutMessageBuilder = new StringBuilder($"Condition was not satisfied within {timeout.TotalSeconds} seconds when polled every {pollingInterval.TotalSeconds} seconds.");

if (occuredExceptions.IsValueCreated)
{
timeoutMessageBuilder.AppendLine();
timeoutMessageBuilder.AppendLine("Occured errors:");

foreach (var occuredExceptionsGroup in occuredExceptions.Value.GroupBy(e => e.Message))
{
timeoutMessageBuilder.AppendLine($" - {occuredExceptionsGroup.Key} ({occuredExceptionsGroup.Count()} times)");
}
}

throw new TimeoutException(timeoutMessageBuilder.ToString());
}
}
}

0 comments on commit 1a5d100

Please sign in to comment.