public void StartTestRunShouldProcessAllSourcesOnExecutionAbortsForAnySource()
        {
            var executionManagerMock     = new Mock <IProxyExecutionManager>();
            var parallelExecutionManager = new ParallelProxyExecutionManager(this.mockRequestData.Object, () => executionManagerMock.Object, 1);

            this.createdMockManagers.Add(executionManagerMock);
            this.SetupMockManagers(processedSources, isCanceled: false, isAborted: true);
            SetupHandleTestRunComplete(this.executionCompleted);

            Task.Run(() => { parallelExecutionManager.StartTestRun(this.testRunCriteriaWithSources, this.mockHandler.Object); });

            Assert.IsTrue(this.executionCompleted.Wait(taskTimeout), "Test run not completed.");
            Assert.AreEqual(2, this.processedSources.Count, "Abort should stop all sources execution.");
        }
        public void StartTestRunShouldAggregateRunData()
        {
            var parallelExecutionManager = new ParallelProxyExecutionManager(this.mockRequestData.Object, this.proxyManagerFunc, 2);
            var syncObject = new object();

            foreach (var manager in createdMockManagers)
            {
                manager.Setup(m => m.StartTestRun(It.IsAny <TestRunCriteria>(), It.IsAny <ITestRunEventsHandler>())).
                Callback <TestRunCriteria, ITestRunEventsHandler>(
                    (criteria, handler) =>
                {
                    lock (syncObject)
                    {
                        this.processedSources.AddRange(criteria.Sources);
                    }

                    Task.Delay(100).Wait();
                    var stats = new Dictionary <TestOutcome, long>();
                    stats.Add(TestOutcome.Passed, 3);
                    stats.Add(TestOutcome.Failed, 2);
                    var runAttachments = new Collection <AttachmentSet>();
                    runAttachments.Add(new AttachmentSet(new Uri("hello://x/"), "Hello"));
                    var executorUris = new List <string>()
                    {
                        "hello1"
                    };
                    bool isCanceled   = false;
                    bool isAborted    = false;
                    TimeSpan timespan = TimeSpan.FromMilliseconds(100);

                    if (string.Equals(criteria.Sources?.FirstOrDefault(), "2.dll"))
                    {
                        isCanceled = true;
                        isAborted  = true;
                        timespan   = TimeSpan.FromMilliseconds(200);
                    }

                    var completeArgs = new TestRunCompleteEventArgs(new
                                                                    TestRunStatistics(5, stats), isCanceled, isAborted, null, runAttachments, timespan);
                    handler.HandleTestRunComplete(completeArgs, null, runAttachments, executorUris);
                });
            }

            Exception assertException = null;

            this.mockHandler.Setup(m => m.HandleTestRunComplete(
                                       It.IsAny <TestRunCompleteEventArgs>(),
                                       It.IsAny <TestRunChangedEventArgs>(),
                                       It.IsAny <ICollection <AttachmentSet> >(),
                                       It.IsAny <ICollection <string> >())).Callback
            <TestRunCompleteEventArgs, TestRunChangedEventArgs, ICollection <AttachmentSet>, ICollection <string> >(
                (completeArgs, runChangedArgs, runAttachments, executorUris) =>
            {
                try
                {
                    Assert.AreEqual(TimeSpan.FromMilliseconds(200), completeArgs.ElapsedTimeInRunningTests,
                                    "Time should be max of all");
                    Assert.AreEqual(2, completeArgs.AttachmentSets.Count,
                                    "All Complete Arg attachments should return");
                    Assert.AreEqual(2, runAttachments.Count, "All RunContextAttachments should return");

                    Assert.IsTrue(completeArgs.IsAborted, "Aborted value must be OR of all values");
                    Assert.IsTrue(completeArgs.IsCanceled, "Canceled value must be OR of all values");

                    Assert.AreEqual(10, completeArgs.TestRunStatistics.ExecutedTests,
                                    "Stats must be aggregated properly");

                    Assert.AreEqual(6, completeArgs.TestRunStatistics.Stats[TestOutcome.Passed],
                                    "Stats must be aggregated properly");
                    Assert.AreEqual(4, completeArgs.TestRunStatistics.Stats[TestOutcome.Failed],
                                    "Stats must be aggregated properly");
                }
                catch (Exception ex)
                {
                    assertException = ex;
                }
                finally
                {
                    this.executionCompleted.Set();
                }
            });

            Task.Run(() =>
            {
                parallelExecutionManager.StartTestRun(testRunCriteriaWithSources, this.mockHandler.Object);
            });

            Assert.IsTrue(this.executionCompleted.Wait(taskTimeout), "Test run not completed.");

            Assert.IsNull(assertException, assertException?.ToString());
            Assert.AreEqual(sources.Count, this.processedSources.Count, "All Sources must be processed.");
            AssertMissingAndDuplicateSources(this.processedSources);
        }