Change task from being canceled to waiting (#118)

This commit is contained in:
rlauuzo 2024-04-16 18:19:05 +02:00 committed by GitHub
parent d288a2b5cf
commit ad3e0c4c08
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
7 changed files with 97 additions and 48 deletions

View File

@ -147,10 +147,10 @@
</div> </div>
<div class="inputContainer"> <div class="inputContainer">
<label class="inputLabel inputLabelUnfocused" for="MaximumEpisodeCreditsDuration"> <label class="inputLabel inputLabelUnfocused" for="MaximumCreditsDuration">
Maximum credits duration (in seconds) Maximum credits duration (in seconds)
</label> </label>
<input id="MaximumEpisodeCreditsDuration" type="number" is="emby-input" min="1" /> <input id="MaximumCreditsDuration" type="number" is="emby-input" min="1" />
<div class="fieldDescription"> <div class="fieldDescription">
Similar sounding audio which is longer than this duration will not be considered credits. Similar sounding audio which is longer than this duration will not be considered credits.
</div> </div>

View File

@ -211,11 +211,11 @@ public class Entrypoint : IHostedService, IDisposable
/// </summary> /// </summary>
private void StartTimer() private void StartTimer()
{ {
if (Plugin.Instance!.AnalyzerTaskIsRunning) if (Entrypoint.AutomaticTaskState == TaskState.Running)
{ {
_analyzeAgain = true; // Items added during a scan will be included later. _analyzeAgain = true; // Items added during a scan will be included later.
} }
else else if (ScheduledTaskSemaphore.CurrentCount > 0)
{ {
_logger.LogInformation("Media Library changed, analyzis will start soon!"); _logger.LogInformation("Media Library changed, analyzis will start soon!");
_queueTimer.Change(TimeSpan.FromMilliseconds(20000), Timeout.InfiniteTimeSpan); _queueTimer.Change(TimeSpan.FromMilliseconds(20000), Timeout.InfiniteTimeSpan);
@ -243,7 +243,7 @@ public class Entrypoint : IHostedService, IDisposable
private void PerformAnalysis() private void PerformAnalysis()
{ {
_logger.LogInformation("Timer elapsed - start analyzing"); _logger.LogInformation("Timer elapsed - start analyzing");
Plugin.Instance!.AnalyzerTaskIsRunning = true; _autoTaskCompletEvent.Reset();
using (_cancellationTokenSource = new CancellationTokenSource()) using (_cancellationTokenSource = new CancellationTokenSource())
{ {
@ -291,8 +291,8 @@ public class Entrypoint : IHostedService, IDisposable
} }
} }
Plugin.Instance!.AnalyzerTaskIsRunning = false;
_autoTaskCompletEvent.Set(); _autoTaskCompletEvent.Set();
_cancellationTokenSource = null;
// New item detected, start timer again // New item detected, start timer again
if (_analyzeAgain) if (_analyzeAgain)
@ -306,17 +306,17 @@ public class Entrypoint : IHostedService, IDisposable
/// <summary> /// <summary>
/// Method to cancel the automatic task. /// Method to cancel the automatic task.
/// </summary> /// </summary>
public static void CancelAutomaticTask() /// <param name="cancellationToken">Cancellation token.</param>
public static void CancelAutomaticTask(CancellationToken cancellationToken)
{ {
if (_cancellationTokenSource != null) if (_cancellationTokenSource != null)
{ {
_cancellationTokenSource.Cancel(); if (!_cancellationTokenSource.IsCancellationRequested)
{
_cancellationTokenSource.Cancel();
}
_autoTaskCompletEvent.Wait(); // Wait for the signal _autoTaskCompletEvent.Wait(TimeSpan.FromSeconds(60), cancellationToken); // Wait for the signal
_autoTaskCompletEvent.Reset(); // Reset for the next task
_cancellationTokenSource.Dispose(); // Now safe to dispose
_cancellationTokenSource = null;
} }
} }

View File

@ -140,11 +140,6 @@ public class Plugin : BasePlugin<PluginConfiguration>, IHasWebPages
FFmpegWrapper.CheckFFmpegVersion(); FFmpegWrapper.CheckFFmpegVersion();
} }
/// <summary>
/// Gets or sets a value indicating whether analysis is running.
/// </summary>
public bool AnalyzerTaskIsRunning { get; set; } = false;
/// <summary> /// <summary>
/// Gets the results of fingerprinting all episodes. /// Gets the results of fingerprinting all episodes.
/// </summary> /// </summary>

View File

@ -69,19 +69,22 @@ public class DetectCreditsTask : IScheduledTask
throw new InvalidOperationException("Library manager was null"); throw new InvalidOperationException("Library manager was null");
} }
// abort if analyzer is already running // abort automatic analyzer if running
if (Plugin.Instance!.AnalyzerTaskIsRunning && Entrypoint.AutomaticTaskState == TaskState.Idle) if (Entrypoint.AutomaticTaskState == TaskState.Running || Entrypoint.AutomaticTaskState == TaskState.Cancelling)
{
return Task.CompletedTask;
}
else if (Plugin.Instance!.AnalyzerTaskIsRunning && Entrypoint.AutomaticTaskState == TaskState.Running)
{ {
_logger.LogInformation("Automatic Task is {0} and will be canceled.", Entrypoint.AutomaticTaskState); _logger.LogInformation("Automatic Task is {0} and will be canceled.", Entrypoint.AutomaticTaskState);
Entrypoint.CancelAutomaticTask(); Entrypoint.CancelAutomaticTask(cancellationToken);
}
ScheduledTaskSemaphore.Wait(-1, cancellationToken);
if (cancellationToken.IsCancellationRequested)
{
ScheduledTaskSemaphore.Release();
return Task.CompletedTask;
} }
_logger.LogInformation("Scheduled Task is starting"); _logger.LogInformation("Scheduled Task is starting");
Plugin.Instance!.AnalyzerTaskIsRunning = true;
var baseCreditAnalyzer = new BaseItemAnalyzerTask( var baseCreditAnalyzer = new BaseItemAnalyzerTask(
AnalysisMode.Credits, AnalysisMode.Credits,
@ -91,8 +94,7 @@ public class DetectCreditsTask : IScheduledTask
baseCreditAnalyzer.AnalyzeItems(progress, cancellationToken); baseCreditAnalyzer.AnalyzeItems(progress, cancellationToken);
Plugin.Instance!.AnalyzerTaskIsRunning = false; ScheduledTaskSemaphore.Release();
return Task.CompletedTask; return Task.CompletedTask;
} }

View File

@ -68,19 +68,22 @@ public class DetectIntrosCreditsTask : IScheduledTask
throw new InvalidOperationException("Library manager was null"); throw new InvalidOperationException("Library manager was null");
} }
// abort if analyzer is already running // abort automatic analyzer if running
if (Plugin.Instance!.AnalyzerTaskIsRunning && Entrypoint.AutomaticTaskState == TaskState.Idle) if (Entrypoint.AutomaticTaskState == TaskState.Running || Entrypoint.AutomaticTaskState == TaskState.Cancelling)
{
return Task.CompletedTask;
}
else if (Plugin.Instance!.AnalyzerTaskIsRunning && Entrypoint.AutomaticTaskState == TaskState.Running)
{ {
_logger.LogInformation("Automatic Task is {0} and will be canceled.", Entrypoint.AutomaticTaskState); _logger.LogInformation("Automatic Task is {0} and will be canceled.", Entrypoint.AutomaticTaskState);
Entrypoint.CancelAutomaticTask(); Entrypoint.CancelAutomaticTask(cancellationToken);
}
ScheduledTaskSemaphore.Wait(-1, cancellationToken);
if (cancellationToken.IsCancellationRequested)
{
ScheduledTaskSemaphore.Release();
return Task.CompletedTask;
} }
_logger.LogInformation("Scheduled Task is starting"); _logger.LogInformation("Scheduled Task is starting");
Plugin.Instance!.AnalyzerTaskIsRunning = true;
var baseIntroAnalyzer = new BaseItemAnalyzerTask( var baseIntroAnalyzer = new BaseItemAnalyzerTask(
AnalysisMode.Introduction, AnalysisMode.Introduction,
@ -98,8 +101,7 @@ public class DetectIntrosCreditsTask : IScheduledTask
baseCreditAnalyzer.AnalyzeItems(progress, cancellationToken); baseCreditAnalyzer.AnalyzeItems(progress, cancellationToken);
Plugin.Instance!.AnalyzerTaskIsRunning = false; ScheduledTaskSemaphore.Release();
return Task.CompletedTask; return Task.CompletedTask;
} }

