diff --git a/DeltaSight.SimpleBackgroundWorker.Tests/ParallelismTests.cs b/DeltaSight.SimpleBackgroundWorker.Tests/ParallelismTests.cs index f49c6bf..6f6d49b 100644 --- a/DeltaSight.SimpleBackgroundWorker.Tests/ParallelismTests.cs +++ b/DeltaSight.SimpleBackgroundWorker.Tests/ParallelismTests.cs @@ -38,9 +38,9 @@ public async Task Test_WithManyDegreesOfParallelism() await Task.Delay(jobTimeMs, t); ended.Add(DateTime.Now); semaphore.Release(); - }, $"Job {i}", e => + }, name: $"Job {i}", errorCallback: ex => { - Assert.Fail(e.Message); + Assert.Fail(ex.Message); return Task.CompletedTask; })) @@ -49,7 +49,7 @@ public async Task Test_WithManyDegreesOfParallelism() await bgWorker.QueueAsync(jobs); // Queue some long running jobs (that shouldn't interfere with max. degree of parallelism) - await bgWorker.QueueAsync(Enumerable.Range(1, 10).Select(x => new BackgroundWorkItem(t => Task.Delay(-1, t), isLongRunning:true))); + await bgWorker.QueueAsync(Enumerable.Range(1, 10).Select(x => BackgroundWorkItem.Create(t => Task.Delay(-1, t), ignoreParallelism:true))); var startAt = DateTime.Now; @@ -62,7 +62,7 @@ public async Task Test_WithManyDegreesOfParallelism() Assert.Multiple(() => { Assert.That(ended, Has.Count.EqualTo(count)); - Assert.That((ended.Max() - startAt).TotalMilliseconds, Is.EqualTo(m * jobTimeMs).Within(jobTimeMs)); + Assert.That((ended.Max() - startAt).TotalMilliseconds, Is.EqualTo(m * jobTimeMs).Within(2 * jobTimeMs)); }); await host.StopAsync(); diff --git a/DeltaSight.SimpleBackgroundWorker/BackgroundWorkItem.cs b/DeltaSight.SimpleBackgroundWorker/BackgroundWorkItem.cs index bd75a02..ef09949 100644 --- a/DeltaSight.SimpleBackgroundWorker/BackgroundWorkItem.cs +++ b/DeltaSight.SimpleBackgroundWorker/BackgroundWorkItem.cs @@ -4,13 +4,14 @@ namespace DeltaSight.SimpleBackgroundWorker; public struct BackgroundWorkItem { - public BackgroundWorkItem(Func execute, string name = "Untitled", Func? onError = null, bool isLongRunning = false, TimeSpan? cancelAfter = null) + private BackgroundWorkItem(Func execute, string name, Func? onError, bool ignoreParallelism, TaskCreationOptions options, TimeSpan? cancelAfter) { Name = name; Execute = execute; OnError = onError; - IsLongRunning = isLongRunning; + Options = options; CancelAfter = cancelAfter; + IgnoreParallelism = ignoreParallelism; } public Guid Guid { get; } = Guid.NewGuid(); @@ -19,11 +20,9 @@ public BackgroundWorkItem(Func execute, string name = " public Func Execute { get; } public Func? OnError { get; } = null; - /// - /// Flag to indicate the task is long running - /// Long running tasks will not impact maximum degree of parallelism - /// - public bool IsLongRunning { get; } + public TaskCreationOptions Options { get; } + + public bool IgnoreParallelism { get; } /// /// If set, the job will be cancelled automatically if the execution takes longer @@ -31,12 +30,14 @@ public BackgroundWorkItem(Func execute, string name = " public TimeSpan? CancelAfter { get; } public static BackgroundWorkItem Create(Func executeWork, - [CallerArgumentExpression("executeWork")] string name = "Untitled", + string? name = null, Func? errorCallback = null, - bool isLongRunning = false, - TimeSpan? cancelAfter = null - ) + bool ignoreParallelism = false, + TaskCreationOptions options = TaskCreationOptions.None, + TimeSpan? cancelAfter = null, + [CallerMemberName] string callerMemberName = "", + [CallerArgumentExpression("executeWork")] string callerArgumentExpression = "") { - return new BackgroundWorkItem(executeWork, name, errorCallback, isLongRunning, cancelAfter); + return new BackgroundWorkItem(executeWork, name ?? $"{callerMemberName}::{callerArgumentExpression}", errorCallback, ignoreParallelism, options, cancelAfter); } } \ No newline at end of file diff --git a/DeltaSight.SimpleBackgroundWorker/DeltaSight.SimpleBackgroundWorker.csproj b/DeltaSight.SimpleBackgroundWorker/DeltaSight.SimpleBackgroundWorker.csproj index a551ca0..5b69bdb 100644 --- a/DeltaSight.SimpleBackgroundWorker/DeltaSight.SimpleBackgroundWorker.csproj +++ b/DeltaSight.SimpleBackgroundWorker/DeltaSight.SimpleBackgroundWorker.csproj @@ -5,7 +5,7 @@ enable DeltaSight.SimpleBackgroundWorker Bas Timmermans - 2.2.0 + 3.0.0 A very simple and light weight background worker queue that respects a maximum degree of parallelism. Deltasight https://github.com/bt-88/Deltasight.SimpleBackgroundWorker diff --git a/DeltaSight.SimpleBackgroundWorker/SimpleBackgroundWorkerHost.cs b/DeltaSight.SimpleBackgroundWorker/SimpleBackgroundWorkerHost.cs index 426fa8a..5765eb2 100644 --- a/DeltaSight.SimpleBackgroundWorker/SimpleBackgroundWorkerHost.cs +++ b/DeltaSight.SimpleBackgroundWorker/SimpleBackgroundWorkerHost.cs @@ -51,9 +51,7 @@ private async Task Run(BackgroundWorkItem workItem, CancellationToken stoppingTo var task = await Task.Factory.StartNew( () => workItem.Execute(cts.Token), - workItem.IsLongRunning - ? TaskCreationOptions.None - : TaskCreationOptions.LongRunning).ConfigureAwait(false); + workItem.Options).ConfigureAwait(false); await task; @@ -99,14 +97,14 @@ private async Task Run(BackgroundWorkItem workItem, CancellationToken stoppingTo private async ValueTask WaitForWorker(BackgroundWorkItem item, CancellationToken cancellationToken) { - if (item.IsLongRunning) return; + if (item.IgnoreParallelism) return; await _semaphore.WaitAsync(cancellationToken); } private void ReleaseWorker(BackgroundWorkItem item) { - if (item.IsLongRunning) return; + if (item.IgnoreParallelism) return; _semaphore.Release(); }