public async Task DataflowTest_InsufficientStorageSpace()
        {
            var exportCalled   = false;
            var convertCalled  = false;
            var completedEvent = new ManualResetEvent(false);
            var service        = new TestExportService(_logger.Object, _configuration, _serviceScopeFactory.Object, _storageInfoProvider.Object);

            service.ExportDataBlockCalled += (sender, args) =>
            {
                exportCalled = true;
            };
            service.ConvertDataBlockCalled += (sender, args) =>
            {
                convertCalled = true;
            };
            _resultsService.Setup(p => p.GetPendingJobs(It.IsAny <string>(), It.IsAny <CancellationToken>(), It.IsAny <int>())).Returns(Task.FromResult((IList <TaskResponse>)null));
            _storageInfoProvider.Setup(p => p.HasSpaceAvailableForExport).Returns(false);
            _storageInfoProvider.Setup(p => p.AvailableFreeSpace).Returns(100);

            await service.StartAsync(_cancellationTokenSource.Token);

            Thread.Sleep(1000);
            Assert.False(exportCalled);
            Assert.False(convertCalled);

            _resultsService.Verify(p => p.GetPendingJobs(TestExportService.AgentName, It.IsAny <CancellationToken>(), 10), Times.Never());
            await StopAndVerify(service);

            _logger.VerifyLogging($"Export Service completed timer routine.", LogLevel.Trace, Times.Never());
            _storageInfoProvider.Verify(p => p.HasSpaceAvailableForExport, Times.AtLeastOnce());
            _storageInfoProvider.Verify(p => p.AvailableFreeSpace, Times.AtLeastOnce());
        }
        private async Task StopAndVerify(TestExportService service)
        {
            await service.StopAsync(_cancellationTokenSource.Token);

            _resultsService.Invocations.Clear();
            _logger.VerifyLogging($"Export Task Watcher Hosted Service is stopping.", LogLevel.Information, Times.Once());
            Thread.Sleep(500);
            _resultsService.Verify(p => p.GetPendingJobs(TestExportService.AgentName, It.IsAny <CancellationToken>(), 10), Times.Never());
        }
        public async Task DataflowTest_CompletedEntireDataflow()
        {
            var exportCountdown  = new CountdownEvent(1);
            var convertCountdown = new CountdownEvent(1);

            var service = new TestExportService(_logger.Object, _configuration, _serviceScopeFactory.Object, _storageInfoProvider.Object);

            service.ExportDataBlockCalled += (sender, args) =>
            {
                exportCountdown.Signal();
            };
            service.ConvertDataBlockCalled += (sender, args) =>
            {
                convertCountdown.Signal();
            };

            var tasks = GenerateTaskResponse(1);

            _resultsService.Setup(p => p.GetPendingJobs(It.IsAny <string>(), It.IsAny <CancellationToken>(), It.IsAny <int>())).Returns(Task.FromResult(tasks));
            _resultsService.Setup(p => p.ReportSuccess(It.IsAny <Guid>(), It.IsAny <CancellationToken>())).Returns(Task.FromResult(true));
            _resultsService.Setup(p => p.ReportFailure(It.IsAny <Guid>(), It.IsAny <bool>(), It.IsAny <CancellationToken>())).Returns(Task.FromResult(true));
            _payloadsApi.Setup(p => p.Download(It.IsAny <string>(), It.IsAny <string>()))
            .Returns(Task.FromResult(new PayloadFile
            {
                Name = tasks.First().Uris.First(),
                Data = InstanceGenerator.GenerateDicomData()
            }));
            _storageInfoProvider.Setup(p => p.HasSpaceAvailableForExport).Returns(true);
            _storageInfoProvider.Setup(p => p.AvailableFreeSpace).Returns(100);

            await service.StartAsync(_cancellationTokenSource.Token);

            Assert.True(convertCountdown.Wait(3000));
            Assert.True(exportCountdown.Wait(3000));

            _resultsService.Verify(p => p.GetPendingJobs(TestExportService.AgentName, It.IsAny <CancellationToken>(), 10), Times.AtLeastOnce());
            _resultsService.Verify(p => p.ReportSuccess(It.IsAny <Guid>(), It.IsAny <CancellationToken>()), Times.Once());
            _payloadsApi.Verify(p => p.Download(tasks.First().PayloadId, tasks.First().Uris.First()), Times.Once());

            _logger.VerifyLogging($"Failed to download file {tasks.First().Uris.First()}.", LogLevel.Warning, Times.Never());
            _logger.VerifyLogging($"Failure rate exceeded threshold and will not be exported.", LogLevel.Error, Times.Never());
            _logger.VerifyLogging($"Task marked as successful.", LogLevel.Error, Times.Never());

            await StopAndVerify(service);

            _logger.VerifyLogging($"Export Service completed timer routine.", LogLevel.Trace, Times.AtLeastOnce());
            _storageInfoProvider.Verify(p => p.HasSpaceAvailableForExport, Times.AtLeastOnce());
            _storageInfoProvider.Verify(p => p.AvailableFreeSpace, Times.Never());
        }
        public async Task DataflowTest_ConvertReturnsEmpty()
        {
            var exportCountdown  = new CountdownEvent(1);
            var convertCountdown = new CountdownEvent(1);

            var service = new TestExportService(_logger.Object, _configuration, _serviceScopeFactory.Object, _storageInfoProvider.Object);

            service.ConvertReturnsEmpty    = true;
            service.ExportDataBlockCalled += (sender, args) =>
            {
                exportCountdown.Signal();
            };
            service.ConvertDataBlockCalled += (sender, args) =>
            {
                convertCountdown.Signal();
            };

            var tasks = GenerateTaskResponse(1);

            _resultsService.Setup(p => p.GetPendingJobs(It.IsAny <string>(), It.IsAny <CancellationToken>(), It.IsAny <int>())).Returns(Task.FromResult(tasks));
            _resultsService.Setup(p => p.ReportSuccess(It.IsAny <Guid>(), It.IsAny <CancellationToken>())).Returns(Task.FromResult(true));
            _resultsService.Setup(p => p.ReportFailure(It.IsAny <Guid>(), It.IsAny <bool>(), It.IsAny <CancellationToken>())).Returns(Task.FromResult(true));
            _storageInfoProvider.Setup(p => p.HasSpaceAvailableForExport).Returns(true);
            _storageInfoProvider.Setup(p => p.AvailableFreeSpace).Returns(100);

            await service.StartAsync(_cancellationTokenSource.Token);

            Assert.True(convertCountdown.Wait(3000));
            Assert.False(exportCountdown.Wait(3000));
            _resultsService.Verify(p => p.GetPendingJobs(TestExportService.AgentName, It.IsAny <CancellationToken>(), 10), Times.AtLeastOnce());
            await StopAndVerify(service);

            _logger.VerifyLogging($"Export Service completed timer routine.", LogLevel.Trace, Times.AtLeastOnce());
            _storageInfoProvider.Verify(p => p.HasSpaceAvailableForExport, Times.AtLeastOnce());
            _storageInfoProvider.Verify(p => p.AvailableFreeSpace, Times.Never());
        }