View File

@ -68,19 +68,22 @@ public class DetectIntrosTask : IScheduledTask
throw new InvalidOperationException("Library manager was null"); throw new InvalidOperationException("Library manager was null");
} }
// abort if analyzer is already running // abort automatic analyzer if running
if (Plugin.Instance!.AnalyzerTaskIsRunning && Entrypoint.AutomaticTaskState == TaskState.Idle) if (Entrypoint.AutomaticTaskState == TaskState.Running || Entrypoint.AutomaticTaskState == TaskState.Cancelling)
{
return Task.CompletedTask;
}
else if (Plugin.Instance!.AnalyzerTaskIsRunning && Entrypoint.AutomaticTaskState == TaskState.Running)
{ {
_logger.LogInformation("Automatic Task is {0} and will be canceled.", Entrypoint.AutomaticTaskState); _logger.LogInformation("Automatic Task is {0} and will be canceled.", Entrypoint.AutomaticTaskState);
Entrypoint.CancelAutomaticTask(); Entrypoint.CancelAutomaticTask(cancellationToken);
}
ScheduledTaskSemaphore.Wait(-1, cancellationToken);
if (cancellationToken.IsCancellationRequested)
{
ScheduledTaskSemaphore.Release();
return Task.CompletedTask;
} }
_logger.LogInformation("Scheduled Task is starting"); _logger.LogInformation("Scheduled Task is starting");
Plugin.Instance!.AnalyzerTaskIsRunning = true;
var baseIntroAnalyzer = new BaseItemAnalyzerTask( var baseIntroAnalyzer = new BaseItemAnalyzerTask(
AnalysisMode.Introduction, AnalysisMode.Introduction,
@ -90,8 +93,7 @@ public class DetectIntrosTask : IScheduledTask
baseIntroAnalyzer.AnalyzeItems(progress, cancellationToken); baseIntroAnalyzer.AnalyzeItems(progress, cancellationToken);
Plugin.Instance!.AnalyzerTaskIsRunning = false; ScheduledTaskSemaphore.Release();
return Task.CompletedTask; return Task.CompletedTask;
} }

View File

@ -0,0 +1,48 @@
using System;
using System.Threading;
namespace ConfusedPolarBear.Plugin.IntroSkipper;
internal sealed class ScheduledTaskSemaphore : IDisposable
{
private static readonly SemaphoreSlim _semaphore = new SemaphoreSlim(1, 1);
private ScheduledTaskSemaphore()
{
}
public static int CurrentCount => _semaphore.CurrentCount;
public static bool Wait(int timeout, CancellationToken cancellationToken)
{
return _semaphore.Wait(timeout, cancellationToken);
}
public static int Release()
{
return _semaphore.Release();
}
/// <summary>
/// Dispose.
/// </summary>
public void Dispose()
{
Dispose(true);
GC.SuppressFinalize(this);
}
/// <summary>
/// Protected dispose.
/// </summary>
/// <param name="disposing">Dispose.</param>
private void Dispose(bool disposing)
{
if (!disposing)
{
return;
}
_semaphore.Dispose();
}
}