/// <summary>
        /// This method will send data to the API for storage in the database
        /// </summary>
        /// <param name="productList">List of products with their image url</param>
        /// <returns></returns>
        private async Task <bool> SendDataToAPI(List <Products> productList)
        {
            try
            {
                var serverDetails = new SettingsService().LoadSettings();

                var productData = new ProductData
                {
                    Username = serverDetails.Username,
                    Password = serverDetails.Password,
                    Products = productList
                };

                var data = JsonConvert.SerializeObject(productData);

                var result = await HttpService.PostModelLinks(productData, serverDetails.ServerURL);

                if (result.Status.ToLowerInvariant().Equals("success"))
                {
                    return(true);
                }
                else
                {
                    ProcessingException?.Invoke("Could not save data to Server due to following reason. Reason:" + result.Message);
                    return(false);
                }
            }
            catch (Exception ex)
            {
                ProcessingException?.Invoke("There was an error while sending the data to the server. Exception: " + ex.Message);
                return(false);
            }
        }
Example #2
0
        private async Task ProcessQueueAsync(
            ChannelReader <TrackInfo> queueReader,
            CancellationToken cancellationToken = default)
        {
            while (await queueReader.WaitToReadAsync(cancellationToken)
                   .ConfigureAwait(false))
            {
                var info = await queueReader.ReadAsync(cancellationToken);

                _logger.LogInformation("Playing {title} ({url})",
                                       info.TrackName, info.OriginalLocation);

                CurrentTrack = info;

                try
                {
                    await ProcessQueueItemAsync(info, cancellationToken);
                }
                catch (OperationCanceledException)
                    when(!cancellationToken.IsCancellationRequested)
                    { /* expected for unsupported tracks */
                    }
                catch (Exception e)
                {
                    if (!(e is AggregateException aggregate))
                    {
                        aggregate = new AggregateException(e);
                    }

                    var args = new UnobservedTaskExceptionEventArgs(aggregate);
                    ProcessingException?.Invoke(this, args);

                    if (!args.Observed)
                    {
                        _logger.LogError(aggregate,
                                         "Unhandled exception occured while processing " +
                                         "queue. Track {url} may be skipped.",
                                         info.OriginalLocation);
                    }
                }
            }
        }
