Files
LeafWeb/Web/Services/PiscalQueueManager.cs
T

112 lines
2.9 KiB
C#

using System;
using System.Linq;
using System.Threading;
using Hangfire;
using LeafWeb.Core.Entities;
using LeafWeb.Core.Remote;
namespace LeafWeb.Web.Services
{
public class PiscalQueueManager : PiscalQueueBase
{
private static readonly object ProcessQueueLock = new object();
public void ProcessQueue()
{
// prevent multiple entry into processing the queue
if (Monitor.TryEnter(ProcessQueueLock))
{
Logger.Trace("ProcessQueue entered");
try
{
UpdateRunning();
StartNextPending();
}
finally
{
Logger.Trace("ProcessQueue exit");
Monitor.Exit(ProcessQueueLock);
}
}
else
{
Logger.Trace("ProcessQueue locked, queue already processing");
}
}
private void StartNextPending()
{
var runningLeafInputs = DataService.GetRunningLeafInputs().ToList();
if (runningLeafInputs.Any())
{
Logger.Trace("Leaf input currently running , don't enqueue any new");
return;
}
var pendingInput =
DataService
.GetLeafInputs(LeafInputStatusType.Pending)
.OrderBy(l => l.StatusHistory.Min(sh => sh.DateTime))
.FirstOrDefault();
if (pendingInput == null)
{
Logger.Trace("No pending leaf input");
return;
}
var pendingInputId = pendingInput.Id;
Logger.Info("LeafInput: {0}, Starting", pendingInputId);
DataService.SetLeafInputStatus(pendingInput, LeafInputStatusType.Starting);
BackgroundJob.Enqueue<StartPending>(c => c.DoWork(pendingInputId));
}
private void UpdateRunning()
{
var running = DataService.GetLeafInputs(LeafInputStatusType.Running).ToList();
foreach (var leafInput in running)
{
try
{
var status = PiscalService.GetStatus(leafInput);
var leafInputId = leafInput.Id;
switch (status)
{
case PiscalStatus.NotStarted:
// if it's not started - this is unusual state
Logger.Warn("LeafInput: {0}, Piscal Not Started", leafInput.Id);
break;
case PiscalStatus.Running:
Logger.Trace("LeafInput: {0}, Piscal Running", leafInput.Id);
// continue running
break;
case PiscalStatus.Complete:
// TODO: change to "retrieving output"?
DataService.SetLeafInputStatus(leafInput, LeafInputStatusType.Finishing);
var retrieveFilesId = BackgroundJob.Enqueue<RetrieveOutputFiles>(s => s.DoWork(leafInputId));
BackgroundJob.ContinueWith<Cleanup>(retrieveFilesId, s => s.DoWork(leafInputId));
BackgroundJob.ContinueWith<EmailNotificationService>(retrieveFilesId,
email => email.SendLeafWebComplete(leafInputId));
BackgroundJob.ContinueWith<SetComplete>(retrieveFilesId, s => s.DoWork(leafInputId));
break;
}
}
catch (PiscalClientException ex)
{
PiscalExceptionNotify(ex, leafInput);
}
catch (Exception ex)
{
var errorMessage = FormatException(ex, leafInput.Id);
Logger.Error(errorMessage);
}
}
}
}
}