/// <summary>
        /// Performs an upload and a remote analysis of the sample media file.
        /// </summary>
        /// <param name="sourcePath">The source file path.</param>
        /// <param name="accountName">The account name to upload to.</param>
        /// <param name="container">The container to upload to.</param>
        /// <returns>The MediaInfo report.</returns>
        public async Task <JObject> ExecuteAsync(string sourcePath, string accountName, string container)
        {
            if (string.IsNullOrEmpty(sourcePath))
            {
                throw new ArgumentNullException(nameof(sourcePath));
            }

            var localFileExists = File.Exists(sourcePath);

            if (!localFileExists)
            {
                var msg = $"Non-existent local file: {sourcePath} as '{nameof(sourcePath)}'.  A report on an existing remote file will be attempted.";
                _logger.LogError(msg);
            }

            if (string.IsNullOrEmpty(Path.GetFileName(sourcePath)))
            {
                var msg = $"{nameof(sourcePath)} does not end with a filename: {sourcePath}";
                _logger.LogError(msg);
                throw new ArgumentException(msg, nameof(container));
            }

            if (string.IsNullOrEmpty(accountName))
            {
                throw new ArgumentNullException(nameof(accountName));
            }

#pragma warning disable CA1308 // Normalize strings to uppercase
            if (accountName != accountName.ToLowerInvariant())
#pragma warning restore CA1308 // Normalize strings to uppercase
            {
                var msg = $"Account names should be lower case: {accountName}";
                throw new ArgumentException(msg, nameof(accountName));
            }

            if (string.IsNullOrEmpty(container))
            {
                throw new ArgumentNullException(nameof(container));
            }

            var blobUri = new Uri($"https://{accountName}.blob.core.windows.net/{container}/{Path.GetFileName(sourcePath)}");
            if (localFileExists)
            {
                var containerUri = new Uri($"https://{accountName}.blob.core.windows.net/{container}");
                _ = await _azureStorageOperations.ContainerCreateIfNotExistsAsync(containerUri).ConfigureAwait(false);

                _ = await _azureStorageOperations.BlobUploadAsync(sourcePath, blobUri).ConfigureAwait(false);
            }

            var report = await _mediaInfoReportService.GetMediaInfoCompleteInformForUriAsync(blobUri).ConfigureAwait(false);

            return(report);
        }
        public async Task GetMediaInfoCompleteInformForUriAsync_Should_Throw_When_BlobUriIsNull()
        {
            // Arrange
            StorageClientProviderContext context = StorageClientProviderContext.None;

            // Act & Assert
            await Assert.ThrowsAsync <ArgumentNullException>(async() =>
                                                             await _service.GetMediaInfoCompleteInformForUriAsync(null, context).ConfigureAwait(true))
            .ConfigureAwait(true);
        }
        public async Task <IActionResult> Run(
            [HttpTrigger(AuthorizationLevel.Function, "get", "post", Route = null)] HttpRequest req)
        {
            if (req?.Method == HttpMethods.Get)
            {
                var message = $"Do not use {req.Method}, use POST with a body or query of 'blobUri'.";
                _logger.LogInformation(message);
                return(new BadRequestObjectResult(new { message }));
            }

            string blobUriString = req?.Query["blobUri"];

            using (StreamReader streamReader = new StreamReader(req?.Body))
            {
                string requestBody = await streamReader.ReadToEndAsync().ConfigureAwait(false);

                dynamic data = JsonConvert.DeserializeObject(requestBody);
                blobUriString ??= data?.blobUri;
            }

            if (!Uri.TryCreate(blobUriString, UriKind.Absolute, out Uri blobUri))
            {
                var message = $"Failed to parse 'blobUri' in query or body: {blobUriString}";
                _logger.LogInformation(message);
                return(new BadRequestObjectResult(new { message }));
            }

            JObject report;

            try
            {
                report = await _mediaInfoReportService.GetMediaInfoCompleteInformForUriAsync(blobUri).ConfigureAwait(false);
            }
            catch (Exception e)
            {
                _logger.LogError(e, $"Failed to analyze {blobUri}");
                return(new BadRequestObjectResult(new { message = $"Failed to analyze {blobUri}", exception = e }));
            }

            return(new OkObjectResult(report));
        }
        /// <inheritdoc/>
        protected override async Task <ResponseBaseDTO> DoWorkAsync(RequestBlobAnalysisCreateDTO eventData, string eventType)
        {
            _ = eventData ?? throw new ArgumentNullException(nameof(eventData));
            _ = eventData.BlobUri ?? throw new ArgumentException("Blob uri cannot be null.");

            Log.LogEventObject(LogEventIds.AboutToCallAnalysisDeliveryEntry, eventData);
            var context = new StorageClientProviderContext(eventData.OperationContext);

            var analysisResult = await _mediaInfoReportService.GetMediaInfoCompleteInformForUriAsync(eventData.BlobUri, context).ConfigureAwait(true);

            Log.LogEventObject(LogEventIds.AnalysisOfDeliveryFileSuccessful, eventData);

            JObject blobMetadata = await _storageService.GetBlobMetadataAsync(eventData.BlobUri, context).ConfigureAwait(false);

            return(new ResponseBlobAnalysisSuccessDTO
            {
                OperationContext = eventData.OperationContext,
                BlobUri = eventData.BlobUri,
                BlobMetadata = blobMetadata,
                AnalysisResult = analysisResult,
            });
        }