Example #3
0
        /// <summary>
        /// This method will store the data locally in the JSON file at the destination location
        /// </summary>
        /// <param name="productList">List of products</param>
        /// <param name="destinationLocation">Destination location path</param>
        private bool StoreDataLocally(List <Products> productList, string destinationLocation)
        {
            try
            {
                // Combine all the processed textfile in 1 Json file and place in the destiantion folder
                var destinationFile = Path.Combine(destinationLocation, "ParameterizedData.json");

                using (StreamWriter file = File.CreateText(destinationFile))
                {
                    JsonSerializer serializer = new JsonSerializer();
                    serializer.Serialize(file, productList);
                }

                return(true);
            }
            catch (Exception ex)
            {
                ProcessingException?.Invoke("There was an error while storing the data at local destination. Exception: " + ex.Message);
                return(false);
            }
        }
        /// <summary>
        /// Method to start converting the ifc files in to the GLTF format
        /// </summary>
        /// <param name="sourceLocation">Source location path</param>
        /// <param name="destinationLocation">Destination location path</param>
        /// <param name="destinationType">Type of destination, such as server, local or both</param>
        /// <returns>IFC convert Status to update the UI</returns>
        public async Task <IFCConvertStatus> ConvertFiles(string sourceLocation, string destinationLocation, DestinationLocationType destinationType)
        {
            try
            {
                return(await Task.Run(async() =>
                {
                    // Check if destination folder exist
                    if (!Directory.Exists(destinationLocation))
                    {
                        ProcessingException?.Invoke("The destination folder does not exist. Please specify the correct folder");
                        return IFCConvertStatus.Error;
                    }

                    // get all file names from the source location
                    var allFilenames = Directory.EnumerateFiles(sourceLocation).Select(p => Path.GetFileName(p));

                    // Get all filenames that have a .ifc extension
                    var files = allFilenames.Where(fn => Path.GetExtension(fn) == ".ifc");

                    // If there are no files, then return to notify the user
                    if (files == null || files.Count() == 0)
                    {
                        return IFCConvertStatus.NoFiles;
                    }

                    // Get total number of files, (need it for the progress bar)
                    var totalFiles = files.Count();

                    // Send the total count of the files to the viewmodel for update on UI
                    TotalFiles?.Invoke(totalFiles.ToString());

                    // Process each file and convert it
                    foreach (var file in files)
                    {
                        var sourceFile = Path.Combine(sourceLocation, file);
                        var filePathWithGLTFExtentsion = Path.ChangeExtension(file, ".glb");
                        var destinationFile = Path.Combine(destinationLocation, filePathWithGLTFExtentsion);
                        IFCConvert.Convert(sourceFile, destinationFile);
                        totalFiles--;

                        // Send message to UI to update progress bar
                        RemainingFiles?.Invoke((totalFiles).ToString());
                    }

                    // Send a call to the S3 bucket to upload data and the API
                    if (destinationType == DestinationLocationType.Both)
                    {
                        var productList = UploadModels(files, sourceLocation, destinationLocation);

                        if (productList != null)
                        {
                            var result = await SendDataToAPI(productList);

                            if (!result)
                            {
                                return IFCConvertStatus.Error;
                            }
                        }
                        else
                        {
                            return IFCConvertStatus.Error;
                        }
                    }

                    // Return success message
                    return IFCConvertStatus.Done;
                }));
            }
            catch (Exception ex)
            {
                ProcessingException?.Invoke("There was an error while converting the IFC files. Exception: " + ex.Message);
                return(IFCConvertStatus.Error);
            }
        }
        /// <summary>
        /// This method will utilize the S3UploadService to upload the converted models to the S3 bucket.
        /// </summary>
        /// <param name="files">List of files that need to be uploaded</param>
        /// <param name="sourceLocation"></param>
        /// <param name="destinationLocation"></param>
        /// <returns>Return list of products or null</returns>
        private List <Products> UploadModels(IEnumerable <string> files, string sourceLocation, string destinationLocation)
        {
            try
            {
                // Get the AWS details from the settings
                var awsDetails = new SettingsService().LoadSettings();

                // Initialization
                var uploader    = new S3UploadService(awsDetails.BucketName, awsDetails.AccessKey, awsDetails.SecretKey);
                var sourceFiles = new List <string>();
                var productUrls = new List <Products>();

                // Create 3dModel Folder on AWS to upload the models
                uploader.CreateFolder();

                // Get the List of all 3D Models
                foreach (var file in files)
                {
                    var sourceFile = Path.Combine(sourceLocation, file);
                    var filePathWithGLTFExtentsion = Path.ChangeExtension(file, ".glb");
                    var sourceFilePath             = Path.Combine(destinationLocation, filePathWithGLTFExtentsion);
                    sourceFiles.Add(sourceFilePath);
                }

                // Model Count for Progress bar
                var totalModels = files.Count();
                var uploaded    = 0;

                // Create separate threads to upload files on the AWS.
                Parallel.ForEach(sourceFiles, currentFile =>
                {
                    // Call a method to see if the file is created at the location or not before accessing it.
                    var fileFound   = WaitForFile(currentFile);
                    string filename = Path.GetFileName(currentFile);

                    // If file is found, then start uploading process
                    // else send a message to the user with the issue related to filename.
                    if (fileFound)
                    {
                        var product = new Products
                        {
                            Code              = Path.GetFileNameWithoutExtension(currentFile),
                            ModelURL          = uploader.UploadFile(currentFile, filename),
                            ProductParameters = null
                        };

                        productUrls.Add(product);
                        uploaded++;
                        RemainingModels?.Invoke((totalModels - uploaded).ToString());
                    }
                    else
                    {
                        ProcessingException?.Invoke("The file: " + filename + " could not be found in the destination folder for uploading");
                    }
                });

                // Return list of all the urls for the uploaded objects
                return(productUrls);
            }
            catch (Exception ex)
            {
                ProcessingException?.Invoke("There was an exeception while uploading the files to S3 bucket. Exception: " + ex.Message);
                return(null);
            }
        }
