public void RequestStop() { lock (m_Mutex) { RunInfo runInfo = RunInfo; if (runInfo != null) { runInfo.RequestStop(); } } }
public void Run(CancellationToken token, IProgress <string> fileSourceProgress, IProgress <IEnumerable <FileProgressInfo> > testedProgress, IProgress <IEnumerable <FileProgressInfo> > matchedProgress, IProgress <IEnumerable <ExceptionInfo> > exceptionProgress, IProgress <bool> completeProgress, TimeSpan reportInterval) { int numMatched = 0; DateTime lastExceptionReportTime = DateTime.Now; DateTime lastTestedReportTime = DateTime.Now; DateTime lastMatchedReportTime = DateTime.Now; try { if (fileSourceProgress == null) { fileSourceProgress = new Progress <string>(x => { }); } if (testedProgress == null) { testedProgress = new Progress <IEnumerable <FileProgressInfo> >(x => { }); } if (matchedProgress == null) { matchedProgress = new Progress <IEnumerable <FileProgressInfo> >(x => { }); } if (exceptionProgress == null) { exceptionProgress = new Progress <IEnumerable <ExceptionInfo> >(x => { }); } if (completeProgress == null) { completeProgress = new Progress <bool>(x => { }); } lock (m_Mutex) { RunInfo = new RunInfo(FileSource, Condition, FieldSources, TestedProcessors, MatchedProcessors, MaxToMatch, token, fileSourceProgress, testedProgress, matchedProgress, exceptionProgress, completeProgress); TimeSpan interval = TimeSpan.FromMilliseconds(100); Timer = new Timer(state => { ReportFilesAndExceptions(); if (StopRequested) { Timer.Dispose(); } }, null, interval, interval); } token.ThrowIfCancellationRequested(); FileSource.Init(RunInfo); token.ThrowIfCancellationRequested(); Condition.Init(RunInfo); token.ThrowIfCancellationRequested(); foreach (IFieldSource fieldSource in FieldSources) { token.ThrowIfCancellationRequested(); fieldSource.Init(RunInfo); } foreach (IProcessor processor in TestedProcessors) { token.ThrowIfCancellationRequested(); processor.Init(RunInfo); } foreach (IProcessor processor in MatchedProcessors) { token.ThrowIfCancellationRequested(); processor.Init(RunInfo); } } catch (OperationCanceledException ex) { Cleanup(exceptionProgress); throw ex; } catch (Exception ex) { Cleanup(exceptionProgress); RunInfo.ExceptionInfos.Enqueue(new ExceptionInfo(ex)); ReportFilesAndExceptions(); completeProgress?.Report(false); return; } try { foreach (FileInfo file in FileSource.Files) { token.ThrowIfCancellationRequested(); try { Dictionary <Type, IFileCache> caches = new Dictionary <Type, IFileCache>(); List <string> values = new List <string>(); MatchResult result = null; MatchResultType matchResultType = MatchResultType.NotApplicable; if (!file.Exists) { continue; } try { GetFileCaches(Condition, FieldSources, file, caches, exceptionProgress); try { result = Condition.Matches(file, caches, token); if (result?.Values != null) { values.AddRange(result.Values); } matchResultType = result == null ? MatchResultType.NotApplicable : result.Type; } catch (Exception ex) when(!(ex is OperationCanceledException)) { RunInfo.ExceptionInfos.Enqueue(new ExceptionInfo(ex, file)); } if (result != null) { foreach (IFieldSource fieldSource in FieldSources) { if (fieldSource != null) { try { string[] vals = fieldSource.GetValues(file, caches, token); if (vals != null) { values.AddRange(vals); } } catch (Exception ex) when(!(ex is OperationCanceledException)) { RunInfo.ExceptionInfos.Enqueue(new ExceptionInfo(ex, file)); } } } string[] allValues = values.ToArray(); RunInfo.TestedFileProgressInfos.Enqueue(new FileProgressInfo(file, result.Type, allValues)); RunProcessors(TestedProcessors, file, matchResultType, allValues); if (result.Type == MatchResultType.Yes) { RunInfo.MatchedFileProgressInfos.Enqueue(new FileProgressInfo(file, result.Type, allValues)); RunProcessors(MatchedProcessors, file, matchResultType, allValues); numMatched++; } } } finally { DisposeFileCaches(caches, RunInfo.ExceptionInfos); } } catch (Exception ex) when(!(ex is OperationCanceledException)) { RunInfo.ExceptionInfos.Enqueue(new ExceptionInfo(ex, file)); } if (RunInfo.StopRequested || numMatched == MaxToMatch) { break; } } AggregateProcessors(TestedProcessors); AggregateProcessors(MatchedProcessors); } catch (Exception ex) when(!(ex is OperationCanceledException)) { RunInfo.ExceptionInfos.Enqueue(new ExceptionInfo(ex)); } finally { Cleanup(exceptionProgress); } ReportFilesAndExceptions(); completeProgress?.Report(false); }