using System; using ln.application; using System.Threading; using ln.logging; using ln.application.service; using ln.skyscanner.entities; using ln.skyscanner.checks; using System.Collections.Generic; using ln.types.threads; using System.Linq; namespace ln.skyscanner.services { public class CheckService : ApplicationServiceBase { Pool checkPool; public CheckService() :base("Check Service") { DependOnService(); } public override void ServiceMain(IApplicationInterface applicationInterface) { EntityService entityService = Dependency(); Dictionary checkJobs = new Dictionary(); HashSet currentNodes = new HashSet(); checkPool = new Pool(64); long nextMinute = DateTimeOffset.Now.ToUnixTimeMilliseconds(); Ready(); while (!StopRequested) { /* Logging.Log(LogLevel.INFO, "SkyChecker.scheduler(): scheduler save CheckStates"); lock (saveQueue) { foreach (SkyCheckState checkState in saveQueue) { SkyScanner.Instance.Entities.SkyCheckStates.Upsert(checkState); } saveQueue.Clear(); } */ Logging.Log(LogLevel.INFO, "SkyChecker.scheduler(): scheduler starts"); currentNodes.Clear(); foreach (Node node in entityService.NodeCollection) { currentNodes.Add(node); if (!checkJobs.ContainsKey(node)) { CheckJob checkJob = new CheckJob(node); checkJobs.Add(node, checkJob); } } foreach (Node node in checkJobs.Keys.ToArray()) { currentNodes.Remove(node); } if (currentNodes.Count > 0) { foreach (Node node in currentNodes) checkJobs.Remove(node); } currentNodes.Clear(); Logging.Log(LogLevel.INFO, "SkyChecker.scheduler(): prepared {0} checks", checkJobs.Count); Logging.Log(LogLevel.INFO, "SkyChecker.scheduler(): scheduled {0} checks", checkPool.Enqueue(checkJobs.Values)); while (true) { while ((nextMinute - DateTimeOffset.Now.ToUnixTimeMilliseconds()) < 0) nextMinute += 60000; try { Thread.Sleep((int)(nextMinute - DateTimeOffset.Now.ToUnixTimeMilliseconds())); } catch (ThreadInterruptedException) { Logging.Log(LogLevel.INFO, "CheckService: scheduler was interrupted"); if (StopRequested) break; } } } } } }