Example #6
0
        /// <summary>
        /// Method to process the text file and generate JSON files
        /// </summary>
        /// <param name="sourceLocation">Source location path</param>
        /// <param name="destinationLocation">Destination location path</param>
        /// <returns>Textfile processing Status to update the UI</returns>
        public async Task <TextfileProcessingStatus> ProcessFiles(string sourceLocation, string destinationLocation, DestinationLocationType destinationType)
        {
            try
            {
                return(await Task.Run(async() =>
                {
                    // get all file names from the source location
                    var allFilenames = Directory.EnumerateFiles(sourceLocation).Select(p => Path.GetFileName(p));

                    // Get all filenames that have a .txt extension
                    var files = allFilenames.Where(fn => Path.GetExtension(fn) == ".txt");

                    // If there are no files, then return to notify the user
                    if (files == null || files.Count() == 0)
                    {
                        return TextfileProcessingStatus.NoFiles;
                    }

                    // Get total number of files, (need it for the progress bar)
                    var totalFiles = files.Count();

                    // Send the total count of the files to the viewmodel for update on UI
                    TotalFiles?.Invoke(totalFiles.ToString());

                    // List for all the products with their key value pairs of data. This list will be serialzied and sent to the API
                    var productList = new List <Products>();

                    // Process each file and convert it
                    foreach (var file in files)
                    {
                        // Get the path for the source file
                        var sourceFile = Path.Combine(sourceLocation, file);

                        // Read all the lines of the file
                        var lines = File.ReadAllLines(sourceFile).ToArray();

                        // Final Heading Tokens after being cleaned and formatted would be stored in this list
                        var finalHeadings = ProcessHeaderString(lines[0]);

                        // Loop over rest of the lines apart from the heading line
                        foreach (var line in lines.Skip(1))
                        {
                            // Will contain the values from the CSV file
                            var content = ProcessData(line);

                            // Time to process the strings and convert to Json
                            // However, if this condition is not satisfied, that means there is something wrong with the file. We need to alert the user.
                            if (content != null && finalHeadings != null && content.Count() > 0 && finalHeadings.Count > 0 && finalHeadings.Count == content.Count)
                            {
                                var product = new Products
                                {
                                    ProductParameters = new List <ProductParameters>(),
                                };

                                // Now make the key value pairs of the tokenized strings
                                for (var i = 0; i < finalHeadings.Count; i++)
                                {
                                    // add a check to fill out the product code if the token is "Product Code". Then we need to update the product code
                                    // otherwise, fill out key value pairs
                                    if (finalHeadings[i].ToLowerInvariant().Equals("product code"))
                                    {
                                        product.Code = content[i];
                                    }
                                    else
                                    {
                                        var productParam = new ProductParameters
                                        {
                                            Key = finalHeadings[i],
                                            Value = content[i]
                                        };

                                        product.ProductParameters.Add(productParam);
                                    }
                                }

                                productList.Add(product);
                            }
                            else
                            {
                                ColumnMismatch?.Invoke("A mismatch between heading and content columns occured in file: " + Path.GetFileNameWithoutExtension(file));
                            }
                        }

                        totalFiles--;

                        // Send message to UI to update progress bar
                        RemainingFiles?.Invoke((totalFiles).ToString());
                    }

                    // check user's preference and save or send the file accordingly.
                    if (destinationType == DestinationLocationType.Local)
                    {
                        var result = StoreDataLocally(productList, destinationLocation);
                        return result ? TextfileProcessingStatus.Done : TextfileProcessingStatus.Error;
                    }
                    else if (destinationType == DestinationLocationType.Server)
                    {
                        var result = await SendDataToAPI(productList);
                        return result ? TextfileProcessingStatus.Done : TextfileProcessingStatus.Error;
                    }
                    else if (destinationType == DestinationLocationType.Both)
                    {
                        var localStorageResult = StoreDataLocally(productList, destinationLocation);
                        var serverStorageResult = await SendDataToAPI(productList);
                        return (localStorageResult && serverStorageResult) ? TextfileProcessingStatus.Done : TextfileProcessingStatus.PartialSuccess;
                    }

                    // Return success message
                    return TextfileProcessingStatus.Done;
                }));
            }
            catch (Exception ex)
            {
                ProcessingException?.Invoke("There was an error while processing the textfiles. Exception: " + ex.Message);
                return(TextfileProcessingStatus.Error);
            }
        }